Skip to content

Allow custom public share tokens for form links#3311

Open
alexander-rebello wants to merge 8 commits intonextcloud:mainfrom
alexander-rebello:main
Open

Allow custom public share tokens for form links#3311
alexander-rebello wants to merge 8 commits intonextcloud:mainfrom
alexander-rebello:main

Conversation

@alexander-rebello
Copy link
Copy Markdown

This adds admin-gated custom tokens for public Forms share links. By default the feature is disabled, so existing instances keep the current random-token behavior. When enabled by an admin, form owners can edit the token of an existing public link directly in the sharing sidebar, save it explicitly, and the old URL becomes invalid immediately.

It also adds the necessary backend support for token updates, keeps public-link routing compatible with custom tokens, and includes tests plus API documentation updates.

Signed-off-by: Alexander Rebello <me@alexander-rebello.de>
Signed-off-by: Alexander Rebello <me@alexander-rebello.de>
Signed-off-by: Alexander Rebello <me@alexander-rebello.de>
@codecov
Copy link
Copy Markdown

codecov Bot commented Apr 24, 2026

Codecov Report

❌ Patch coverage is 97.67442% with 1 line in your changes missing coverage. Please review.

Files with missing lines Patch % Lines
lib/Controller/ShareApiController.php 97.43% 1 Missing ⚠️

📢 Thoughts on this report? Let us know!

Signed-off-by: Alexander Rebello <me@alexander-rebello.de>
Signed-off-by: Alexander Rebello <me@alexander-rebello.de>
Signed-off-by: Alexander Rebello <me@alexander-rebello.de>
Chartman123
Chartman123 previously approved these changes Apr 24, 2026
Copy link
Copy Markdown
Collaborator

@Chartman123 Chartman123 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added some review comments on the PHP part

Comment thread docs/API_v3.md Outdated
Comment on lines +656 to +679
### Update a Public Share Token

- Endpoint: `/api/v3/forms/{formId}/shares/{shareId}/token`
- Method: `PATCH`
- Url-Parameters:
| Parameter | Type | Description |
|-----------|---------|-------------|
| _formId_ | Integer | ID of the form containing the share |
| _shareId_ | Integer | ID of the public link share to update |
- Parameters:
| Parameter | Type | Description |
|-----------|---------|-------------|
| _token_ | String | New token for the public share link |
- Restrictions:
- Only available when the admin setting _allowCustomPublicShareTokens_ is enabled.
- Only link shares can be updated.
- Token must be unique among link shares and only contain alphanumeric characters.
- Token length must be between 8 and 256 characters.
- Response: **Status-Code OK**, as well as the id of the updated share.

```
"data": 5
```

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wouldn't add a new endpoint for that, please use the already existing update share endpoint

Comment thread lib/Controller/PageController.php Outdated
#[OpenAPI(scope: OpenAPI::SCOPE_IGNORE)]
class PageController extends Controller {
private const TEMPLATE_MAIN = 'main';
private const PUBLIC_SHARE_HASH_REQUIREMENT = '[a-zA-Z0-9]{8,256}';
Copy link
Copy Markdown
Collaborator

@Chartman123 Chartman123 Apr 24, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could this be moved to our central Constants.php file?

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, makes sense

Comment thread lib/Controller/PageController.php Outdated
#[NoCSRFRequired()]
#[PublicPage()]
#[FrontpageRoute(verb: 'GET', url: '/s/{hash}', requirements: ['hash' => '[a-zA-Z0-9]{24,}'])]
#[FrontpageRoute(verb: 'GET', url: '/s/{hash}', requirements: ['hash' => self::PUBLIC_SHARE_HASH_REQUIREMENT])]
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would probably be good if we can decide here wether custom share tokens are allowed on that instance. But IIRC it's not working with dynamically defined requirements.

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Meaning it would be good, but can't be done in this instance? Or should I try?

Comment thread lib/Controller/ShareApiController.php Outdated
#[CORS()]
#[NoAdminRequired()]
#[ApiRoute(verb: 'PATCH', url: '/api/v3/forms/{formId}/shares/{shareId}/token')]
public function updateShareToken(int $formId, int $shareId, string $token): DataResponse {
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See other comment... Should be moved to already existing endpoint

Signed-off-by: Alexander Rebello <me@alexander-rebello.de>
Signed-off-by: Alexander Rebello <me@alexander-rebello.de>
@alexander-rebello alexander-rebello marked this pull request as draft April 24, 2026 08:53
@alexander-rebello alexander-rebello marked this pull request as ready for review April 24, 2026 08:57
@Chartman123 Chartman123 added enhancement New feature or request 3. to review Waiting for reviews feature: 👥 sharing settings labels Apr 24, 2026
@Chartman123 Chartman123 added this to the 5.3 milestone Apr 24, 2026
@Chartman123 Chartman123 dismissed their stale review April 24, 2026 09:58

Accidentally approved the PR instead of just adding the review comments

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

3. to review Waiting for reviews enhancement New feature or request feature: 👥 sharing settings

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants