(
input: RegisterDynamicClientInput,
options: DiscoveryRequestOptions = {},
)
| 606 | }; |
| 607 | |
| 608 | export const registerDynamicClient = ( |
| 609 | input: RegisterDynamicClientInput, |
| 610 | options: DiscoveryRequestOptions = {}, |
| 611 | ): Effect.Effect<OAuthClientInformation, OAuthDiscoveryError> => |
| 612 | Effect.gen(function* () { |
| 613 | yield* validateEndpointUrl( |
| 614 | input.registrationEndpoint, |
| 615 | "registration_endpoint", |
| 616 | options.endpointUrlPolicy, |
| 617 | ).pipe( |
| 618 | Effect.mapError( |
| 619 | (cause) => |
| 620 | new DcrTransport({ |
| 621 | detail: "registration_endpoint must use https: or loopback http:", |
| 622 | cause, |
| 623 | }), |
| 624 | ), |
| 625 | ); |
| 626 | |
| 627 | const headers: Record<string, string> = { |
| 628 | "content-type": "application/json", |
| 629 | accept: "application/json", |
| 630 | }; |
| 631 | if (input.initialAccessToken) { |
| 632 | headers.authorization = `Bearer ${input.initialAccessToken}`; |
| 633 | } |
| 634 | |
| 635 | let request = HttpClientRequest.post(input.registrationEndpoint).pipe( |
| 636 | HttpClientRequest.bodyJsonUnsafe(buildDcrBody(input.metadata)), |
| 637 | ); |
| 638 | for (const [name, value] of Object.entries(headers)) { |
| 639 | request = HttpClientRequest.setHeader(request, name, value); |
| 640 | } |
| 641 | |
| 642 | const response = yield* executeText( |
| 643 | request, |
| 644 | options, |
| 645 | "Dynamic Client Registration request failed", |
| 646 | ).pipe( |
| 647 | Effect.mapError( |
| 648 | (cause) => |
| 649 | new DcrTransport({ |
| 650 | detail: "Dynamic Client Registration request failed", |
| 651 | cause, |
| 652 | }), |
| 653 | ), |
| 654 | ); |
| 655 | |
| 656 | // Accept both 200 and 201 as success — RFC 7591 mandates 201, but |
| 657 | // Todoist (and others) return 200 OK with the client information body. |
| 658 | if (response.status !== 200 && response.status !== 201) { |
| 659 | return yield* interpretDcrFailure(response.status, response.body); |
| 660 | } |
| 661 | |
| 662 | return yield* decodeClientInformationJson(response.body).pipe( |
| 663 | Effect.mapError( |
| 664 | (err) => |
| 665 | new OAuthDiscoveryError({ |
no test coverage detected