【问题标题】:ApiKey authentication in tastypie with mongoengine使用 mongoengine 在美味派中进行 ApiKey 身份验证
【发布时间】:2013-10-06 19:56:42
【问题描述】:

有没有人成功地从 mongoengine.django.auth 为 User 实现 ApiKey 以与tastepie ApiKeyAuthentication 一起使用?

我知道之前关于此事的帖子,但它们仅针对 ORM,而我正在尝试为 mongoengine 设置它。另外,tastepie 自己的 ApiKey 类似乎严重依赖关系结构(使用 User 的相关字段api_key

提前致谢!

【问题讨论】:

    标签: api restful-authentication mongoengine tastypie


    【解决方案1】:

    按照这个线程https://github.com/mitar/django-tastypie-mongoengine/issues/25,我创建了带有 api_key 字段的 MongoUser 类

    # models.py (or documents.py)
    from mongoengine.django.auth import User
    
    class MongoUser(User):
        """
        Subclass of mongoengine.django.auth.User with email as username
        and API key for authentication.
        """
        USERNAME_FIELD = 'email'
        REQUIRED_FIELDS = ['password']
    
        api_key = StringField(max_length=256, default='')
        api_key_created = DateTimeField(help_text=_(u'Created'))
    
        def save(self, *args, **kwargs):
            if not self.api_key:
                self.set_api_key()
    
            return super(MongoUser, self).save(*args, **kwargs)
    
        def set_api_key(self):
            self.api_key = self.generate_key()
            self.api_key_created = datetime.now()
    
        def generate_key(self):
            new_uuid = uuid.uuid4()
            return hmac.new(str(new_uuid), digestmod=sha1).hexdigest()
    

    添加了一个信号(通常):

    # resources.py
    from mongoengine import signals
    from myapp import models
    signals.post_save.connect(create_api_key, sender=models.MongoUser)
    

    然后使用以下子类化tastepie.ApiKeyAuthentication:

    # resources.py
    class CustomApiKeyAuthentication(ApiKeyAuthentication):
        """
        Authenticates everyone if the request is GET otherwise performs
        ApiKeyAuthentication.
        """
        def is_mongouser_authenticated(self, request):
            """
            Custom solution for MongoUser ApiKey authentication.
            ApiKey here is not a class (as it is realized in ORM approach),
            but a field MongoUser class.
            """
            username, api_key = super(CustomApiKeyAuthentication,
                                      self).extract_credentials(request)
            try:
                models.MongoUser.objects.get(username=username, api_key=api_key)
            except models.MongoUser.DoesNotExist:
                return False
    
            return True
    
        def is_authenticated(self, request, **kwargs):
            """
            Custom solution for `is_authenticated` function: MongoUsers has got
            authenticated through custom api_key check.
            """
            if request.method == 'GET':
                return True
            try:
                is_authenticated = super(CustomApiKeyAuthentication,
                                         self).is_authenticated(request, **kwargs)
            except TypeError as e:
                if "MongoUser" in str(e):
                    is_authenticated = self.is_mongouser_authenticated(request)
                else:
                    is_authenticated = False
            return is_authenticated
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2013-08-27
      • 2016-02-23
      • 2020-12-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多