'Django: How do you get user id on model.py page and set dynamically a default value

I have 2 models(Model Projects and Model Variables) in two apps (Projects app and Variables app). The models are not related in any ways. I want to set the default value in Projects with value in Variables

Model Projects:
class Projects(models.Model):
    completion_time = models.FloatField(default='0')

Model Variables:
class Variables(models.Model):
    user_var_id = models.OneToOneField(User, null=True, blank=True, on_delete=models.CASCADE)
    internal_completion_time = models.FloatField(default='0')   

I want users to set a value in the variables and when they create a new project they would have that value from the variables be set as a default value for a new project by default. eg how could i do something like this

variable = Variables.Objects.Get(user_var_id=current_user_id-that i dont know how to get)

class Projects(models.Model):
    completion_time = models.FloatField(default=variable.internal_completion_time )

I thought it could be done by adding dynamically the default value, querying the variables filtering for the user and adding the value to the model but i dont know how to get the current user id on the model.py page. How can i do this maybe with another method.



Solution 1:[1]

#to get request in models.py
from crequest.middleware import CrequestMiddleware
current_request = CrequestMiddleware.get_request()

pip install django-crequest

Step 1.Add crequest to INSTALLED_APPS in your settings.py

Step 2.Add crequest.middleware.CrequestMiddleware to MIDDLEWARE_CLASSES after the authentication and session middleware.

Solution 2:[2]

If you want to save through Admin panel, try this:

class VariablesAdmin(admin.ModelAdmin):
    def save_model(self, request, obj, form, change):
        obj.user_var_id = request.user.id
        super().save_model(request, obj, form, change)

If you want to save through api or view-set, try this:

variable = Variables()
variable.user_var_id = request.user.id
variable.save()

Solution 3:[3]

So what you want is that when a user creates a project it will get the value from their variables.

What you can do is create a signal so when a project is created it will get the user and the related field and add that into the project and then save.

https://docs.djangoproject.com/en/3.1/topics/signals/

Solution 4:[4]

Inside your views, request.user.id will always return the id of the current user. You can simply use that in your queries to get the models you want. You are also wrongly capitalizing both 'object' and 'get' in your code, which is incorrect.

So your query should look like this:

variable = Variables.objects.get(user_var_id=request.user.id)

EDIT: You seem to want access to a 'current user' inside your models file, rather than (logically) inside your views file; request.user.id is only available in views, since every view receives a request.

Solution 5:[5]

From @Surya Pratap Rana, you can add the below in models.py

#to get request in models.py
from django.contrib.auth.models import User
from crequest.middleware import CrequestMiddleware
from rest_framework.request     import Request
current_request = CrequestMiddleware.get_request(User)

and in your class that you need add user login as default

owner = models.ForeignKey('auth.User', null=True, on_delete=models.CASCADE, default=current_request)

I used this method in my program.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2 Purnendu Kar
Solution 3 Bryant
Solution 4
Solution 5