class Token(models.Model): REQUEST = 1 ACCESS = 2 TOKEN_TYPES = ((REQUEST, u'Request'), (ACCESS, u'Access')) key = models.CharField(max_length=KEY_SIZE, null=True, blank=True) secret = models.CharField(max_length=SECRET_SIZE, null=True, blank=True) token_type = models.SmallIntegerField(choices=TOKEN_TYPES, db_index=True) timestamp = models.IntegerField(default=long(time())) is_approved = models.BooleanField(default=False) lrs_auth_id = models.CharField(max_length=50, null=True) user = models.ForeignKey(User, null=True, blank=True, related_name='tokens', db_index=True) consumer = models.ForeignKey(Consumer) scope = models.CharField(max_length=100, default="statements/write,statements/read/mine") ## OAuth 1.0a stuff verifier = models.CharField(max_length=VERIFIER_SIZE) callback = models.CharField(max_length=MAX_URL_LENGTH, null=True, blank=True) callback_confirmed = models.BooleanField(default=False) objects = TokenManager() def __unicode__(self): return u"%s Token %s for %s" % (self.get_token_type_display(), self.key, self.consumer) def scope_to_list(self): return self.scope.split(",") def timestamp_asdatetime(self): return datetime.fromtimestamp(self.timestamp) def key_partial(self): return self.key[:10] def to_string(self, only_key=False): token_dict = { 'oauth_token': self.key, 'oauth_token_secret': self.secret, 'oauth_callback_confirmed': self.callback_confirmed and 'true' or 'error' } if self.verifier: token_dict['oauth_verifier'] = self.verifier if only_key: del token_dict['oauth_token_secret'] del token_dict['oauth_callback_confirmed'] return urllib.urlencode(token_dict) def generate_random_codes(self): """ Used to generate random key/secret pairings. Use this after you've added the other data in place of save(). """ key = generate_random(length=KEY_SIZE) secret = generate_random(length=SECRET_SIZE) while Token.objects.filter( models.Q(key__exact=key) | models.Q(secret__exact=secret)).count(): key = generate_random(length=KEY_SIZE) secret = generate_random(length=SECRET_SIZE) self.key = key self.secret = secret self.save() def get_callback_url(self): """ OAuth 1.0a, append the oauth_verifier. """ if self.callback and self.verifier: parts = urlparse.urlparse(self.callback) scheme, netloc, path, params, query, fragment = parts[:6] if query: query = '%s&oauth_verifier=%s' % (query, self.verifier) else: query = 'oauth_verifier=%s' % self.verifier return urlparse.urlunparse( (scheme, netloc, path, params, query, fragment)) return self.callback
class Token(models.Model): REQUEST = 1 ACCESS = 2 TOKEN_TYPES = ((REQUEST, u'Request'), (ACCESS, u'Access')) key = models.CharField(max_length=KEY_SIZE, null=True, blank=True) secret = models.CharField(max_length=SECRET_SIZE, null=True, blank=True) token_type = models.SmallIntegerField(choices=TOKEN_TYPES) timestamp = models.IntegerField(default=default_token_timestamp) is_approved = models.BooleanField(default=False) user = models.ForeignKey(AUTH_USER_MODEL, null=True, blank=True, related_name='tokens') consumer = models.ForeignKey(Consumer) scope = models.ForeignKey(Scope, null=True, blank=True) @property def resource(self): return self.scope @resource.setter def resource(self, value): self.scope = value ## OAuth 1.0a stuff verifier = models.CharField(max_length=VERIFIER_SIZE) callback = models.CharField(max_length=MAX_URL_LENGTH, null=True, blank=True) callback_confirmed = models.BooleanField(default=False) objects = TokenManager() def __unicode__(self): return u"%s Token %s for %s" % (self.get_token_type_display(), self.key, self.consumer) def to_string(self, only_key=False): token_dict = { 'oauth_token': self.key, 'oauth_token_secret': self.secret, 'oauth_callback_confirmed': self.callback_confirmed and 'true' or 'error' } if self.verifier: token_dict['oauth_verifier'] = self.verifier if only_key: del token_dict['oauth_token_secret'] del token_dict['oauth_callback_confirmed'] return six.moves.urllib.parse.urlencode(token_dict) def generate_random_codes(self): """ Used to generate random key/secret pairings. Use this after you've added the other data in place of save(). """ self.key = uuid.uuid4().hex self.secret = get_random_string(length=SECRET_SIZE) self.save() def get_callback_url(self, args=None): """ OAuth 1.0a, append the oauth_verifier. """ if self.callback and self.verifier: parts = six.moves.urllib.parse.urlparse(self.callback) scheme, netloc, path, params, query, fragment = parts[:6] if query: query = '%s&oauth_verifier=%s' % (query, self.verifier) else: query = 'oauth_verifier=%s' % self.verifier # workaround for non-http scheme urlparse problem in py2.6 (issue #2) if "?" in path: query = "%s&%s" % (path.split("?")[-1], query) path = "?".join(path[:-1]) if args is not None: query += "&%s" % six.moves.urllib.parse.urlencode(args) return six.moves.urllib.parse.urlunparse((scheme, netloc, path, params, query, fragment)) args = args is not None and "?%s" % six.moves.urllib.parse.urlencode(args) or "" return self.callback and self.callback + args def set_callback(self, callback): if callback != OUT_OF_BAND: # out of band, says "we can't do this!" if check_valid_callback(callback): self.callback = callback self.callback_confirmed = True self.save() else: raise oauth.Error('Invalid callback URL.')