Umar.H
Umar.H

Reputation: 23099

django not picking up migration where managed = False

I have a simple web-app I'm trying to create to visualise some carbon data (to teach myself Django!)

As my data model is a little complex I use the managed=False and import a view from my postgres database where I wrangle my data.

When I first ran the migration I noticed I left in a field that I didn't have in my view, so naturally I changed it. Now when I run makemigrations for my app called carbon it says there are no changes.

What is the correct way to remedy this?

additionally, for some reason when I try to run an orm query to pull in some data it expected me to have an id field in my view, can someone explain this, if possible?

models.py

class CarbonViewHour(models.Model):
    daily_hour = models.CharField(max_length=50)
    reading    = models.FloatField()
    #date       = models.DateField() This was removed 

    class Meta:
       managed = False
       db_table = 'carbon_v_hourly_meter_readings'

    def __str__(self) -> str:
        return f"{self.reading}-{self.daily_hour}"

the change I made was to remove a field from CarbonTimeView

date       = models.DateField()

views.py

class CarbonTimeView(TemplateView):
    
    template_name = 'carbon/chart.html'
    
    def get_context_data(self, **kwargs):
        context = super().get_context_data(**kwargs)
        context['qsm'] = CarbonViewMinute.objects.all().order_by('date')
        context['qsh'] = CarbonViewHour.objects.all()
        context['title'] = 'Daily Carbon Data'
        return context

SQL View.

DROP VIEW IF EXISTS public.carbon_v_hourly_meter_readings;
CREATE VIEW public.carbon_v_hourly_meter_readings
AS 

with cte AS ( 
    SELECT  -1             as id  -- im not sure why but Django expected an ID field? 
        ,   t.hour_num as daily_hour
        ,   c.reading
        ,   c.meter 

    FROM public.carbon_carbon c 
    INNER JOIN public.d_time_long t -- time dimension 
        ON c.date::time = t.full_time          

    WHERE DATE(c.date)   = (select max(DATE(c.date))
                    FROM public.carbon_carbon c )

    )

    SELECT  id 
        ,   daily_hour
        ,   AVG(reading) as reading 
        ,   meter 
    
    FROM cte 

    GROUP BY id
        ,    daily_hour 
        ,    meter

    ORDER BY daily_hour;



    

Upvotes: 1

Views: 1002

Answers (2)

Anzar
Anzar

Reputation: 1

I know this post is too old, but i got the same issue and now i was working on a new project with Django and created a new app only for my Databases views models and of course, each one is writed with managed = False inside, and it worked. Dont ask me why, it just worked

Upvotes: 0

iklinac
iklinac

Reputation: 15738

From Django documentation


Options.managed

If False, no database table creation, modification, or deletion operations will be performed for this model. This is useful if the model represents an existing table or a database view that has been created by some other means. This is the only difference when managed=False. All other aspects of model handling are exactly the same as normal. This includes

Adding an automatic primary key field to the model if you don’t declare it. To avoid confusion for later code readers, it’s recommended to specify all the columns from the database table you are modeling when using unmanaged models.

Django is also not capable to do any migrations to views, that is why they are generally left as unmanaged an used scarcely

Upvotes: 1

Related Questions