+5
-5
docs/extensions.md
+5
-5
docs/extensions.md
···
425
425
426
426
### Documenting Scope Requirements
427
427
428
-
Use the `#[RequiresScope]` attribute to document which OAuth scopes your extension methods require. This helps with documentation and enables scope checking in authenticated mode:
428
+
Use the `#[ScopedEndpoint]` attribute to document which OAuth scopes your extension methods require. This helps with documentation and enables scope checking in authenticated mode:
429
429
430
430
```php
431
-
use SocialDept\AtpClient\Attributes\RequiresScope;
431
+
use SocialDept\AtpClient\Attributes\ScopedEndpoint;
432
432
use SocialDept\AtpClient\Client\Requests\Request;
433
433
use SocialDept\AtpClient\Enums\Scope;
434
434
435
435
class BskyMetricsClient extends Request
436
436
{
437
-
#[RequiresScope(Scope::TransitionGeneric, granular: 'rpc:app.bsky.feed.getTimeline')]
437
+
#[ScopedEndpoint(Scope::TransitionGeneric, granular: 'rpc:app.bsky.feed.getTimeline')]
438
438
public function getTimelineMetrics(): array
439
439
{
440
440
$timeline = $this->atp->bsky->feed->getTimeline();
441
441
// Process and return metrics...
442
442
}
443
443
444
-
// Methods without #[RequiresScope] work in both public and authenticated modes
444
+
// Methods without #[ScopedEndpoint] work in both public and authenticated modes
445
445
public function getPublicPostMetrics(string $uri): array
446
446
{
447
447
$thread = $this->atp->bsky->feed->getPostThread($uri);
···
450
450
}
451
451
```
452
452
453
-
Methods with `#[RequiresScope]` indicate they require authentication, while methods without it can work in public mode. See [scopes.md](scopes.md) for full documentation on scope handling.
453
+
Methods with `#[ScopedEndpoint]` indicate they require authentication, while methods without it can work in public mode. See [scopes.md](scopes.md) for full documentation on scope handling.
454
454
455
455
## Available Domains
456
456
+17
-17
docs/scopes.md
+17
-17
docs/scopes.md
···
23
23
Scope::identity('handle') // Identity attribute access
24
24
```
25
25
26
-
### RequiresScope Attribute
26
+
### ScopedEndpoint Attribute
27
27
28
28
```php
29
-
use SocialDept\AtpClient\Attributes\RequiresScope;
29
+
use SocialDept\AtpClient\Attributes\ScopedEndpoint;
30
30
use SocialDept\AtpClient\Enums\Scope;
31
31
32
-
#[RequiresScope(Scope::TransitionGeneric)]
32
+
#[ScopedEndpoint(Scope::TransitionGeneric)]
33
33
public function getTimeline(): GetTimelineResponse
34
34
{
35
35
// Method implementation
···
73
73
'identity:handle' // Manage handle
74
74
```
75
75
76
-
## The RequiresScope Attribute
76
+
## The ScopedEndpoint Attribute
77
77
78
-
The `#[RequiresScope]` attribute documents and optionally enforces scope requirements on methods.
78
+
The `#[ScopedEndpoint]` attribute documents and optionally enforces scope requirements on methods.
79
79
80
80
### Basic Usage
81
81
···
84
84
85
85
namespace App\Atp;
86
86
87
-
use SocialDept\AtpClient\Attributes\RequiresScope;
87
+
use SocialDept\AtpClient\Attributes\ScopedEndpoint;
88
88
use SocialDept\AtpClient\Client\Requests\Request;
89
89
use SocialDept\AtpClient\Enums\Scope;
90
90
91
91
class CustomClient extends Request
92
92
{
93
-
#[RequiresScope(Scope::TransitionGeneric)]
93
+
#[ScopedEndpoint(Scope::TransitionGeneric)]
94
94
public function getTimeline(): array
95
95
{
96
96
return $this->atp->client->get('app.bsky.feed.getTimeline')->json();
···
103
103
Document the future granular scope that will replace the transition scope:
104
104
105
105
```php
106
-
#[RequiresScope(
106
+
#[ScopedEndpoint(
107
107
Scope::TransitionGeneric,
108
108
granular: 'rpc:app.bsky.feed.getTimeline'
109
109
)]
···
118
118
Add a human-readable description for documentation:
119
119
120
120
```php
121
-
#[RequiresScope(
121
+
#[ScopedEndpoint(
122
122
Scope::TransitionGeneric,
123
123
granular: 'rpc:app.bsky.feed.getTimeline',
124
124
description: 'Access to the user\'s home timeline'
···
134
134
When a method requires multiple scopes, all must be present:
135
135
136
136
```php
137
-
#[RequiresScope([Scope::TransitionGeneric, Scope::TransitionEmail])]
137
+
#[ScopedEndpoint([Scope::TransitionGeneric, Scope::TransitionEmail])]
138
138
public function getEmailPreferences(): array
139
139
{
140
140
// Requires BOTH scopes
···
146
146
Use multiple attributes for alternative scope requirements:
147
147
148
148
```php
149
-
#[RequiresScope(Scope::Atproto)]
150
-
#[RequiresScope(Scope::TransitionGeneric)]
149
+
#[ScopedEndpoint(Scope::Atproto)]
150
+
#[ScopedEndpoint(Scope::TransitionGeneric)]
151
151
public function getProfile(string $actor): ProfileViewDetailed
152
152
{
153
153
// Either scope satisfies the requirement
···
298
298
$client->bsky->feed->getTimeline(); // Requires transition:generic scope
299
299
```
300
300
301
-
Methods that work in public mode typically don't have `#[RequiresScope]` attributes, while authenticated-only methods do.
301
+
Methods that work in public mode typically don't have `#[ScopedEndpoint]` attributes, while authenticated-only methods do.
302
302
303
303
## Exception Handling
304
304
···
339
339
340
340
### 1. Document All Scope Requirements
341
341
342
-
Always add `#[RequiresScope]` to methods that require authentication:
342
+
Always add `#[ScopedEndpoint]` to methods that require authentication:
343
343
344
344
```php
345
-
#[RequiresScope(
345
+
#[ScopedEndpoint(
346
346
Scope::TransitionGeneric,
347
347
granular: 'rpc:app.bsky.feed.getTimeline',
348
348
description: 'Fetches the authenticated user\'s home timeline'
···
356
356
357
357
```php
358
358
// Good
359
-
#[RequiresScope(Scope::TransitionGeneric)]
359
+
#[ScopedEndpoint(Scope::TransitionGeneric)]
360
360
361
361
// Avoid
362
-
#[RequiresScope('transition:generic')]
362
+
#[ScopedEndpoint('transition:generic')]
363
363
```
364
364
365
365
### 3. Request Minimal Scopes