如何基于Graphene / Django上的用户类型限制对模型的字段访问? [英] How to limit field access on a model based on user type on Graphene/Django?

查看:105
本文介绍了如何基于Graphene / Django上的用户类型限制对模型的字段访问?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

假设我有一个模型:

  class Employee(models.Model):
first_name = models。 CharField(max_length = 40)
last_name = models.CharField(max_length = 60)
工资= models.DecimalField(decimal_places = 2)

我希望任何人都可以访问first_name和last_name,但只希望某些用户能够读取薪水,因为这是机密数据。



然后我想将工资的写入/更新限制为什至是另一种类型的用户。



我如何限制字段的读取/写入/更新



编辑:



这是在GraphQL中API上下文。我正在使用石墨烯。我想在解析器功能中看到一个可扩展的解决方案。

解决方案

查询


假设您拥有


  1. 定义为


    employees = graphene.List(EmployeeType)


  2. $ b $的查询b
  3. 用于查询的解析器,例如


    def resolve_employees(self,info,** kwargs):
    返回Employee.objects.all()




  1. 权限在名为 can_view_salary can_edit_salary


的员工模型上

然后,您需要定义 EmployeeType ,其值取决于用户的 salary 。像

 从graphene_django.types从myapp.models导入DjangoObjectType 
导入Employee

类EmployeeType(DjangoObjectType ):
class Meta:
model = Employee

def resolve_salary(self,info):
if info.context.user.has_perm('myapp.can_view_salary' ):
返回self.salary
返回None

重要的要点是您正在创建一个自定义的解决函数,用于根据权限值切换的薪水。您不需要为 first_name last_name 创建任何其他解析程序。


< BR>




变异


先阅读文档。但没有示例进行更新。


简而言之,这是您可以采用的方法:


  1. 创建一种方法以将员工设置为 Mutation 方法


    类MyMutations(graphene.ObjectType):
    set_employee = SetEmployee.Field()



  2. SetEmployee 创建一个方法,该方法获取Employee对象并对其进行更新。某些用户将忽略薪金字段。再次注意,通过将字符串作为输入,我忽略了十进制问题。


    class SetEmployee(graphene.Mutation):

     类参数:
    id = graphene.ID()
    first_name = graphene.String()
    last_name = graphene.String()
    工资= graphene.String()

    员工= graphene.Field(lambda:EmployeeType)


    @classmethod
    def mutate(cls,root,info,** args):
    employee_id = args.get('employee_id')

    #按id获取雇员对象
    employee = Employee.objects.get(id = employee_id)
    first_name = args.get('first_name')
    last_name = args.get('last_name')
    薪水= args.get('薪水')

    #如果first_name:
    employee.first_name = first_name
    ,如果姓氏:
    employee.last_name,则从变异输入
    中更新employee字段= last_name
    (如果有薪金和info.context.user)。 has_perm('myapp.can_edit_salary'):
    employee.salary =薪水
    employee.save()
    return SetEmployee(employee = employee)




Let's say I have a model:

class Employee(models.Model):
    first_name = models.CharField(max_length=40)
    last_name = models.CharField(max_length=60)
    salary = models.DecimalField(decimal_places=2)

I want anyone to be able to access first_name and last_name but only want certain users to be able to read salary because this is confidential data.

And then I want to restrict write/update for salary to an even different kind of user.

How do I restrict field read/write/update depending on the request user?

EDIT:

This is in the GraphQL API context. I am using Graphene. I'd like to see a scalable solution in the resolver function.

解决方案

QUERIES

Assuming that you have

  1. a query defined like

    employees = graphene.List(EmployeeType)

  2. a resolver for the query like

    def resolve_employees(self, info, **kwargs): return Employee.objects.all()

and

  1. permissions on your Employee model called can_view_salary and can_edit_salary

Then you'll need to define the EmployeeType with a value of salary that is dependent on the user. Something like

from graphene_django.types import DjangoObjectType
from myapp.models import Employee

class EmployeeType(DjangoObjectType):
    class Meta:
        model = Employee
        
    def resolve_salary(self, info):
        if info.context.user.has_perm('myapp.can_view_salary'):
            return self.salary
        return None

The important takeaway is that you're creating a custom resolve function for the salary that is switching based on the value of a permission. You don't need to create any other resolvers for first_name and last_name.




MUTATIONS

Read the documentation first. But there isn't an example for doing an update.

In brief, here's the approach that you can take:

  1. Create a method to set the employee in your Mutation method

    class MyMutations(graphene.ObjectType): set_employee = SetEmployee.Field()

  2. Create a method for SetEmployee that gets the Employee object and updates it. The salary field is ignored for certain users. Note again that I am ignoring the Decimal issue by taking a string as an input.

    class SetEmployee(graphene.Mutation):

     class Arguments:
         id = graphene.ID()
         first_name = graphene.String()
         last_name = graphene.String()
         salary = graphene.String()
    
     employee = graphene.Field(lambda: EmployeeType)
    
    
     @classmethod
     def mutate(cls, root, info, **args):
         employee_id = args.get('employee_id')
    
         # Fetch the employee object by id
         employee = Employee.objects.get(id=employee_id)
         first_name = args.get('first_name')
         last_name = args.get('last_name')
         salary = args.get('salary')
    
         # Update the employee fields from the mutation inputs
         if first_name:
             employee.first_name = first_name
         if last_name:
             employee.last_name = last_name
         if salary and info.context.user.has_perm('myapp.can_edit_salary'):
             employee.salary = salary
         employee.save()
         return SetEmployee(employee=employee)
    

这篇关于如何基于Graphene / Django上的用户类型限制对模型的字段访问?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆