Background
setActorDispatcher() currently accepts a single path pattern, which means a Fedify application can only serve actors under one URL structure—typically /users/{identifier}. This has come up as a limitation in at least two distinct scenarios.
Fixed paths with no identifier
Some applications have an instance-level actor at a fixed path like /actor, which doesn't fit the {identifier} pattern at all. Today the only way to handle this is to let the actor dispatcher return null for a sentinel identifier and catch the fall-through in a separate framework route. It works, but it splits logic that belongs together.
Multiple path patterns by actor type
Other applications want to distinguish actor types in the URL structure, e.g., /people/{identifier} for Person actors and /groups/{identifier} for Group actors. This is a reasonable design, but setActorDispatcher() only accepts one pattern, so there's no way to express it.
What would good API look like?
For the fixed-path case, one option is an alias mechanism—a way to tell Fedify that requests to /actor should be dispatched with a specific synthetic identifier:
federation
.setActorDispatcher("/users/{identifier}", callback)
.mapActorAlias("/actor", "__instance__");
For the multiple-pattern case, allowing setActorDispatcher() to be called more than once per Federation is the most natural fit:
federation
.setActorDispatcher("/people/{identifier}", async (ctx, identifier) => { /* Person */ })
.setActorDispatcher("/groups/{identifier}", async (ctx, identifier) => { /* Group */ });
But this raises a question about getActorUri(): with multiple patterns registered, Fedify can't know which one to use for a given identifier without more information. Something like a type hint might be needed:
ctx.getActorUri(identifier, { type: Person })
ctx.getActorUri(identifier, { type: Group })
Open questions
These two cases might call for separate solutions, or they might be unified under a single design. A few things worth discussing:
- Are there other scenarios that should inform the design?
- For the multi-pattern case, is a type hint on
getActorUri() the right approach, or is there a cleaner way to resolve ambiguity?
- How should WebFinger behave when there are multiple path patterns? Should Fedify infer the canonical actor URI from the type of the returned object?
- Should the fixed-path case be treated as a special case of multi-pattern support, or addressed separately?
Background
setActorDispatcher()currently accepts a single path pattern, which means a Fedify application can only serve actors under one URL structure—typically/users/{identifier}. This has come up as a limitation in at least two distinct scenarios.Fixed paths with no identifier
Some applications have an instance-level actor at a fixed path like
/actor, which doesn't fit the{identifier}pattern at all. Today the only way to handle this is to let the actor dispatcher returnnullfor a sentinel identifier and catch the fall-through in a separate framework route. It works, but it splits logic that belongs together.Multiple path patterns by actor type
Other applications want to distinguish actor types in the URL structure, e.g.,
/people/{identifier}forPersonactors and/groups/{identifier}forGroupactors. This is a reasonable design, butsetActorDispatcher()only accepts one pattern, so there's no way to express it.What would good API look like?
For the fixed-path case, one option is an alias mechanism—a way to tell Fedify that requests to
/actorshould be dispatched with a specific synthetic identifier:For the multiple-pattern case, allowing
setActorDispatcher()to be called more than once perFederationis the most natural fit:But this raises a question about
getActorUri(): with multiple patterns registered, Fedify can't know which one to use for a given identifier without more information. Something like a type hint might be needed:Open questions
These two cases might call for separate solutions, or they might be unified under a single design. A few things worth discussing:
getActorUri()the right approach, or is there a cleaner way to resolve ambiguity?