@mulverse/mulguard-core 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +24 -0
- package/adapters.d.ts +522 -0
- package/adapters.d.ts.map +1 -0
- package/adapters.js +170 -0
- package/errors.d.ts +429 -0
- package/errors.d.ts.map +1 -0
- package/errors.js +473 -0
- package/index.d.ts +547 -0
- package/index.d.ts.map +1 -0
- package/index.js +142 -0
- package/jwt.d.ts +132 -0
- package/jwt.d.ts.map +1 -0
- package/jwt.js +123 -0
- package/lib/actions/callback/handle-login.d.ts +35 -0
- package/lib/actions/callback/handle-login.d.ts.map +1 -0
- package/lib/actions/callback/handle-login.js +275 -0
- package/lib/actions/callback/index.d.ts +5 -0
- package/lib/actions/callback/index.d.ts.map +1 -0
- package/lib/actions/callback/index.js +409 -0
- package/lib/actions/callback/oauth/callback.d.ts +36 -0
- package/lib/actions/callback/oauth/callback.d.ts.map +1 -0
- package/lib/actions/callback/oauth/callback.js +248 -0
- package/lib/actions/callback/oauth/checks.d.ts +70 -0
- package/lib/actions/callback/oauth/checks.d.ts.map +1 -0
- package/lib/actions/callback/oauth/checks.js +188 -0
- package/lib/actions/callback/oauth/csrf-token.d.ts +33 -0
- package/lib/actions/callback/oauth/csrf-token.d.ts.map +1 -0
- package/lib/actions/callback/oauth/csrf-token.js +39 -0
- package/lib/actions/index.d.ts +6 -0
- package/lib/actions/index.d.ts.map +1 -0
- package/lib/actions/index.js +5 -0
- package/lib/actions/session.d.ts +5 -0
- package/lib/actions/session.d.ts.map +1 -0
- package/lib/actions/session.js +127 -0
- package/lib/actions/signin/authorization-url.d.ts +12 -0
- package/lib/actions/signin/authorization-url.d.ts.map +1 -0
- package/lib/actions/signin/authorization-url.js +94 -0
- package/lib/actions/signin/index.d.ts +4 -0
- package/lib/actions/signin/index.d.ts.map +1 -0
- package/lib/actions/signin/index.js +22 -0
- package/lib/actions/signin/send-token.d.ts +10 -0
- package/lib/actions/signin/send-token.d.ts.map +1 -0
- package/lib/actions/signin/send-token.js +98 -0
- package/lib/actions/signout.d.ts +11 -0
- package/lib/actions/signout.d.ts.map +1 -0
- package/lib/actions/signout.js +30 -0
- package/lib/actions/webauthn-options.d.ts +8 -0
- package/lib/actions/webauthn-options.d.ts.map +1 -0
- package/lib/actions/webauthn-options.js +60 -0
- package/lib/index.d.ts +2 -0
- package/lib/index.d.ts.map +1 -0
- package/lib/index.js +70 -0
- package/lib/init.d.ts +25 -0
- package/lib/init.d.ts.map +1 -0
- package/lib/init.js +172 -0
- package/lib/pages/error.d.ts +17 -0
- package/lib/pages/error.d.ts.map +1 -0
- package/lib/pages/error.js +40 -0
- package/lib/pages/index.d.ts +42 -0
- package/lib/pages/index.d.ts.map +1 -0
- package/lib/pages/index.js +136 -0
- package/lib/pages/signin.d.ts +10 -0
- package/lib/pages/signin.d.ts.map +1 -0
- package/lib/pages/signin.js +75 -0
- package/lib/pages/signout.d.ts +8 -0
- package/lib/pages/signout.d.ts.map +1 -0
- package/lib/pages/signout.js +17 -0
- package/lib/pages/styles.d.ts +3 -0
- package/lib/pages/styles.d.ts.map +1 -0
- package/lib/pages/styles.js +381 -0
- package/lib/pages/verify-request.d.ts +8 -0
- package/lib/pages/verify-request.d.ts.map +1 -0
- package/lib/pages/verify-request.js +11 -0
- package/lib/symbols.d.ts +50 -0
- package/lib/symbols.d.ts.map +1 -0
- package/lib/symbols.js +57 -0
- package/lib/utils/actions.d.ts +3 -0
- package/lib/utils/actions.d.ts.map +1 -0
- package/lib/utils/actions.js +14 -0
- package/lib/utils/assert.d.ts +14 -0
- package/lib/utils/assert.d.ts.map +1 -0
- package/lib/utils/assert.js +168 -0
- package/lib/utils/callback-url.d.ts +17 -0
- package/lib/utils/callback-url.d.ts.map +1 -0
- package/lib/utils/callback-url.js +27 -0
- package/lib/utils/cookie.d.ts +111 -0
- package/lib/utils/cookie.d.ts.map +1 -0
- package/lib/utils/cookie.js +205 -0
- package/lib/utils/date.d.ts +7 -0
- package/lib/utils/date.d.ts.map +1 -0
- package/lib/utils/date.js +8 -0
- package/lib/utils/email.d.ts +20 -0
- package/lib/utils/email.d.ts.map +1 -0
- package/lib/utils/email.js +57 -0
- package/lib/utils/env.d.ts +9 -0
- package/lib/utils/env.d.ts.map +1 -0
- package/lib/utils/env.js +96 -0
- package/lib/utils/logger.d.ts +18 -0
- package/lib/utils/logger.d.ts.map +1 -0
- package/lib/utils/logger.js +50 -0
- package/lib/utils/merge.d.ts +3 -0
- package/lib/utils/merge.d.ts.map +1 -0
- package/lib/utils/merge.js +23 -0
- package/lib/utils/providers.d.ts +19 -0
- package/lib/utils/providers.d.ts.map +1 -0
- package/lib/utils/providers.js +149 -0
- package/lib/utils/session.d.ts +7 -0
- package/lib/utils/session.d.ts.map +1 -0
- package/lib/utils/session.js +29 -0
- package/lib/utils/web.d.ts +10 -0
- package/lib/utils/web.d.ts.map +1 -0
- package/lib/utils/web.js +109 -0
- package/lib/utils/webauthn-client.d.ts +30 -0
- package/lib/utils/webauthn-client.d.ts.map +1 -0
- package/lib/utils/webauthn-client.js +197 -0
- package/lib/utils/webauthn-utils.d.ts +81 -0
- package/lib/utils/webauthn-utils.d.ts.map +1 -0
- package/lib/utils/webauthn-utils.js +343 -0
- package/lib/vendored/cookie.d.ts +120 -0
- package/lib/vendored/cookie.d.ts.map +1 -0
- package/lib/vendored/cookie.js +237 -0
- package/package.json +118 -0
- package/providers/42-school.d.ts +240 -0
- package/providers/42-school.d.ts.map +1 -0
- package/providers/42-school.js +78 -0
- package/providers/apple.d.ts +149 -0
- package/providers/apple.d.ts.map +1 -0
- package/providers/apple.js +104 -0
- package/providers/asgardeo.d.ts +102 -0
- package/providers/asgardeo.d.ts.map +1 -0
- package/providers/asgardeo.js +93 -0
- package/providers/atlassian.d.ts +94 -0
- package/providers/atlassian.d.ts.map +1 -0
- package/providers/atlassian.js +84 -0
- package/providers/auth0.d.ts +116 -0
- package/providers/auth0.d.ts.map +1 -0
- package/providers/auth0.js +49 -0
- package/providers/authentik.d.ts +90 -0
- package/providers/authentik.d.ts.map +1 -0
- package/providers/authentik.js +65 -0
- package/providers/azure-ad-b2c.d.ts +104 -0
- package/providers/azure-ad-b2c.d.ts.map +1 -0
- package/providers/azure-ad-b2c.js +100 -0
- package/providers/azure-ad.d.ts +19 -0
- package/providers/azure-ad.d.ts.map +1 -0
- package/providers/azure-ad.js +23 -0
- package/providers/azure-devops.d.ts +128 -0
- package/providers/azure-devops.d.ts.map +1 -0
- package/providers/azure-devops.js +158 -0
- package/providers/bankid-no.d.ts +134 -0
- package/providers/bankid-no.d.ts.map +1 -0
- package/providers/bankid-no.js +65 -0
- package/providers/battlenet.d.ts +85 -0
- package/providers/battlenet.d.ts.map +1 -0
- package/providers/battlenet.js +81 -0
- package/providers/beyondidentity.d.ts +77 -0
- package/providers/beyondidentity.d.ts.map +1 -0
- package/providers/beyondidentity.js +84 -0
- package/providers/bitbucket.d.ts +89 -0
- package/providers/bitbucket.d.ts.map +1 -0
- package/providers/bitbucket.js +92 -0
- package/providers/box.d.ts +63 -0
- package/providers/box.d.ts.map +1 -0
- package/providers/box.js +73 -0
- package/providers/boxyhq-saml.d.ts +121 -0
- package/providers/boxyhq-saml.d.ts.map +1 -0
- package/providers/boxyhq-saml.js +127 -0
- package/providers/bungie.d.ts +167 -0
- package/providers/bungie.d.ts.map +1 -0
- package/providers/bungie.js +174 -0
- package/providers/click-up.d.ts +75 -0
- package/providers/click-up.d.ts.map +1 -0
- package/providers/click-up.js +89 -0
- package/providers/cognito.d.ts +81 -0
- package/providers/cognito.d.ts.map +1 -0
- package/providers/cognito.js +73 -0
- package/providers/coinbase.d.ts +69 -0
- package/providers/coinbase.d.ts.map +1 -0
- package/providers/coinbase.js +78 -0
- package/providers/concept2.d.ts +81 -0
- package/providers/concept2.d.ts.map +1 -0
- package/providers/concept2.js +86 -0
- package/providers/credentials.d.ts +132 -0
- package/providers/credentials.d.ts.map +1 -0
- package/providers/credentials.js +74 -0
- package/providers/descope.d.ts +91 -0
- package/providers/descope.d.ts.map +1 -0
- package/providers/descope.js +78 -0
- package/providers/discord.d.ts +139 -0
- package/providers/discord.d.ts.map +1 -0
- package/providers/discord.js +86 -0
- package/providers/dribbble.d.ts +88 -0
- package/providers/dribbble.d.ts.map +1 -0
- package/providers/dribbble.js +85 -0
- package/providers/dropbox.d.ts +65 -0
- package/providers/dropbox.d.ts.map +1 -0
- package/providers/dropbox.js +88 -0
- package/providers/duende-identity-server6.d.ts +91 -0
- package/providers/duende-identity-server6.d.ts.map +1 -0
- package/providers/duende-identity-server6.js +80 -0
- package/providers/email.d.ts +41 -0
- package/providers/email.d.ts.map +1 -0
- package/providers/email.js +18 -0
- package/providers/eventbrite.d.ts +78 -0
- package/providers/eventbrite.d.ts.map +1 -0
- package/providers/eventbrite.js +88 -0
- package/providers/eveonline.d.ts +94 -0
- package/providers/eveonline.d.ts.map +1 -0
- package/providers/eveonline.js +92 -0
- package/providers/facebook.d.ts +84 -0
- package/providers/facebook.d.ts.map +1 -0
- package/providers/facebook.js +93 -0
- package/providers/faceit.d.ts +64 -0
- package/providers/faceit.d.ts.map +1 -0
- package/providers/faceit.js +74 -0
- package/providers/figma.d.ts +75 -0
- package/providers/figma.d.ts.map +1 -0
- package/providers/figma.js +81 -0
- package/providers/forwardemail.d.ts +4 -0
- package/providers/forwardemail.d.ts.map +1 -0
- package/providers/forwardemail.js +32 -0
- package/providers/foursquare.d.ts +71 -0
- package/providers/foursquare.d.ts.map +1 -0
- package/providers/foursquare.js +91 -0
- package/providers/freshbooks.d.ts +66 -0
- package/providers/freshbooks.d.ts.map +1 -0
- package/providers/freshbooks.js +76 -0
- package/providers/frontegg.d.ts +95 -0
- package/providers/frontegg.d.ts.map +1 -0
- package/providers/frontegg.js +88 -0
- package/providers/fusionauth.d.ts +279 -0
- package/providers/fusionauth.d.ts.map +1 -0
- package/providers/fusionauth.js +292 -0
- package/providers/github.d.ts +127 -0
- package/providers/github.d.ts.map +1 -0
- package/providers/github.js +115 -0
- package/providers/gitlab.d.ts +115 -0
- package/providers/gitlab.d.ts.map +1 -0
- package/providers/gitlab.js +75 -0
- package/providers/google.d.ts +138 -0
- package/providers/google.d.ts.map +1 -0
- package/providers/google.js +119 -0
- package/providers/hubspot.d.ts +76 -0
- package/providers/hubspot.d.ts.map +1 -0
- package/providers/hubspot.js +93 -0
- package/providers/huggingface.d.ts +216 -0
- package/providers/huggingface.d.ts.map +1 -0
- package/providers/huggingface.js +101 -0
- package/providers/identity-server4.d.ts +69 -0
- package/providers/identity-server4.d.ts.map +1 -0
- package/providers/identity-server4.js +64 -0
- package/providers/index.d.ts +61 -0
- package/providers/index.d.ts.map +1 -0
- package/providers/index.js +3 -0
- package/providers/instagram.d.ts +74 -0
- package/providers/instagram.d.ts.map +1 -0
- package/providers/instagram.js +87 -0
- package/providers/kakao.d.ts +148 -0
- package/providers/kakao.d.ts.map +1 -0
- package/providers/kakao.js +103 -0
- package/providers/keycloak.d.ts +100 -0
- package/providers/keycloak.d.ts.map +1 -0
- package/providers/keycloak.js +73 -0
- package/providers/kinde.d.ts +73 -0
- package/providers/kinde.d.ts.map +1 -0
- package/providers/kinde.js +51 -0
- package/providers/line.d.ts +83 -0
- package/providers/line.d.ts.map +1 -0
- package/providers/line.js +73 -0
- package/providers/linkedin.d.ts +77 -0
- package/providers/linkedin.d.ts.map +1 -0
- package/providers/linkedin.js +65 -0
- package/providers/logto.d.ts +98 -0
- package/providers/logto.d.ts.map +1 -0
- package/providers/logto.js +81 -0
- package/providers/loops.d.ts +40 -0
- package/providers/loops.d.ts.map +1 -0
- package/providers/loops.js +59 -0
- package/providers/mailchimp.d.ts +66 -0
- package/providers/mailchimp.d.ts.map +1 -0
- package/providers/mailchimp.js +76 -0
- package/providers/mailgun.d.ts +55 -0
- package/providers/mailgun.d.ts.map +1 -0
- package/providers/mailgun.js +74 -0
- package/providers/mailru.d.ts +63 -0
- package/providers/mailru.d.ts.map +1 -0
- package/providers/mailru.js +61 -0
- package/providers/mastodon.d.ts +90 -0
- package/providers/mastodon.d.ts.map +1 -0
- package/providers/mastodon.js +75 -0
- package/providers/mattermost.d.ts +132 -0
- package/providers/mattermost.d.ts.map +1 -0
- package/providers/mattermost.js +83 -0
- package/providers/medium.d.ts +68 -0
- package/providers/medium.d.ts.map +1 -0
- package/providers/medium.js +84 -0
- package/providers/microsoft-entra-id.d.ts +428 -0
- package/providers/microsoft-entra-id.d.ts.map +1 -0
- package/providers/microsoft-entra-id.js +156 -0
- package/providers/naver.d.ts +80 -0
- package/providers/naver.d.ts.map +1 -0
- package/providers/naver.js +79 -0
- package/providers/netlify.d.ts +66 -0
- package/providers/netlify.d.ts.map +1 -0
- package/providers/netlify.js +85 -0
- package/providers/netsuite.d.ts +189 -0
- package/providers/netsuite.d.ts.map +1 -0
- package/providers/netsuite.js +170 -0
- package/providers/nextcloud.d.ts +150 -0
- package/providers/nextcloud.d.ts.map +1 -0
- package/providers/nextcloud.js +99 -0
- package/providers/nodemailer.d.ts +27 -0
- package/providers/nodemailer.d.ts.map +1 -0
- package/providers/nodemailer.js +34 -0
- package/providers/notion.d.ts +99 -0
- package/providers/notion.d.ts.map +1 -0
- package/providers/notion.js +110 -0
- package/providers/oauth.d.ts +188 -0
- package/providers/oauth.d.ts.map +1 -0
- package/providers/oauth.js +1 -0
- package/providers/okta.d.ts +99 -0
- package/providers/okta.d.ts.map +1 -0
- package/providers/okta.js +63 -0
- package/providers/onelogin.d.ts +65 -0
- package/providers/onelogin.d.ts.map +1 -0
- package/providers/onelogin.js +61 -0
- package/providers/ory-hydra.d.ts +79 -0
- package/providers/ory-hydra.d.ts.map +1 -0
- package/providers/ory-hydra.js +67 -0
- package/providers/osso.d.ts +79 -0
- package/providers/osso.d.ts.map +1 -0
- package/providers/osso.js +77 -0
- package/providers/osu.d.ts +116 -0
- package/providers/osu.d.ts.map +1 -0
- package/providers/osu.js +75 -0
- package/providers/passage.d.ts +88 -0
- package/providers/passage.d.ts.map +1 -0
- package/providers/passage.js +75 -0
- package/providers/passkey.d.ts +65 -0
- package/providers/passkey.d.ts.map +1 -0
- package/providers/passkey.js +87 -0
- package/providers/patreon.d.ts +73 -0
- package/providers/patreon.d.ts.map +1 -0
- package/providers/patreon.js +77 -0
- package/providers/ping-id.d.ts +57 -0
- package/providers/ping-id.d.ts.map +1 -0
- package/providers/ping-id.js +40 -0
- package/providers/pinterest.d.ts +79 -0
- package/providers/pinterest.d.ts.map +1 -0
- package/providers/pinterest.js +85 -0
- package/providers/pipedrive.d.ts +99 -0
- package/providers/pipedrive.d.ts.map +1 -0
- package/providers/pipedrive.js +71 -0
- package/providers/postmark.d.ts +4 -0
- package/providers/postmark.d.ts.map +1 -0
- package/providers/postmark.js +36 -0
- package/providers/provider-types.d.ts +3 -0
- package/providers/provider-types.d.ts.map +1 -0
- package/providers/provider-types.js +1 -0
- package/providers/reddit.d.ts +88 -0
- package/providers/reddit.d.ts.map +1 -0
- package/providers/reddit.js +90 -0
- package/providers/resend.d.ts +4 -0
- package/providers/resend.d.ts.map +1 -0
- package/providers/resend.js +32 -0
- package/providers/roblox.d.ts +67 -0
- package/providers/roblox.d.ts.map +1 -0
- package/providers/roblox.js +53 -0
- package/providers/salesforce.d.ts +59 -0
- package/providers/salesforce.d.ts.map +1 -0
- package/providers/salesforce.js +52 -0
- package/providers/sendgrid.d.ts +4 -0
- package/providers/sendgrid.d.ts.map +1 -0
- package/providers/sendgrid.js +35 -0
- package/providers/simplelogin.d.ts +87 -0
- package/providers/simplelogin.d.ts.map +1 -0
- package/providers/simplelogin.js +83 -0
- package/providers/slack.d.ts +102 -0
- package/providers/slack.d.ts.map +1 -0
- package/providers/slack.js +69 -0
- package/providers/spotify.d.ts +75 -0
- package/providers/spotify.d.ts.map +1 -0
- package/providers/spotify.js +73 -0
- package/providers/strava.d.ts +68 -0
- package/providers/strava.d.ts.map +1 -0
- package/providers/strava.js +80 -0
- package/providers/threads.d.ts +108 -0
- package/providers/threads.d.ts.map +1 -0
- package/providers/threads.js +89 -0
- package/providers/tiktok.d.ts +248 -0
- package/providers/tiktok.d.ts.map +1 -0
- package/providers/tiktok.js +195 -0
- package/providers/todoist.d.ts +76 -0
- package/providers/todoist.d.ts.map +1 -0
- package/providers/todoist.js +97 -0
- package/providers/trakt.d.ts +93 -0
- package/providers/trakt.d.ts.map +1 -0
- package/providers/trakt.js +91 -0
- package/providers/twitch.d.ts +71 -0
- package/providers/twitch.d.ts.map +1 -0
- package/providers/twitch.js +96 -0
- package/providers/twitter.d.ts +183 -0
- package/providers/twitter.d.ts.map +1 -0
- package/providers/twitter.js +100 -0
- package/providers/united-effects.d.ts +80 -0
- package/providers/united-effects.d.ts.map +1 -0
- package/providers/united-effects.js +72 -0
- package/providers/vipps.d.ts +71 -0
- package/providers/vipps.d.ts.map +1 -0
- package/providers/vipps.js +33 -0
- package/providers/vk.d.ts +334 -0
- package/providers/vk.d.ts.map +1 -0
- package/providers/vk.js +103 -0
- package/providers/webauthn.d.ts +148 -0
- package/providers/webauthn.d.ts.map +1 -0
- package/providers/webauthn.js +128 -0
- package/providers/webex.d.ts +78 -0
- package/providers/webex.d.ts.map +1 -0
- package/providers/webex.js +73 -0
- package/providers/wechat.d.ts +78 -0
- package/providers/wechat.d.ts.map +1 -0
- package/providers/wechat.js +105 -0
- package/providers/wikimedia.d.ts +99 -0
- package/providers/wikimedia.d.ts.map +1 -0
- package/providers/wikimedia.js +90 -0
- package/providers/wordpress.d.ts +65 -0
- package/providers/wordpress.d.ts.map +1 -0
- package/providers/wordpress.js +71 -0
- package/providers/workos.d.ts +154 -0
- package/providers/workos.d.ts.map +1 -0
- package/providers/workos.js +143 -0
- package/providers/yandex.d.ts +131 -0
- package/providers/yandex.d.ts.map +1 -0
- package/providers/yandex.js +80 -0
- package/providers/zitadel.d.ts +117 -0
- package/providers/zitadel.d.ts.map +1 -0
- package/providers/zitadel.js +95 -0
- package/providers/zoho.d.ts +63 -0
- package/providers/zoho.d.ts.map +1 -0
- package/providers/zoho.js +79 -0
- package/providers/zoom.d.ts +93 -0
- package/providers/zoom.d.ts.map +1 -0
- package/providers/zoom.js +82 -0
- package/src/adapters/server-actions-helpers.ts +126 -0
- package/src/adapters.ts +603 -0
- package/src/errors.ts +551 -0
- package/src/index.ts +689 -0
- package/src/jwt.ts +283 -0
- package/src/lib/actions/callback/handle-login.ts +334 -0
- package/src/lib/actions/callback/index.ts +554 -0
- package/src/lib/actions/callback/oauth/callback.ts +347 -0
- package/src/lib/actions/callback/oauth/checks.ts +258 -0
- package/src/lib/actions/callback/oauth/csrf-token.ts +60 -0
- package/src/lib/actions/index.ts +5 -0
- package/src/lib/actions/session.ts +167 -0
- package/src/lib/actions/signin/authorization-url.ts +123 -0
- package/src/lib/actions/signin/index.ts +37 -0
- package/src/lib/actions/signin/send-token.ts +124 -0
- package/src/lib/actions/signout.ts +38 -0
- package/src/lib/actions/webauthn-options.ts +100 -0
- package/src/lib/index.ts +97 -0
- package/src/lib/init.ts +236 -0
- package/src/lib/pages/error.tsx +106 -0
- package/src/lib/pages/index.ts +181 -0
- package/src/lib/pages/signin.tsx +255 -0
- package/src/lib/pages/signout.tsx +49 -0
- package/src/lib/pages/styles.css +377 -0
- package/src/lib/pages/styles.ts +381 -0
- package/src/lib/pages/verify-request.tsx +36 -0
- package/src/lib/symbols.ts +60 -0
- package/src/lib/utils/actions.ts +17 -0
- package/src/lib/utils/assert.ts +259 -0
- package/src/lib/utils/callback-url.ts +42 -0
- package/src/lib/utils/cookie.ts +248 -0
- package/src/lib/utils/date.ts +8 -0
- package/src/lib/utils/email.ts +65 -0
- package/src/lib/utils/env.ts +113 -0
- package/src/lib/utils/logger.ts +75 -0
- package/src/lib/utils/merge.ts +30 -0
- package/src/lib/utils/providers.ts +203 -0
- package/src/lib/utils/session.ts +41 -0
- package/src/lib/utils/web.ts +151 -0
- package/src/lib/utils/webauthn-client.js +229 -0
- package/src/lib/utils/webauthn-utils.ts +531 -0
- package/src/lib/vendored/cookie.ts +383 -0
- package/src/providers/42-school.ts +256 -0
- package/src/providers/apple.ts +206 -0
- package/src/providers/asgardeo.ts +118 -0
- package/src/providers/atlassian.ts +120 -0
- package/src/providers/auth0.ts +127 -0
- package/src/providers/authentik.ts +100 -0
- package/src/providers/azure-ad-b2c.ts +124 -0
- package/src/providers/azure-ad.ts +30 -0
- package/src/providers/azure-devops.ts +184 -0
- package/src/providers/bankid-no.ts +161 -0
- package/src/providers/battlenet.ts +107 -0
- package/src/providers/beyondidentity.ts +102 -0
- package/src/providers/bitbucket.ts +122 -0
- package/src/providers/box.ts +87 -0
- package/src/providers/boxyhq-saml.ts +148 -0
- package/src/providers/bungie.ts +192 -0
- package/src/providers/click-up.ts +104 -0
- package/src/providers/cognito.ts +94 -0
- package/src/providers/coinbase.ts +93 -0
- package/src/providers/concept2.ts +108 -0
- package/src/providers/credentials.ts +157 -0
- package/src/providers/descope.ts +105 -0
- package/src/providers/discord.ts +176 -0
- package/src/providers/dribbble.ts +122 -0
- package/src/providers/dropbox.ts +102 -0
- package/src/providers/duende-identity-server6.ts +101 -0
- package/src/providers/email.ts +60 -0
- package/src/providers/eventbrite.ts +105 -0
- package/src/providers/eveonline.ts +117 -0
- package/src/providers/facebook.ts +119 -0
- package/src/providers/faceit.ts +90 -0
- package/src/providers/figma.ts +105 -0
- package/src/providers/forwardemail.ts +37 -0
- package/src/providers/foursquare.ts +105 -0
- package/src/providers/freshbooks.ts +90 -0
- package/src/providers/frontegg.ts +111 -0
- package/src/providers/fusionauth.ts +336 -0
- package/src/providers/github.ts +187 -0
- package/src/providers/gitlab.ts +140 -0
- package/src/providers/google.ts +152 -0
- package/src/providers/hubspot.ts +117 -0
- package/src/providers/huggingface.ts +234 -0
- package/src/providers/identity-server4.ts +78 -0
- package/src/providers/index.ts +115 -0
- package/src/providers/instagram.ts +103 -0
- package/src/providers/kakao.ts +184 -0
- package/src/providers/keycloak.ts +111 -0
- package/src/providers/kinde.ts +85 -0
- package/src/providers/line.ts +99 -0
- package/src/providers/linkedin.ts +91 -0
- package/src/providers/logto.ts +122 -0
- package/src/providers/loops.ts +79 -0
- package/src/providers/mailchimp.ts +90 -0
- package/src/providers/mailgun.ts +98 -0
- package/src/providers/mailru.ts +75 -0
- package/src/providers/mastodon.ts +112 -0
- package/src/providers/mattermost.ts +154 -0
- package/src/providers/medium.ts +89 -0
- package/src/providers/microsoft-entra-id.ts +497 -0
- package/src/providers/naver.ts +102 -0
- package/src/providers/netlify.ts +90 -0
- package/src/providers/netsuite.ts +225 -0
- package/src/providers/nextcloud.ts +207 -0
- package/src/providers/nodemailer.ts +84 -0
- package/src/providers/notion.ts +166 -0
- package/src/providers/oauth.ts +310 -0
- package/src/providers/okta.ts +111 -0
- package/src/providers/onelogin.ts +75 -0
- package/src/providers/ory-hydra.ts +93 -0
- package/src/providers/osso.ts +91 -0
- package/src/providers/osu.ts +138 -0
- package/src/providers/passage.ts +103 -0
- package/src/providers/passkey.ts +94 -0
- package/src/providers/patreon.ts +98 -0
- package/src/providers/ping-id.ts +68 -0
- package/src/providers/pinterest.ts +106 -0
- package/src/providers/pipedrive.ts +120 -0
- package/src/providers/postmark.ts +38 -0
- package/src/providers/provider-types.ts +107 -0
- package/src/providers/reddit.ts +104 -0
- package/src/providers/resend.ts +35 -0
- package/src/providers/roblox.ts +94 -0
- package/src/providers/salesforce.ts +73 -0
- package/src/providers/sendgrid.ts +36 -0
- package/src/providers/simplelogin.ts +107 -0
- package/src/providers/slack.ts +115 -0
- package/src/providers/spotify.ts +99 -0
- package/src/providers/strava.ts +101 -0
- package/src/providers/threads.ts +135 -0
- package/src/providers/tiktok.ts +319 -0
- package/src/providers/todoist.ts +122 -0
- package/src/providers/trakt.ts +120 -0
- package/src/providers/twitch.ts +121 -0
- package/src/providers/twitter.ts +207 -0
- package/src/providers/united-effects.ts +89 -0
- package/src/providers/vipps.ts +86 -0
- package/src/providers/vk.ts +401 -0
- package/src/providers/webauthn.ts +296 -0
- package/src/providers/webex.ts +102 -0
- package/src/providers/wechat.ts +141 -0
- package/src/providers/wikimedia.ts +258 -0
- package/src/providers/wordpress.ts +86 -0
- package/src/providers/workos.ts +180 -0
- package/src/providers/yandex.ts +159 -0
- package/src/providers/zitadel.ts +128 -0
- package/src/providers/zoho.ts +84 -0
- package/src/providers/zoom.ts +119 -0
- package/src/types.ts +430 -0
- package/src/warnings.ts +21 -0
- package/types.d.ts +309 -0
- package/types.d.ts.map +1 -0
- package/types.js +53 -0
- package/warnings.d.ts +17 -0
- package/warnings.d.ts.map +1 -0
- package/warnings.js +1 -0
|
@@ -0,0 +1,168 @@
|
|
|
1
|
+
import { defaultCookies } from "./cookie.js";
|
|
2
|
+
import { AuthError, DuplicateConditionalUI, ExperimentalFeatureNotEnabled, InvalidCallbackUrl, InvalidEndpoints, MissingAdapter, MissingAdapterMethods, MissingAuthorize, MissingSecret, MissingWebAuthnAutocomplete, UnsupportedStrategy, UntrustedHost, } from "../../errors.js";
|
|
3
|
+
import { createServerActionsAdapter } from "../../adapters/server-actions-helpers.js";
|
|
4
|
+
let warned = false;
|
|
5
|
+
function isValidHttpUrl(url, baseUrl) {
|
|
6
|
+
try {
|
|
7
|
+
return /^https?:/.test(new URL(url, url.startsWith("/") ? baseUrl : undefined).protocol);
|
|
8
|
+
}
|
|
9
|
+
catch {
|
|
10
|
+
return false;
|
|
11
|
+
}
|
|
12
|
+
}
|
|
13
|
+
function isSemverString(version) {
|
|
14
|
+
return /^v\d+(?:\.\d+){0,2}$/.test(version);
|
|
15
|
+
}
|
|
16
|
+
let hasCredentials = false;
|
|
17
|
+
let hasEmail = false;
|
|
18
|
+
let hasWebAuthn = false;
|
|
19
|
+
const emailMethods = [
|
|
20
|
+
"createVerificationToken",
|
|
21
|
+
"useVerificationToken",
|
|
22
|
+
"getUserByEmail",
|
|
23
|
+
];
|
|
24
|
+
const sessionMethods = [
|
|
25
|
+
"createUser",
|
|
26
|
+
"getUser",
|
|
27
|
+
"getUserByEmail",
|
|
28
|
+
"getUserByAccount",
|
|
29
|
+
"updateUser",
|
|
30
|
+
"linkAccount",
|
|
31
|
+
"createSession",
|
|
32
|
+
"getSessionAndUser",
|
|
33
|
+
"updateSession",
|
|
34
|
+
"deleteSession",
|
|
35
|
+
];
|
|
36
|
+
const webauthnMethods = [
|
|
37
|
+
"createUser",
|
|
38
|
+
"getUser",
|
|
39
|
+
"linkAccount",
|
|
40
|
+
"getAccount",
|
|
41
|
+
"getAuthenticator",
|
|
42
|
+
"createAuthenticator",
|
|
43
|
+
"listAuthenticatorsByUserId",
|
|
44
|
+
"updateAuthenticatorCounter",
|
|
45
|
+
];
|
|
46
|
+
/**
|
|
47
|
+
* Verify that the user configured Auth.js correctly.
|
|
48
|
+
* Good place to mention deprecations as well.
|
|
49
|
+
*
|
|
50
|
+
* This is invoked before the init method, so default values are not available yet.
|
|
51
|
+
*/
|
|
52
|
+
export function assertConfig(request, options) {
|
|
53
|
+
const { url } = request;
|
|
54
|
+
const warnings = [];
|
|
55
|
+
if (!warned && options.debug)
|
|
56
|
+
warnings.push("debug-enabled");
|
|
57
|
+
if (!options.trustHost) {
|
|
58
|
+
return new UntrustedHost(`Host must be trusted. URL was: ${request.url}`);
|
|
59
|
+
}
|
|
60
|
+
if (!options.secret?.length) {
|
|
61
|
+
return new MissingSecret("Please define a `secret`");
|
|
62
|
+
}
|
|
63
|
+
const callbackUrlParam = request.query?.callbackUrl;
|
|
64
|
+
if (callbackUrlParam && !isValidHttpUrl(callbackUrlParam, url.origin)) {
|
|
65
|
+
return new InvalidCallbackUrl(`Invalid callback URL. Received: ${callbackUrlParam}`);
|
|
66
|
+
}
|
|
67
|
+
const { callbackUrl: defaultCallbackUrl } = defaultCookies(options.useSecureCookies ?? url.protocol === "https:");
|
|
68
|
+
const callbackUrlCookie = request.cookies?.[options.cookies?.callbackUrl?.name ?? defaultCallbackUrl.name];
|
|
69
|
+
if (callbackUrlCookie && !isValidHttpUrl(callbackUrlCookie, url.origin)) {
|
|
70
|
+
return new InvalidCallbackUrl(`Invalid callback URL. Received: ${callbackUrlCookie}`);
|
|
71
|
+
}
|
|
72
|
+
// Keep track of webauthn providers that use conditional UI
|
|
73
|
+
let hasConditionalUIProvider = false;
|
|
74
|
+
for (const p of options.providers) {
|
|
75
|
+
const provider = typeof p === "function" ? p() : p;
|
|
76
|
+
if ((provider.type === "oauth" || provider.type === "oidc") &&
|
|
77
|
+
!(provider.issuer ?? provider.options?.issuer)) {
|
|
78
|
+
const { authorization: a, token: t, userinfo: u } = provider;
|
|
79
|
+
let key;
|
|
80
|
+
if (typeof a !== "string" && !a?.url)
|
|
81
|
+
key = "authorization";
|
|
82
|
+
else if (typeof t !== "string" && !t?.url)
|
|
83
|
+
key = "token";
|
|
84
|
+
else if (typeof u !== "string" && !u?.url)
|
|
85
|
+
key = "userinfo";
|
|
86
|
+
if (key) {
|
|
87
|
+
return new InvalidEndpoints(`Provider "${provider.id}" is missing both \`issuer\` and \`${key}\` endpoint config. At least one of them is required`);
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
if (provider.type === "credentials")
|
|
91
|
+
hasCredentials = true;
|
|
92
|
+
else if (provider.type === "email")
|
|
93
|
+
hasEmail = true;
|
|
94
|
+
else if (provider.type === "webauthn") {
|
|
95
|
+
hasWebAuthn = true;
|
|
96
|
+
// Validate simpleWebAuthnBrowserVersion
|
|
97
|
+
if (provider.simpleWebAuthnBrowserVersion &&
|
|
98
|
+
!isSemverString(provider.simpleWebAuthnBrowserVersion)) {
|
|
99
|
+
return new AuthError(`Invalid provider config for "${provider.id}": simpleWebAuthnBrowserVersion "${provider.simpleWebAuthnBrowserVersion}" must be a valid semver string.`);
|
|
100
|
+
}
|
|
101
|
+
if (provider.enableConditionalUI) {
|
|
102
|
+
// Make sure only one webauthn provider has "enableConditionalUI" set to true
|
|
103
|
+
if (hasConditionalUIProvider) {
|
|
104
|
+
return new DuplicateConditionalUI(`Multiple webauthn providers have 'enableConditionalUI' set to True. Only one provider can have this option enabled at a time`);
|
|
105
|
+
}
|
|
106
|
+
hasConditionalUIProvider = true;
|
|
107
|
+
// Make sure at least one formField has "webauthn" in its autocomplete param
|
|
108
|
+
const hasWebauthnFormField = Object.values(provider.formFields).some((f) => f.autocomplete && f.autocomplete.toString().indexOf("webauthn") > -1);
|
|
109
|
+
if (!hasWebauthnFormField) {
|
|
110
|
+
return new MissingWebAuthnAutocomplete(`Provider "${provider.id}" has 'enableConditionalUI' set to True, but none of its formFields have 'webauthn' in their autocomplete param`);
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
if (hasCredentials) {
|
|
116
|
+
const dbStrategy = options.session?.strategy === "database";
|
|
117
|
+
const onlyCredentials = !options.providers.some((p) => (typeof p === "function" ? p() : p).type !== "credentials");
|
|
118
|
+
if (dbStrategy && onlyCredentials) {
|
|
119
|
+
return new UnsupportedStrategy("Signing in with credentials only supported if JWT strategy is enabled");
|
|
120
|
+
}
|
|
121
|
+
const credentialsNoAuthorize = options.providers.some((p) => {
|
|
122
|
+
const provider = typeof p === "function" ? p() : p;
|
|
123
|
+
return provider.type === "credentials" && !provider.authorize;
|
|
124
|
+
});
|
|
125
|
+
if (credentialsNoAuthorize) {
|
|
126
|
+
return new MissingAuthorize("Must define an authorize() handler to use credentials authentication provider");
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
const { adapter, serverActions, session } = options;
|
|
130
|
+
// Convert serverActions to adapter if provided and no adapter exists
|
|
131
|
+
const effectiveAdapter = adapter || (serverActions ? createServerActionsAdapter(serverActions) : undefined);
|
|
132
|
+
const requiredMethods = [];
|
|
133
|
+
if (hasEmail ||
|
|
134
|
+
session?.strategy === "database" ||
|
|
135
|
+
(!session?.strategy && effectiveAdapter)) {
|
|
136
|
+
if (hasEmail) {
|
|
137
|
+
if (!effectiveAdapter)
|
|
138
|
+
return new MissingAdapter("Email login requires an adapter or serverActions");
|
|
139
|
+
requiredMethods.push(...emailMethods);
|
|
140
|
+
}
|
|
141
|
+
else {
|
|
142
|
+
if (!effectiveAdapter)
|
|
143
|
+
return new MissingAdapter("Database session requires an adapter or serverActions");
|
|
144
|
+
requiredMethods.push(...sessionMethods);
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
if (hasWebAuthn) {
|
|
148
|
+
// Log experimental warning
|
|
149
|
+
if (options.experimental?.enableWebAuthn) {
|
|
150
|
+
warnings.push("experimental-webauthn");
|
|
151
|
+
}
|
|
152
|
+
else {
|
|
153
|
+
return new ExperimentalFeatureNotEnabled("WebAuthn is an experimental feature. To enable it, set `experimental.enableWebAuthn` to `true` in your config");
|
|
154
|
+
}
|
|
155
|
+
if (!effectiveAdapter)
|
|
156
|
+
return new MissingAdapter("WebAuthn requires an adapter or serverActions");
|
|
157
|
+
requiredMethods.push(...webauthnMethods);
|
|
158
|
+
}
|
|
159
|
+
if (effectiveAdapter) {
|
|
160
|
+
const missing = requiredMethods.filter((m) => !(m in effectiveAdapter));
|
|
161
|
+
if (missing.length) {
|
|
162
|
+
return new MissingAdapterMethods(`Required adapter methods were missing: ${missing.join(", ")}`);
|
|
163
|
+
}
|
|
164
|
+
}
|
|
165
|
+
if (!warned)
|
|
166
|
+
warned = true;
|
|
167
|
+
return warnings;
|
|
168
|
+
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import type { InternalOptions } from "../../types.js";
|
|
2
|
+
interface CreateCallbackUrlParams {
|
|
3
|
+
options: InternalOptions;
|
|
4
|
+
/** Try reading value from request body (POST) then from query param (GET) */
|
|
5
|
+
paramValue?: string;
|
|
6
|
+
cookieValue?: string;
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Get callback URL based on query param / cookie + validation,
|
|
10
|
+
* and add it to `req.options.callbackUrl`.
|
|
11
|
+
*/
|
|
12
|
+
export declare function createCallbackUrl({ options, paramValue, cookieValue, }: CreateCallbackUrlParams): Promise<{
|
|
13
|
+
callbackUrl: string;
|
|
14
|
+
callbackUrlCookie: string | undefined;
|
|
15
|
+
}>;
|
|
16
|
+
export {};
|
|
17
|
+
//# sourceMappingURL=callback-url.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"callback-url.d.ts","sourceRoot":"","sources":["../../src/lib/utils/callback-url.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,gBAAgB,CAAA;AAErD,UAAU,uBAAuB;IAC/B,OAAO,EAAE,eAAe,CAAA;IACxB,6EAA6E;IAC7E,UAAU,CAAC,EAAE,MAAM,CAAA;IACnB,WAAW,CAAC,EAAE,MAAM,CAAA;CACrB;AAED;;;GAGG;AACH,wBAAsB,iBAAiB,CAAC,EACtC,OAAO,EACP,UAAU,EACV,WAAW,GACZ,EAAE,uBAAuB;;;GAwBzB"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Get callback URL based on query param / cookie + validation,
|
|
3
|
+
* and add it to `req.options.callbackUrl`.
|
|
4
|
+
*/
|
|
5
|
+
export async function createCallbackUrl({ options, paramValue, cookieValue, }) {
|
|
6
|
+
const { url, callbacks } = options;
|
|
7
|
+
let callbackUrl = url.origin;
|
|
8
|
+
if (paramValue) {
|
|
9
|
+
// If callbackUrl form field or query parameter is passed try to use it if allowed
|
|
10
|
+
callbackUrl = await callbacks.redirect({
|
|
11
|
+
url: paramValue,
|
|
12
|
+
baseUrl: url.origin,
|
|
13
|
+
});
|
|
14
|
+
}
|
|
15
|
+
else if (cookieValue) {
|
|
16
|
+
// If no callbackUrl specified, try using the value from the cookie if allowed
|
|
17
|
+
callbackUrl = await callbacks.redirect({
|
|
18
|
+
url: cookieValue,
|
|
19
|
+
baseUrl: url.origin,
|
|
20
|
+
});
|
|
21
|
+
}
|
|
22
|
+
return {
|
|
23
|
+
callbackUrl,
|
|
24
|
+
// Save callback URL in a cookie so that it can be used for subsequent requests in signin/signout/callback flow
|
|
25
|
+
callbackUrlCookie: callbackUrl !== cookieValue ? callbackUrl : undefined,
|
|
26
|
+
};
|
|
27
|
+
}
|
|
@@ -0,0 +1,111 @@
|
|
|
1
|
+
import type { CookieOption, LoggerInstance, RequestInternal } from "../../types.js";
|
|
2
|
+
/** Stringified form of `JWT`. Extract the content with `jwt.decode` */
|
|
3
|
+
export type JWTString = string;
|
|
4
|
+
export type SetCookieOptions = Partial<CookieOption["options"]> & {
|
|
5
|
+
expires?: Date | string;
|
|
6
|
+
encode?: (val: unknown) => string;
|
|
7
|
+
};
|
|
8
|
+
/**
|
|
9
|
+
* If `options.session.strategy` is set to `jwt`, this is a stringified `JWT`.
|
|
10
|
+
* In case of `strategy: "database"`, this is the `sessionToken` of the session in the database.
|
|
11
|
+
*/
|
|
12
|
+
export type SessionToken<T extends "jwt" | "database" = "jwt"> = T extends "jwt" ? JWTString : string;
|
|
13
|
+
/**
|
|
14
|
+
* Use secure cookies if the site uses HTTPS
|
|
15
|
+
* This being conditional allows cookies to work non-HTTPS development URLs
|
|
16
|
+
* Honour secure cookie option, which sets 'secure' and also adds '__Secure-'
|
|
17
|
+
* prefix, but enable them by default if the site URL is HTTPS; but not for
|
|
18
|
+
* non-HTTPS URLs like http://localhost which are used in development).
|
|
19
|
+
* For more on prefixes see https://googlechrome.github.io/samples/cookie-prefixes/
|
|
20
|
+
*
|
|
21
|
+
* @TODO Review cookie settings (names, options)
|
|
22
|
+
*/
|
|
23
|
+
export declare function defaultCookies(useSecureCookies: boolean): {
|
|
24
|
+
readonly sessionToken: {
|
|
25
|
+
readonly name: "__Secure-authjs.session-token" | "authjs.session-token";
|
|
26
|
+
readonly options: {
|
|
27
|
+
readonly httpOnly: true;
|
|
28
|
+
readonly sameSite: "lax";
|
|
29
|
+
readonly path: "/";
|
|
30
|
+
readonly secure: boolean;
|
|
31
|
+
};
|
|
32
|
+
};
|
|
33
|
+
readonly callbackUrl: {
|
|
34
|
+
readonly name: "__Secure-authjs.callback-url" | "authjs.callback-url";
|
|
35
|
+
readonly options: {
|
|
36
|
+
readonly httpOnly: true;
|
|
37
|
+
readonly sameSite: "lax";
|
|
38
|
+
readonly path: "/";
|
|
39
|
+
readonly secure: boolean;
|
|
40
|
+
};
|
|
41
|
+
};
|
|
42
|
+
readonly csrfToken: {
|
|
43
|
+
readonly name: "authjs.csrf-token" | "__Host-authjs.csrf-token";
|
|
44
|
+
readonly options: {
|
|
45
|
+
readonly httpOnly: true;
|
|
46
|
+
readonly sameSite: "lax";
|
|
47
|
+
readonly path: "/";
|
|
48
|
+
readonly secure: boolean;
|
|
49
|
+
};
|
|
50
|
+
};
|
|
51
|
+
readonly pkceCodeVerifier: {
|
|
52
|
+
readonly name: "__Secure-authjs.pkce.code_verifier" | "authjs.pkce.code_verifier";
|
|
53
|
+
readonly options: {
|
|
54
|
+
readonly httpOnly: true;
|
|
55
|
+
readonly sameSite: "lax";
|
|
56
|
+
readonly path: "/";
|
|
57
|
+
readonly secure: boolean;
|
|
58
|
+
readonly maxAge: number;
|
|
59
|
+
};
|
|
60
|
+
};
|
|
61
|
+
readonly state: {
|
|
62
|
+
readonly name: "__Secure-authjs.state" | "authjs.state";
|
|
63
|
+
readonly options: {
|
|
64
|
+
readonly httpOnly: true;
|
|
65
|
+
readonly sameSite: "lax";
|
|
66
|
+
readonly path: "/";
|
|
67
|
+
readonly secure: boolean;
|
|
68
|
+
readonly maxAge: number;
|
|
69
|
+
};
|
|
70
|
+
};
|
|
71
|
+
readonly nonce: {
|
|
72
|
+
readonly name: "__Secure-authjs.nonce" | "authjs.nonce";
|
|
73
|
+
readonly options: {
|
|
74
|
+
readonly httpOnly: true;
|
|
75
|
+
readonly sameSite: "lax";
|
|
76
|
+
readonly path: "/";
|
|
77
|
+
readonly secure: boolean;
|
|
78
|
+
};
|
|
79
|
+
};
|
|
80
|
+
readonly webauthnChallenge: {
|
|
81
|
+
readonly name: "__Secure-authjs.challenge" | "authjs.challenge";
|
|
82
|
+
readonly options: {
|
|
83
|
+
readonly httpOnly: true;
|
|
84
|
+
readonly sameSite: "lax";
|
|
85
|
+
readonly path: "/";
|
|
86
|
+
readonly secure: boolean;
|
|
87
|
+
readonly maxAge: number;
|
|
88
|
+
};
|
|
89
|
+
};
|
|
90
|
+
};
|
|
91
|
+
export interface Cookie extends CookieOption {
|
|
92
|
+
value: string;
|
|
93
|
+
}
|
|
94
|
+
export declare class SessionStore {
|
|
95
|
+
#private;
|
|
96
|
+
constructor(option: CookieOption, cookies: RequestInternal["cookies"], logger: LoggerInstance | Console);
|
|
97
|
+
/**
|
|
98
|
+
* The JWT Session or database Session ID
|
|
99
|
+
* constructed from the cookie chunks.
|
|
100
|
+
*/
|
|
101
|
+
get value(): string;
|
|
102
|
+
/**
|
|
103
|
+
* Given a cookie value, return new cookies, chunked, to fit the allowed cookie size.
|
|
104
|
+
* If the cookie has changed from chunked to unchunked or vice versa,
|
|
105
|
+
* it deletes the old cookies as well.
|
|
106
|
+
*/
|
|
107
|
+
chunk(value: string, options: Partial<Cookie["options"]>): Cookie[];
|
|
108
|
+
/** Returns a list of cookies that should be cleaned. */
|
|
109
|
+
clean(): Cookie[];
|
|
110
|
+
}
|
|
111
|
+
//# sourceMappingURL=cookie.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cookie.d.ts","sourceRoot":"","sources":["../../src/lib/utils/cookie.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACV,YAAY,EAEZ,cAAc,EACd,eAAe,EAChB,MAAM,gBAAgB,CAAA;AA2BvB,uEAAuE;AACvE,MAAM,MAAM,SAAS,GAAG,MAAM,CAAA;AAE9B,MAAM,MAAM,gBAAgB,GAAG,OAAO,CAAC,YAAY,CAAC,SAAS,CAAC,CAAC,GAAG;IAChE,OAAO,CAAC,EAAE,IAAI,GAAG,MAAM,CAAA;IACvB,MAAM,CAAC,EAAE,CAAC,GAAG,EAAE,OAAO,KAAK,MAAM,CAAA;CAClC,CAAA;AAED;;;GAGG;AACH,MAAM,MAAM,YAAY,CAAC,CAAC,SAAS,KAAK,GAAG,UAAU,GAAG,KAAK,IAAI,CAAC,SAAS,KAAK,GAC5E,SAAS,GACT,MAAM,CAAA;AAEV;;;;;;;;;GASG;AACH,wBAAgB,cAAc,CAAC,gBAAgB,EAAE,OAAO;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAyEvD;AAED,MAAM,WAAW,MAAO,SAAQ,YAAY;IAC1C,KAAK,EAAE,MAAM,CAAA;CACd;AAID,qBAAa,YAAY;;gBAMrB,MAAM,EAAE,YAAY,EACpB,OAAO,EAAE,eAAe,CAAC,SAAS,CAAC,EACnC,MAAM,EAAE,cAAc,GAAG,OAAO;IAclC;;;OAGG;IACH,IAAI,KAAK,WAWR;IA2CD;;;;OAIG;IACH,KAAK,CAAC,KAAK,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC,GAAG,MAAM,EAAE;IAmBnE,wDAAwD;IACxD,KAAK,IAAI,MAAM,EAAE;CAGlB"}
|
|
@@ -0,0 +1,205 @@
|
|
|
1
|
+
var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {
|
|
2
|
+
if (kind === "m") throw new TypeError("Private method is not writable");
|
|
3
|
+
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a setter");
|
|
4
|
+
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it");
|
|
5
|
+
return (kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;
|
|
6
|
+
};
|
|
7
|
+
var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
|
|
8
|
+
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
|
|
9
|
+
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
|
10
|
+
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
|
11
|
+
};
|
|
12
|
+
var _SessionStore_instances, _SessionStore_chunks, _SessionStore_option, _SessionStore_logger, _SessionStore_chunk, _SessionStore_clean;
|
|
13
|
+
// Uncomment to recalculate the estimated size
|
|
14
|
+
// of an empty session cookie
|
|
15
|
+
// import * as cookie from "../vendored/cookie.js"
|
|
16
|
+
// const { serialize } = cookie
|
|
17
|
+
// console.log(
|
|
18
|
+
// "Cookie estimated to be ",
|
|
19
|
+
// serialize(`__Secure.authjs.session-token.0`, "", {
|
|
20
|
+
// expires: new Date(),
|
|
21
|
+
// httpOnly: true,
|
|
22
|
+
// maxAge: Number.MAX_SAFE_INTEGER,
|
|
23
|
+
// path: "/",
|
|
24
|
+
// sameSite: "strict",
|
|
25
|
+
// secure: true,
|
|
26
|
+
// domain: "example.com",
|
|
27
|
+
// }).length,
|
|
28
|
+
// " bytes"
|
|
29
|
+
// )
|
|
30
|
+
const ALLOWED_COOKIE_SIZE = 4096;
|
|
31
|
+
// Based on commented out section above
|
|
32
|
+
const ESTIMATED_EMPTY_COOKIE_SIZE = 160;
|
|
33
|
+
const CHUNK_SIZE = ALLOWED_COOKIE_SIZE - ESTIMATED_EMPTY_COOKIE_SIZE;
|
|
34
|
+
/**
|
|
35
|
+
* Use secure cookies if the site uses HTTPS
|
|
36
|
+
* This being conditional allows cookies to work non-HTTPS development URLs
|
|
37
|
+
* Honour secure cookie option, which sets 'secure' and also adds '__Secure-'
|
|
38
|
+
* prefix, but enable them by default if the site URL is HTTPS; but not for
|
|
39
|
+
* non-HTTPS URLs like http://localhost which are used in development).
|
|
40
|
+
* For more on prefixes see https://googlechrome.github.io/samples/cookie-prefixes/
|
|
41
|
+
*
|
|
42
|
+
* @TODO Review cookie settings (names, options)
|
|
43
|
+
*/
|
|
44
|
+
export function defaultCookies(useSecureCookies) {
|
|
45
|
+
const cookiePrefix = useSecureCookies ? "__Secure-" : "";
|
|
46
|
+
return {
|
|
47
|
+
// default cookie options
|
|
48
|
+
sessionToken: {
|
|
49
|
+
name: `${cookiePrefix}authjs.session-token`,
|
|
50
|
+
options: {
|
|
51
|
+
httpOnly: true,
|
|
52
|
+
sameSite: "lax",
|
|
53
|
+
path: "/",
|
|
54
|
+
secure: useSecureCookies,
|
|
55
|
+
},
|
|
56
|
+
},
|
|
57
|
+
callbackUrl: {
|
|
58
|
+
name: `${cookiePrefix}authjs.callback-url`,
|
|
59
|
+
options: {
|
|
60
|
+
httpOnly: true,
|
|
61
|
+
sameSite: "lax",
|
|
62
|
+
path: "/",
|
|
63
|
+
secure: useSecureCookies,
|
|
64
|
+
},
|
|
65
|
+
},
|
|
66
|
+
csrfToken: {
|
|
67
|
+
// Default to __Host- for CSRF token for additional protection if using useSecureCookies
|
|
68
|
+
// NB: The `__Host-` prefix is stricter than the `__Secure-` prefix.
|
|
69
|
+
name: `${useSecureCookies ? "__Host-" : ""}authjs.csrf-token`,
|
|
70
|
+
options: {
|
|
71
|
+
httpOnly: true,
|
|
72
|
+
sameSite: "lax",
|
|
73
|
+
path: "/",
|
|
74
|
+
secure: useSecureCookies,
|
|
75
|
+
},
|
|
76
|
+
},
|
|
77
|
+
pkceCodeVerifier: {
|
|
78
|
+
name: `${cookiePrefix}authjs.pkce.code_verifier`,
|
|
79
|
+
options: {
|
|
80
|
+
httpOnly: true,
|
|
81
|
+
sameSite: "lax",
|
|
82
|
+
path: "/",
|
|
83
|
+
secure: useSecureCookies,
|
|
84
|
+
maxAge: 60 * 15, // 15 minutes in seconds
|
|
85
|
+
},
|
|
86
|
+
},
|
|
87
|
+
state: {
|
|
88
|
+
name: `${cookiePrefix}authjs.state`,
|
|
89
|
+
options: {
|
|
90
|
+
httpOnly: true,
|
|
91
|
+
sameSite: "lax",
|
|
92
|
+
path: "/",
|
|
93
|
+
secure: useSecureCookies,
|
|
94
|
+
maxAge: 60 * 15, // 15 minutes in seconds
|
|
95
|
+
},
|
|
96
|
+
},
|
|
97
|
+
nonce: {
|
|
98
|
+
name: `${cookiePrefix}authjs.nonce`,
|
|
99
|
+
options: {
|
|
100
|
+
httpOnly: true,
|
|
101
|
+
sameSite: "lax",
|
|
102
|
+
path: "/",
|
|
103
|
+
secure: useSecureCookies,
|
|
104
|
+
},
|
|
105
|
+
},
|
|
106
|
+
webauthnChallenge: {
|
|
107
|
+
name: `${cookiePrefix}authjs.challenge`,
|
|
108
|
+
options: {
|
|
109
|
+
httpOnly: true,
|
|
110
|
+
sameSite: "lax",
|
|
111
|
+
path: "/",
|
|
112
|
+
secure: useSecureCookies,
|
|
113
|
+
maxAge: 60 * 15, // 15 minutes in seconds
|
|
114
|
+
},
|
|
115
|
+
},
|
|
116
|
+
};
|
|
117
|
+
}
|
|
118
|
+
export class SessionStore {
|
|
119
|
+
constructor(option, cookies, logger) {
|
|
120
|
+
_SessionStore_instances.add(this);
|
|
121
|
+
_SessionStore_chunks.set(this, {});
|
|
122
|
+
_SessionStore_option.set(this, void 0);
|
|
123
|
+
_SessionStore_logger.set(this, void 0);
|
|
124
|
+
__classPrivateFieldSet(this, _SessionStore_logger, logger, "f");
|
|
125
|
+
__classPrivateFieldSet(this, _SessionStore_option, option, "f");
|
|
126
|
+
if (!cookies)
|
|
127
|
+
return;
|
|
128
|
+
const { name: sessionCookiePrefix } = option;
|
|
129
|
+
for (const [name, value] of Object.entries(cookies)) {
|
|
130
|
+
if (!name.startsWith(sessionCookiePrefix) || !value)
|
|
131
|
+
continue;
|
|
132
|
+
__classPrivateFieldGet(this, _SessionStore_chunks, "f")[name] = value;
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
/**
|
|
136
|
+
* The JWT Session or database Session ID
|
|
137
|
+
* constructed from the cookie chunks.
|
|
138
|
+
*/
|
|
139
|
+
get value() {
|
|
140
|
+
// Sort the chunks by their keys before joining
|
|
141
|
+
const sortedKeys = Object.keys(__classPrivateFieldGet(this, _SessionStore_chunks, "f")).sort((a, b) => {
|
|
142
|
+
const aSuffix = parseInt(a.split(".").pop() || "0");
|
|
143
|
+
const bSuffix = parseInt(b.split(".").pop() || "0");
|
|
144
|
+
return aSuffix - bSuffix;
|
|
145
|
+
});
|
|
146
|
+
// Use the sorted keys to join the chunks in the correct order
|
|
147
|
+
return sortedKeys.map((key) => __classPrivateFieldGet(this, _SessionStore_chunks, "f")[key]).join("");
|
|
148
|
+
}
|
|
149
|
+
/**
|
|
150
|
+
* Given a cookie value, return new cookies, chunked, to fit the allowed cookie size.
|
|
151
|
+
* If the cookie has changed from chunked to unchunked or vice versa,
|
|
152
|
+
* it deletes the old cookies as well.
|
|
153
|
+
*/
|
|
154
|
+
chunk(value, options) {
|
|
155
|
+
// Assume all cookies should be cleaned by default
|
|
156
|
+
const cookies = __classPrivateFieldGet(this, _SessionStore_instances, "m", _SessionStore_clean).call(this);
|
|
157
|
+
// Calculate new chunks
|
|
158
|
+
const chunked = __classPrivateFieldGet(this, _SessionStore_instances, "m", _SessionStore_chunk).call(this, {
|
|
159
|
+
name: __classPrivateFieldGet(this, _SessionStore_option, "f").name,
|
|
160
|
+
value,
|
|
161
|
+
options: { ...__classPrivateFieldGet(this, _SessionStore_option, "f").options, ...options },
|
|
162
|
+
});
|
|
163
|
+
// Update stored chunks / cookies
|
|
164
|
+
for (const chunk of chunked) {
|
|
165
|
+
cookies[chunk.name] = chunk;
|
|
166
|
+
}
|
|
167
|
+
return Object.values(cookies);
|
|
168
|
+
}
|
|
169
|
+
/** Returns a list of cookies that should be cleaned. */
|
|
170
|
+
clean() {
|
|
171
|
+
return Object.values(__classPrivateFieldGet(this, _SessionStore_instances, "m", _SessionStore_clean).call(this));
|
|
172
|
+
}
|
|
173
|
+
}
|
|
174
|
+
_SessionStore_chunks = new WeakMap(), _SessionStore_option = new WeakMap(), _SessionStore_logger = new WeakMap(), _SessionStore_instances = new WeakSet(), _SessionStore_chunk = function _SessionStore_chunk(cookie) {
|
|
175
|
+
const chunkCount = Math.ceil(cookie.value.length / CHUNK_SIZE);
|
|
176
|
+
if (chunkCount === 1) {
|
|
177
|
+
__classPrivateFieldGet(this, _SessionStore_chunks, "f")[cookie.name] = cookie.value;
|
|
178
|
+
return [cookie];
|
|
179
|
+
}
|
|
180
|
+
const cookies = [];
|
|
181
|
+
for (let i = 0; i < chunkCount; i++) {
|
|
182
|
+
const name = `${cookie.name}.${i}`;
|
|
183
|
+
const value = cookie.value.substr(i * CHUNK_SIZE, CHUNK_SIZE);
|
|
184
|
+
cookies.push({ ...cookie, name, value });
|
|
185
|
+
__classPrivateFieldGet(this, _SessionStore_chunks, "f")[name] = value;
|
|
186
|
+
}
|
|
187
|
+
__classPrivateFieldGet(this, _SessionStore_logger, "f").debug("CHUNKING_SESSION_COOKIE", {
|
|
188
|
+
message: `Session cookie exceeds allowed ${ALLOWED_COOKIE_SIZE} bytes.`,
|
|
189
|
+
emptyCookieSize: ESTIMATED_EMPTY_COOKIE_SIZE,
|
|
190
|
+
valueSize: cookie.value.length,
|
|
191
|
+
chunks: cookies.map((c) => c.value.length + ESTIMATED_EMPTY_COOKIE_SIZE),
|
|
192
|
+
});
|
|
193
|
+
return cookies;
|
|
194
|
+
}, _SessionStore_clean = function _SessionStore_clean() {
|
|
195
|
+
const cleanedChunks = {};
|
|
196
|
+
for (const name in __classPrivateFieldGet(this, _SessionStore_chunks, "f")) {
|
|
197
|
+
delete __classPrivateFieldGet(this, _SessionStore_chunks, "f")?.[name];
|
|
198
|
+
cleanedChunks[name] = {
|
|
199
|
+
name,
|
|
200
|
+
value: "",
|
|
201
|
+
options: { ...__classPrivateFieldGet(this, _SessionStore_option, "f").options, maxAge: 0 },
|
|
202
|
+
};
|
|
203
|
+
}
|
|
204
|
+
return cleanedChunks;
|
|
205
|
+
};
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Takes a number in seconds and returns the date in the future.
|
|
3
|
+
* Optionally takes a second date parameter. In that case
|
|
4
|
+
* the date in the future will be calculated from that date instead of now.
|
|
5
|
+
*/
|
|
6
|
+
export declare function fromDate(time: number, date?: number): Date;
|
|
7
|
+
//# sourceMappingURL=date.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"date.d.ts","sourceRoot":"","sources":["../../src/lib/utils/date.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AACH,wBAAgB,QAAQ,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,SAAa,QAEvD"}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Takes a number in seconds and returns the date in the future.
|
|
3
|
+
* Optionally takes a second date parameter. In that case
|
|
4
|
+
* the date in the future will be calculated from that date instead of now.
|
|
5
|
+
*/
|
|
6
|
+
export function fromDate(time, date = Date.now()) {
|
|
7
|
+
return new Date(date + time * 1000);
|
|
8
|
+
}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import type { Theme } from "../../types.js";
|
|
2
|
+
/**
|
|
3
|
+
* Email HTML body
|
|
4
|
+
* Insert invisible space into domains from being turned into a hyperlink by email
|
|
5
|
+
* clients like Outlook and Apple mail, as this is confusing because it seems
|
|
6
|
+
* like they are supposed to click on it to sign in.
|
|
7
|
+
*
|
|
8
|
+
* @note We don't add the email address to avoid needing to escape it, if you do, remember to sanitize it!
|
|
9
|
+
*/
|
|
10
|
+
export declare function html(params: {
|
|
11
|
+
url: string;
|
|
12
|
+
host: string;
|
|
13
|
+
theme: Theme;
|
|
14
|
+
}): string;
|
|
15
|
+
/** Email Text body (fallback for email clients that don't render HTML, e.g. feature phones) */
|
|
16
|
+
export declare function text({ url, host }: {
|
|
17
|
+
url: string;
|
|
18
|
+
host: string;
|
|
19
|
+
}): string;
|
|
20
|
+
//# sourceMappingURL=email.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"email.d.ts","sourceRoot":"","sources":["../../src/lib/utils/email.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,gBAAgB,CAAA;AAE3C;;;;;;;GAOG;AACH,wBAAgB,IAAI,CAAC,MAAM,EAAE;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,KAAK,CAAA;CAAE,UAiDvE;AAED,+FAA+F;AAC/F,wBAAgB,IAAI,CAAC,EAAE,GAAG,EAAE,IAAI,EAAE,EAAE;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,UAEhE"}
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Email HTML body
|
|
3
|
+
* Insert invisible space into domains from being turned into a hyperlink by email
|
|
4
|
+
* clients like Outlook and Apple mail, as this is confusing because it seems
|
|
5
|
+
* like they are supposed to click on it to sign in.
|
|
6
|
+
*
|
|
7
|
+
* @note We don't add the email address to avoid needing to escape it, if you do, remember to sanitize it!
|
|
8
|
+
*/
|
|
9
|
+
export function html(params) {
|
|
10
|
+
const { url, host, theme } = params;
|
|
11
|
+
const escapedHost = host.replace(/\./g, "​.");
|
|
12
|
+
const brandColor = theme.brandColor || "#346df1";
|
|
13
|
+
const buttonText = theme.buttonText || "#fff";
|
|
14
|
+
const color = {
|
|
15
|
+
background: "#f9f9f9",
|
|
16
|
+
text: "#444",
|
|
17
|
+
mainBackground: "#fff",
|
|
18
|
+
buttonBackground: brandColor,
|
|
19
|
+
buttonBorder: brandColor,
|
|
20
|
+
buttonText,
|
|
21
|
+
};
|
|
22
|
+
return `
|
|
23
|
+
<body style="background: ${color.background};">
|
|
24
|
+
<table width="100%" border="0" cellspacing="20" cellpadding="0"
|
|
25
|
+
style="background: ${color.mainBackground}; max-width: 600px; margin: auto; border-radius: 10px;">
|
|
26
|
+
<tr>
|
|
27
|
+
<td align="center"
|
|
28
|
+
style="padding: 10px 0px; font-size: 22px; font-family: Helvetica, Arial, sans-serif; color: ${color.text};">
|
|
29
|
+
Sign in to <strong>${escapedHost}</strong>
|
|
30
|
+
</td>
|
|
31
|
+
</tr>
|
|
32
|
+
<tr>
|
|
33
|
+
<td align="center" style="padding: 20px 0;">
|
|
34
|
+
<table border="0" cellspacing="0" cellpadding="0">
|
|
35
|
+
<tr>
|
|
36
|
+
<td align="center" style="border-radius: 5px;" bgcolor="${color.buttonBackground}"><a href="${url}"
|
|
37
|
+
target="_blank"
|
|
38
|
+
style="font-size: 18px; font-family: Helvetica, Arial, sans-serif; color: ${color.buttonText}; text-decoration: none; border-radius: 5px; padding: 10px 20px; border: 1px solid ${color.buttonBorder}; display: inline-block; font-weight: bold;">Sign
|
|
39
|
+
in</a></td>
|
|
40
|
+
</tr>
|
|
41
|
+
</table>
|
|
42
|
+
</td>
|
|
43
|
+
</tr>
|
|
44
|
+
<tr>
|
|
45
|
+
<td align="center"
|
|
46
|
+
style="padding: 0px 0px 10px 0px; font-size: 16px; line-height: 22px; font-family: Helvetica, Arial, sans-serif; color: ${color.text};">
|
|
47
|
+
If you did not request this email you can safely ignore it.
|
|
48
|
+
</td>
|
|
49
|
+
</tr>
|
|
50
|
+
</table>
|
|
51
|
+
</body>
|
|
52
|
+
`;
|
|
53
|
+
}
|
|
54
|
+
/** Email Text body (fallback for email clients that don't render HTML, e.g. feature phones) */
|
|
55
|
+
export function text({ url, host }) {
|
|
56
|
+
return `Sign in to ${host}\n${url}\n\n`;
|
|
57
|
+
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import type { AuthAction } from "../../types.js";
|
|
2
|
+
import type { AuthConfig } from "../../index.js";
|
|
3
|
+
/**
|
|
4
|
+
* Set default env variables on the config object
|
|
5
|
+
* @param suppressWarnings intended for framework authors.
|
|
6
|
+
*/
|
|
7
|
+
export declare function setEnvDefaults(envObject: any, config: AuthConfig, suppressBasePathWarning?: boolean): void;
|
|
8
|
+
export declare function createActionURL(action: AuthAction, protocol: string, headers: Headers, envObject: any, config: Pick<AuthConfig, "basePath" | "logger">): URL;
|
|
9
|
+
//# sourceMappingURL=env.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"env.d.ts","sourceRoot":"","sources":["../../src/lib/utils/env.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAA;AAChD,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAA;AAGhD;;;GAGG;AACH,wBAAgB,cAAc,CAC5B,SAAS,EAAE,GAAG,EACd,MAAM,EAAE,UAAU,EAClB,uBAAuB,UAAQ,QA2DhC;AAED,wBAAgB,eAAe,CAC7B,MAAM,EAAE,UAAU,EAClB,QAAQ,EAAE,MAAM,EAChB,OAAO,EAAE,OAAO,EAChB,SAAS,EAAE,GAAG,EACd,MAAM,EAAE,IAAI,CAAC,UAAU,EAAE,UAAU,GAAG,QAAQ,CAAC,GAC9C,GAAG,CAkCL"}
|