Skip to content

Token-to-Actor Binding #252

@aaronjae22

Description

@aaronjae22

Authorization Per Lola Spec: "The advertised OAuth endpoint MUST support the activitypub_account_portability scope. That scope MUST be limited to one account. If there is more than one account on the source server, the source MUST NOT allow the token to access any account other than the granted one."

Currently:

  1. User Alice approves a portability request → a token is created
  2. That token has the scope activitypub_account_portability — it says "this token is for migration"
  3. But the token has no record of which actor it belongs to
  4. So anyone holding that token can hit /api/actors/42/followers/ or /api/actors/99/blocked/ and get data for any actor, not just Alice's

Best option is to create a new model that just records "this token -> this actor":

class TokenActorBinding(models.Model):
    token = models.OneToOneField(AccessToken, on_delete=models.CASCADE)
    actor = models.ForeignKey(Actor, on_delete=models.CASCADE)
    created_at = models.DateTimeField(auto_now_add=True)

django-oauth-toolkits indicate in its own source code that on save_bearer_token: "Override _save_bearer_token and not this function when adding custom logic for the storing of these tokens.". The validator subclass is already wired in (OAUTH2_VALIDATOR_CLASS points to our ActivityPubOAuth2Validator). We're just adding one more method override to a class we already own.

def save_bearer_token(self, token, request, *args, **kwargs):
    """
    Save access and refresh token.

    Override _save_bearer_token and not this function when adding custom logic
    for the storing of these token. This allows the transaction logic to be
    separate from the token handling.
    """
    # Use the AccessToken's database instead of making the assumption it is in 'default'.
    with transaction.atomic(using=router.db_for_write(AccessToken)):
        return self._save_bearer_token(token, request, *args, **kwargs)

Metadata

Metadata

Assignees

Labels

No labels
No labels

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions