feat(sharings): Effective recipients endpoints - #4885
Conversation
Factor the resolution of sharings applying to a target out of `scopesFor`, without the membership filter, so the effective recipients computation can reuse it. The root info now carries the root name, and sharing IDs are sorted to keep a deterministic order between identical calls.
|
why do we need 2 apis? why not only |
ok, I got it, but then we need to proxy call to an owner instance and check the permission on the owner side and maybe it's also time to have only one API insted of two, especially if we don't need to support legacy ones and to have somehting like |
It is part of the spec and it seemed reasonable since we have separate routes for everything related to drives at the moment. |
4049a67 to
f7b0947
Compare
| } | ||
|
|
||
| func (a *apiEffectiveRecipient) ID() string { return a.id } | ||
| func (a *apiEffectiveRecipient) Rev() string { return "" } |
There was a problem hiding this comment.
why do we need all these fields in this model? links, relationships, rev? we don't have them, actually
There was a problem hiding this comment.
It's the JSON-API interface.
377e1d6 to
54132bd
Compare
Add a read-only view combining the people who can access a file or folder through its own share and through inherited ancestor shares. Recipients are deduplicated by instance with an email fallback, read-write wins over read-only, the most advanced status is kept via `statusRank`, and each recipient exposes the sources through which the access is granted. No sharing document is mutated.
Expose `GET /sharings/recipients/:file-id` and `GET /sharings/drives/:id/recipients/:file-id` returning the effective recipients of a file or folder as JSON-API. Public share tokens (share-by-link, share preview) are rejected: a link holder must not enumerate sharing members. The response meta carries the target `file_id`. The drive route goes through the shared-drive `proxy()`: on a recipient instance the request is forwarded to the owner with the drive token, so the access check and the recipients resolution run where every sharing applying to the target is known. Membership is enforced owner-side by the `share-interact` permission.
54132bd to
939b537
Compare
Closes #4840
What
Two new read-only endpoints returning the combined list of people who can
access a file or folder, including access inherited from parent shared
folders:
GET /sharings/recipients/:file-idGET /sharings/drives/:id/recipients/:file-idHow
AccessResolver.applicableSharings(extracted fromscopesFor) resolvesevery active additive scope applying to the target — its own share plus
shares inherited from ancestor folders — with no membership filtering.
EffectiveRecipientscollects the direct members of every applicableio.cozy.sharingsdoc (revoked members excluded), deduplicates byinstancewith anemailfallback, lets read-write win over read-only,and keeps the most advanced status.
sources(sharing_id,root_id,root_name,kind,member_index,read_only,manageable) and acan_edit_hereflag (true when at least one source is the target's ownshare).
file_idinmeta.Security / authorization
and the target must belong to that drive.
holder must not be able to enumerate sharing members.
No mutation: these are read-only endpoints, no inherited member is copied
into child sharings.
Tests
model/sharing/effective_recipients_test.go: deduplication(instance/email/bridge between the two), read-only/status merging,
revoked exclusion,
manageable.web/sharings/effective_recipients_test.go: both endpoints, inheritancefrom ancestors, public token rejection, error cases (target outside the
drive, inactive drive, non-member).