From 4d2412a0fe0af860a7bd8da4f6ca660df70428eb Mon Sep 17 00:00:00 2001 From: Erin Allison Date: Mon, 30 Dec 2024 12:38:17 -0500 Subject: [PATCH 1/4] Add Support for Alternate Email Transports (#1580) * Add support for AWS SES and SMTP email transports Signed-off-by: Erin Allison * Correct environment variable names for new email settings Signed-off-by: Erin Allison * Correct option names being passed to nodemailer for SMTP Signed-off-by: Erin Allison * Remove use of AWS SDK synthetic default export It apparently causes issues when transpiled/bundled Signed-off-by: Erin Allison * Add documentation for new email settings Signed-off-by: Erin Allison * Move nodemailer types to devDependencies Signed-off-by: Erin Allison * Adjust mail transport error handling Gotta keep the linter happy :) Signed-off-by: Erin Allison * Fix typecheck error on MailTransportOptions Signed-off-by: Erin Allison * Correct environment variable usage for SMTP email transport Signed-off-by: Erin Allison --------- Signed-off-by: Erin Allison --- .env.example | 28 +- apps/webapp/app/env.server.ts | 15 + apps/webapp/app/services/email.server.ts | 38 +- docs/open-source-self-hosting.mdx | 40 +- internal-packages/emails/package.json | 5 +- internal-packages/emails/src/index.tsx | 80 +- .../emails/src/transports/aws-ses.ts | 67 ++ .../emails/src/transports/index.ts | 52 ++ .../emails/src/transports/null.ts | 29 + .../emails/src/transports/resend.ts | 51 + .../emails/src/transports/smtp.ts | 66 ++ pnpm-lock.yaml | 880 ++++++++++++++++++ 12 files changed, 1286 insertions(+), 65 deletions(-) create mode 100644 internal-packages/emails/src/transports/aws-ses.ts create mode 100644 internal-packages/emails/src/transports/index.ts create mode 100644 internal-packages/emails/src/transports/null.ts create mode 100644 internal-packages/emails/src/transports/resend.ts create mode 100644 internal-packages/emails/src/transports/smtp.ts diff --git a/.env.example b/.env.example index 2e1725cf0b..06cefc0aec 100644 --- a/.env.example +++ b/.env.example @@ -31,10 +31,32 @@ DEV_OTEL_BATCH_PROCESSING_ENABLED="0" # AUTH_GITHUB_CLIENT_ID= # AUTH_GITHUB_CLIENT_SECRET= -# Resend is an email service used for signing in to Trigger.dev via a Magic Link. -# Emails will print to the console if you leave these commented out +# Configure an email transport to allow users to sign in to Trigger.dev via a Magic Link. +# If none are configured, emails will print to the console instead. +# Uncomment one of the following blocks to allow delivery of + +# Resend ### Visit https://resend.com, create an account and get your API key. Then insert it below along with your From and Reply To email addresses. Visit https://resend.com/docs for more information. -# RESEND_API_KEY= +# EMAIL_TRANSPORT=resend +# FROM_EMAIL= +# REPLY_TO_EMAIL= +# RESEND_API_KEY= + +# Generic SMTP +### Enter the configuration provided by your mail provider. Visit https://nodemailer.com/smtp/ for more information +### SMTP_SECURE = false will use STARTTLS when connecting to a server that supports it (usually port 587) +# EMAIL_TRANSPORT=smtp +# FROM_EMAIL= +# REPLY_TO_EMAIL= +# SMTP_HOST= +# SMTP_PORT=587 +# SMTP_SECURE=false +# SMTP_USER= +# SMTP_PASSWORD= + +# AWS Simple Email Service +### Authentication is configured using the default Node.JS credentials provider chain (https://docs.aws.amazon.com/AWSJavaScriptSDK/v3/latest/Package/-aws-sdk-credential-providers/#fromnodeproviderchain) +# EMAIL_TRANSPORT=aws-ses # FROM_EMAIL= # REPLY_TO_EMAIL= diff --git a/apps/webapp/app/env.server.ts b/apps/webapp/app/env.server.ts index 99c810c76f..166b1531d5 100644 --- a/apps/webapp/app/env.server.ts +++ b/apps/webapp/app/env.server.ts @@ -44,9 +44,16 @@ const EnvironmentSchema = z.object({ HIGHLIGHT_PROJECT_ID: z.string().optional(), AUTH_GITHUB_CLIENT_ID: z.string().optional(), AUTH_GITHUB_CLIENT_SECRET: z.string().optional(), + EMAIL_TRANSPORT: z.enum(["resend", "smtp", "aws-ses"]).optional(), FROM_EMAIL: z.string().optional(), REPLY_TO_EMAIL: z.string().optional(), RESEND_API_KEY: z.string().optional(), + SMTP_HOST: z.string().optional(), + SMTP_PORT: z.coerce.number().optional(), + SMTP_SECURE: z.coerce.boolean().optional(), + SMTP_USER: z.string().optional(), + SMTP_PASSWORD: z.string().optional(), + PLAIN_API_KEY: z.string().optional(), RUNTIME_PLATFORM: z.enum(["docker-compose", "ecs", "local"]).default("local"), WORKER_SCHEMA: z.string().default("graphile_worker"), @@ -195,8 +202,16 @@ const EnvironmentSchema = z.object({ ORG_SLACK_INTEGRATION_CLIENT_SECRET: z.string().optional(), /** These enable the alerts feature in v3 */ + ALERT_EMAIL_TRANSPORT: z.enum(["resend", "smtp", "aws-ses"]).optional(), ALERT_FROM_EMAIL: z.string().optional(), + ALERT_REPLY_TO_EMAIL: z.string().optional(), ALERT_RESEND_API_KEY: z.string().optional(), + ALERT_SMTP_HOST: z.string().optional(), + ALERT_SMTP_PORT: z.coerce.number().optional(), + ALERT_SMTP_SECURE: z.coerce.boolean().optional(), + ALERT_SMTP_USER: z.string().optional(), + ALERT_SMTP_PASSWORD: z.string().optional(), + MAX_SEQUENTIAL_INDEX_FAILURE_COUNT: z.coerce.number().default(96), diff --git a/apps/webapp/app/services/email.server.ts b/apps/webapp/app/services/email.server.ts index 46f971505a..cb9e94c3b7 100644 --- a/apps/webapp/app/services/email.server.ts +++ b/apps/webapp/app/services/email.server.ts @@ -1,5 +1,5 @@ import type { DeliverEmail, SendPlainTextOptions } from "emails"; -import { EmailClient } from "emails"; +import { EmailClient, MailTransportOptions } from "emails"; import type { SendEmailOptions } from "remix-auth-email-link"; import { redirect } from "remix-typedjson"; import { env } from "~/env.server"; @@ -13,7 +13,7 @@ const client = singleton( "email-client", () => new EmailClient({ - apikey: env.RESEND_API_KEY, + transport: buildTransportOptions(), imagesBaseUrl: env.APP_ORIGIN, from: env.FROM_EMAIL ?? "team@email.trigger.dev", replyTo: env.REPLY_TO_EMAIL ?? "help@email.trigger.dev", @@ -24,13 +24,45 @@ const alertsClient = singleton( "alerts-email-client", () => new EmailClient({ - apikey: env.ALERT_RESEND_API_KEY, + transport: buildTransportOptions(true), imagesBaseUrl: env.APP_ORIGIN, from: env.ALERT_FROM_EMAIL ?? "noreply@alerts.trigger.dev", replyTo: env.REPLY_TO_EMAIL ?? "help@email.trigger.dev", }) ); +function buildTransportOptions(alerts?: boolean): MailTransportOptions { + const transportType = alerts ? env.ALERT_EMAIL_TRANSPORT : env.EMAIL_TRANSPORT + logger.debug(`Constructing email transport '${transportType}' for usage '${alerts?'alerts':'general'}'`) + + switch (transportType) { + case "aws-ses": + return { type: "aws-ses" }; + case "resend": + return { + type: "resend", + config: { + apiKey: alerts ? env.ALERT_RESEND_API_KEY : env.RESEND_API_KEY, + } + } + case "smtp": + return { + type: "smtp", + config: { + host: alerts ? env.ALERT_SMTP_HOST : env.SMTP_HOST, + port: alerts ? env.ALERT_SMTP_PORT : env.SMTP_PORT, + secure: alerts ? env.ALERT_SMTP_SECURE : env.SMTP_SECURE, + auth: { + user: alerts ? env.ALERT_SMTP_USER : env.SMTP_USER, + pass: alerts ? env.ALERT_SMTP_PASSWORD : env.SMTP_PASSWORD + } + } + }; + default: + return { type: undefined }; + } +} + export async function sendMagicLinkEmail(options: SendEmailOptions): Promise { // Auto redirect when in development mode if (env.NODE_ENV === "development") { diff --git a/docs/open-source-self-hosting.mdx b/docs/open-source-self-hosting.mdx index 5eed85b8e4..d2e785093d 100644 --- a/docs/open-source-self-hosting.mdx +++ b/docs/open-source-self-hosting.mdx @@ -269,7 +269,45 @@ TRIGGER_IMAGE_TAG=v3.0.4 ### Auth options -By default, magic link auth is the only login option. If the `RESEND_API_KEY` env var is not set, the magic links will be logged by the webapp container and not sent via email. +By default, magic link auth is the only login option. If the `EMAIL_TRANSPORT` env var is not set, the magic links will be logged by the webapp container and not sent via email. + +Depending on your choice of mail provider/transport, you will want to configure a set of variables like one of the following: + +##### Resend: +```bash +EMAIL_TRANSPORT=resend +FROM_EMAIL= +REPLY_TO_EMAIL= +RESEND_API_KEY= +``` + +##### SMTP + +Note that setting `SMTP_SECURE=false` does _not_ mean the email is sent insecurely. +This simply means that the connection is secured using the modern STARTTLS protocol command instead of implicit TLS. +You should only set this to true when the SMTP server host directs you to do so (generally when using port 465) + +```bash +EMAIL_TRANSPORT=smtp +FROM_EMAIL= +REPLY_TO_EMAIL= +SMTP_HOST= +SMTP_PORT=587 +SMTP_SECURE=false +SMTP_USER= +SMTP_PASSWORD= +``` + +##### AWS Simple Email Service + +Credentials are to be supplied as with any other program using the AWS SDK. +In this scenario, you would likely either supply the additional environment variables `AWS_REGION`, `AWS_ACCESS_KEY_ID` and `AWS_SECRET_ACCESS_KEY` or, when running on AWS, use credentials supplied by the EC2 IMDS. + +```bash +EMAIL_TRANSPORT=aws-ses +FROM_EMAIL= +REPLY_TO_EMAIL= +``` All email addresses can sign up and log in this way. If you would like to restrict this, you can use the `WHITELISTED_EMAILS` env var. For example: diff --git a/internal-packages/emails/package.json b/internal-packages/emails/package.json index b22fb45e4f..d7fa150fbb 100644 --- a/internal-packages/emails/package.json +++ b/internal-packages/emails/package.json @@ -9,8 +9,10 @@ "dev": "PORT=3080 email dev" }, "dependencies": { + "@aws-sdk/client-ses": "^3.716.0", "@react-email/components": "0.0.16", "@react-email/render": "^0.0.12", + "nodemailer": "^6.9.16", "react": "^18.2.0", "react-email": "^2.1.1", "resend": "^3.2.0", @@ -19,10 +21,11 @@ }, "devDependencies": { "@types/node": "^18", + "@types/nodemailer": "^6.4.17", "@types/react": "18.2.69", "typescript": "^4.9.4" }, "engines": { "node": ">=18.0.0" } -} \ No newline at end of file +} diff --git a/internal-packages/emails/src/index.tsx b/internal-packages/emails/src/index.tsx index 8ad1a35b8e..f1d1eef695 100644 --- a/internal-packages/emails/src/index.tsx +++ b/internal-packages/emails/src/index.tsx @@ -1,7 +1,8 @@ -import { render } from "@react-email/render"; import { ReactElement } from "react"; -import AlertRunFailureEmail, { AlertRunEmailSchema } from "../emails/alert-run-failure"; + +import { z } from "zod"; import AlertAttemptFailureEmail, { AlertAttemptEmailSchema } from "../emails/alert-attempt-failure"; +import AlertRunFailureEmail, { AlertRunEmailSchema } from "../emails/alert-run-failure"; import { setGlobalBasePath } from "../emails/components/BasePath"; import AlertDeploymentFailureEmail, { AlertDeploymentFailureEmailSchema, @@ -12,9 +13,9 @@ import AlertDeploymentSuccessEmail, { import InviteEmail, { InviteEmailSchema } from "../emails/invite"; import MagicLinkEmail from "../emails/magic-link"; import WelcomeEmail from "../emails/welcome"; +import { constructMailTransport, MailTransport, MailTransportOptions } from "./transports"; -import { Resend } from "resend"; -import { z } from "zod"; +export { type MailTransportOptions } export const DeliverEmailSchema = z .discriminatedUnion("email", [ @@ -39,14 +40,20 @@ export type DeliverEmail = z.infer; export type SendPlainTextOptions = { to: string; subject: string; text: string }; export class EmailClient { - #client?: Resend; + #transport: MailTransport; + #imagesBaseUrl: string; #from: string; #replyTo: string; - constructor(config: { apikey?: string; imagesBaseUrl: string; from: string; replyTo: string }) { - this.#client = - config.apikey && config.apikey.startsWith("re_") ? new Resend(config.apikey) : undefined; + constructor(config: { + transport?: MailTransportOptions; + imagesBaseUrl: string; + from: string; + replyTo: string; + }) { + this.#transport = constructMailTransport(config.transport ?? { type: undefined }); + this.#imagesBaseUrl = config.imagesBaseUrl; this.#from = config.from; this.#replyTo = config.replyTo; @@ -57,25 +64,21 @@ export class EmailClient { setGlobalBasePath(this.#imagesBaseUrl); - return this.#sendEmail({ + return await this.#transport.send({ to: data.to, subject, react: component, + from: this.#from, + replyTo: this.#replyTo, }); } async sendPlainText(options: SendPlainTextOptions) { - if (this.#client) { - await this.#client.emails.send({ - from: this.#from, - to: options.to, - reply_to: this.#replyTo, - subject: options.subject, - text: options.text, - }); - - return; - } + await this.#transport.sendPlainText({ + ...options, + from: this.#from, + replyTo: this.#replyTo, + }); } #getTemplate(data: DeliverEmail): { @@ -124,41 +127,4 @@ export class EmailClient { } } } - - async #sendEmail({ to, subject, react }: { to: string; subject: string; react: ReactElement }) { - if (this.#client) { - const result = await this.#client.emails.send({ - from: this.#from, - to, - reply_to: this.#replyTo, - subject, - react, - }); - - if (result.error) { - console.error( - `Failed to send email to ${to}, ${subject}. Error ${result.error.name}: ${result.error.message}` - ); - throw new EmailError(result.error); - } - - return; - } - - console.log(` -##### sendEmail to ${to}, subject: ${subject} - -${render(react, { - plainText: true, -})} - `); - } -} - -//EmailError type where you can set the name and message -export class EmailError extends Error { - constructor({ name, message }: { name: string; message: string }) { - super(message); - this.name = name; - } } diff --git a/internal-packages/emails/src/transports/aws-ses.ts b/internal-packages/emails/src/transports/aws-ses.ts new file mode 100644 index 0000000000..58a136e1d6 --- /dev/null +++ b/internal-packages/emails/src/transports/aws-ses.ts @@ -0,0 +1,67 @@ +import { render } from "@react-email/render"; +import { EmailError, MailMessage, MailTransport, PlainTextMailMessage } from "./index"; +import nodemailer from "nodemailer" +import * as awsSes from "@aws-sdk/client-ses" + +export type AwsSesMailTransportOptions = { + type: 'aws-ses', +} + +export class AwsSesMailTransport implements MailTransport { + #client: nodemailer.Transporter; + + constructor(options: AwsSesMailTransportOptions) { + const ses = new awsSes.SESClient() + + this.#client = nodemailer.createTransport({ + SES: { + aws: awsSes, + ses + } + }) + } + + async send({to, from, replyTo, subject, react}: MailMessage): Promise { + try { + await this.#client.sendMail({ + from: from, + to, + replyTo: replyTo, + subject, + html: render(react), + }); + } + catch (error) { + if (error instanceof Error) { + console.error( + `Failed to send email to ${to}, ${subject}. Error ${error.name}: ${error.message}` + ); + throw new EmailError(error); + } else { + throw error; + } + } + } + + async sendPlainText({to, from, replyTo, subject, text}: PlainTextMailMessage): Promise { + try { + await this.#client.sendMail({ + from: from, + to, + replyTo: replyTo, + subject, + text: text, + }); + } + catch (error) { + if (error instanceof Error) { + console.error( + `Failed to send email to ${to}, ${subject}. Error ${error.name}: ${error.message}` + ); + throw new EmailError(error); + } else { + throw error; + } + } + } +} diff --git a/internal-packages/emails/src/transports/index.ts b/internal-packages/emails/src/transports/index.ts new file mode 100644 index 0000000000..af85ab6ee1 --- /dev/null +++ b/internal-packages/emails/src/transports/index.ts @@ -0,0 +1,52 @@ +import { ReactElement } from "react"; +import { AwsSesMailTransport, AwsSesMailTransportOptions } from "./aws-ses"; +import { NullMailTransport, NullMailTransportOptions } from "./null"; +import { ResendMailTransport, ResendMailTransportOptions } from "./resend"; +import { SmtpMailTransport, SmtpMailTransportOptions } from "./smtp"; + +export type MailMessage = { + to: string; + from: string; + replyTo: string; + subject: string; + react: ReactElement; +}; + +export type PlainTextMailMessage = { + to: string; + from: string; + replyTo: string; + subject: string; + text: string; +} + +export interface MailTransport { + send(message: MailMessage): Promise; + sendPlainText(message: PlainTextMailMessage): Promise; +} + +export class EmailError extends Error { + constructor({ name, message }: { name: string; message: string }) { + super(message); + this.name = name; + } +} + +export type MailTransportOptions = + AwsSesMailTransportOptions | + ResendMailTransportOptions | + NullMailTransportOptions | + SmtpMailTransportOptions + +export function constructMailTransport(options: MailTransportOptions): MailTransport { + switch(options.type) { + case "aws-ses": + return new AwsSesMailTransport(options); + case "resend": + return new ResendMailTransport(options); + case "smtp": + return new SmtpMailTransport(options); + case undefined: + return new NullMailTransport(options); + } +} diff --git a/internal-packages/emails/src/transports/null.ts b/internal-packages/emails/src/transports/null.ts new file mode 100644 index 0000000000..bb8fe10c38 --- /dev/null +++ b/internal-packages/emails/src/transports/null.ts @@ -0,0 +1,29 @@ +import { render } from "@react-email/render"; +import { MailMessage, MailTransport, PlainTextMailMessage } from "./index"; + +export type NullMailTransportOptions = { + type: undefined, +} + +export class NullMailTransport implements MailTransport { + constructor(options: NullMailTransportOptions) { + } + + async send({to, subject, react}: MailMessage): Promise { + console.log(` +##### sendEmail to ${to}, subject: ${subject} + +${render(react, { + plainText: true, + })} + `); + } + + async sendPlainText({to, subject, text}: PlainTextMailMessage): Promise { + console.log(` +##### sendEmail to ${to}, subject: ${subject} + +${text} + `); + } +} diff --git a/internal-packages/emails/src/transports/resend.ts b/internal-packages/emails/src/transports/resend.ts new file mode 100644 index 0000000000..9241dd4b93 --- /dev/null +++ b/internal-packages/emails/src/transports/resend.ts @@ -0,0 +1,51 @@ +import { EmailError, MailMessage, MailTransport, PlainTextMailMessage } from "./index"; +import { Resend } from "resend"; + +export type ResendMailTransportOptions = { + type: 'resend', + config: { + apiKey?: string + } +} + +export class ResendMailTransport implements MailTransport { + #client: Resend; + + constructor(options: ResendMailTransportOptions) { + this.#client = new Resend(options.config.apiKey) + } + + async send({to, from, replyTo, subject, react}: MailMessage): Promise { + const result = await this.#client.emails.send({ + from: from, + to, + reply_to: replyTo, + subject, + react, + }); + + if (result.error) { + console.error( + `Failed to send email to ${to}, ${subject}. Error ${result.error.name}: ${result.error.message}` + ); + throw new EmailError(result.error); + } + } + + async sendPlainText({to, from, replyTo, subject, text}: PlainTextMailMessage): Promise { + const result = await this.#client.emails.send({ + from: from, + to, + reply_to: replyTo, + subject, + text, + }); + + if (result.error) { + console.error( + `Failed to send email to ${to}, ${subject}. Error ${result.error.name}: ${result.error.message}` + ); + throw new EmailError(result.error); + } + } +} diff --git a/internal-packages/emails/src/transports/smtp.ts b/internal-packages/emails/src/transports/smtp.ts new file mode 100644 index 0000000000..5dfd1dec57 --- /dev/null +++ b/internal-packages/emails/src/transports/smtp.ts @@ -0,0 +1,66 @@ +import { render } from "@react-email/render"; +import nodemailer from "nodemailer"; +import { EmailError, MailMessage, MailTransport, PlainTextMailMessage } from "./index"; + +export type SmtpMailTransportOptions = { + type: "smtp"; + config: { + host?: string; + port?: number; + secure?: boolean; + auth?: { + user?: string; + pass?: string; + }; + }; +}; + +export class SmtpMailTransport implements MailTransport { + #client: nodemailer.Transporter; + + constructor(options: SmtpMailTransportOptions) { + this.#client = nodemailer.createTransport(options.config); + } + + async send({ to, from, replyTo, subject, react }: MailMessage): Promise { + try { + await this.#client.sendMail({ + from: from, + to, + replyTo: replyTo, + subject, + html: render(react), + }); + } catch (error) { + if (error instanceof Error) { + console.error( + `Failed to send email to ${to}, ${subject}. Error ${error.name}: ${error.message}` + ); + throw new EmailError(error); + } else { + throw error; + } + } + } + + async sendPlainText({ to, from, replyTo, subject, text }: PlainTextMailMessage): Promise { + try { + await this.#client.sendMail({ + from: from, + to, + replyTo: replyTo, + subject, + text: text, + }); + } catch (error) { + if (error instanceof Error) { + console.error( + `Failed to send email to ${to}, ${subject}. Error ${error.name}: ${error.message}` + ); + throw new EmailError(error); + } else { + throw error; + } + } + } +} diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 17bc72bddc..f208eb3d2a 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -859,12 +859,18 @@ importers: internal-packages/emails: dependencies: + '@aws-sdk/client-ses': + specifier: ^3.716.0 + version: 3.716.0 '@react-email/components': specifier: 0.0.16 version: 0.0.16(@types/react@18.2.69)(react@18.3.1) '@react-email/render': specifier: ^0.0.12 version: 0.0.12 + nodemailer: + specifier: ^6.9.16 + version: 6.9.16 react: specifier: ^18.2.0 version: 18.3.1 @@ -884,6 +890,9 @@ importers: '@types/node': specifier: ^18 version: 18.19.20 + '@types/nodemailer': + specifier: ^6.4.17 + version: 6.4.17 '@types/react': specifier: 18.2.69 version: 18.2.69 @@ -2362,6 +2371,18 @@ packages: tslib: 1.14.1 dev: false + /@aws-crypto/sha256-browser@5.2.0: + resolution: {integrity: sha512-AXfN/lGotSQwu6HNcEsIASo7kWXZ5HYWvfOmSNKDsEqC4OashTp8alTmaz+F7TC2L083SFv5RdB+qU3Vs1kZqw==} + dependencies: + '@aws-crypto/sha256-js': 5.2.0 + '@aws-crypto/supports-web-crypto': 5.2.0 + '@aws-crypto/util': 5.2.0 + '@aws-sdk/types': 3.714.0 + '@aws-sdk/util-locate-window': 3.310.0 + '@smithy/util-utf8': 2.0.2 + tslib: 2.6.2 + dev: false + /@aws-crypto/sha256-js@3.0.0: resolution: {integrity: sha512-PnNN7os0+yd1XvXAy23CFOmTbMaDxgxXtTKHybrJ39Y8kGzBATgBFibWJKH6BhytLI/Zyszs87xCOBNyBig6vQ==} dependencies: @@ -2370,12 +2391,27 @@ packages: tslib: 1.14.1 dev: false + /@aws-crypto/sha256-js@5.2.0: + resolution: {integrity: sha512-FFQQyu7edu4ufvIZ+OadFpHHOt+eSTBaYaki44c+akjg7qZg9oOQeLlk77F6tSYqjDAFClrHJk9tMf0HdVyOvA==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-crypto/util': 5.2.0 + '@aws-sdk/types': 3.714.0 + tslib: 2.6.2 + dev: false + /@aws-crypto/supports-web-crypto@3.0.0: resolution: {integrity: sha512-06hBdMwUAb2WFTuGG73LSC0wfPu93xWwo5vL2et9eymgmu3Id5vFAHBbajVWiGhPO37qcsdCap/FqXvJGJWPIg==} dependencies: tslib: 1.14.1 dev: false + /@aws-crypto/supports-web-crypto@5.2.0: + resolution: {integrity: sha512-iAvUotm021kM33eCdNfwIN//F77/IADDSs58i+MDaOqFrVjZo9bAal0NK7HurRuWLLpF1iLX7gbWrjHjeo+YFg==} + dependencies: + tslib: 2.6.2 + dev: false + /@aws-crypto/util@3.0.0: resolution: {integrity: sha512-2OJlpeJpCR48CC8r+uKVChzs9Iungj9wkZrl8Z041DWEWvyIHILYKCPNzJghKsivj+S3mLo6BVc7mBNzdxA46w==} dependencies: @@ -2384,6 +2420,64 @@ packages: tslib: 1.14.1 dev: false + /@aws-crypto/util@5.2.0: + resolution: {integrity: sha512-4RkU9EsI6ZpBve5fseQlGNUWKMa1RLPQ1dnjnQoe07ldfIzcsGb5hC5W0Dm7u423KWzawlrpbjXBrXCEv9zazQ==} + dependencies: + '@aws-sdk/types': 3.714.0 + '@smithy/util-utf8': 2.0.2 + tslib: 2.6.2 + dev: false + + /@aws-sdk/client-ses@3.716.0: + resolution: {integrity: sha512-lYsg2x3Z6R5ngBX1EqFKR6jf77ewbGg+aZV6V4ucVCghaGGcGnGisRP4FAep3IgkrZuByEYeJaA6cTli98qaOQ==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-crypto/sha256-browser': 5.2.0 + '@aws-crypto/sha256-js': 5.2.0 + '@aws-sdk/client-sso-oidc': 3.716.0(@aws-sdk/client-sts@3.716.0) + '@aws-sdk/client-sts': 3.716.0 + '@aws-sdk/core': 3.716.0 + '@aws-sdk/credential-provider-node': 3.716.0(@aws-sdk/client-sso-oidc@3.716.0)(@aws-sdk/client-sts@3.716.0) + '@aws-sdk/middleware-host-header': 3.714.0 + '@aws-sdk/middleware-logger': 3.714.0 + '@aws-sdk/middleware-recursion-detection': 3.714.0 + '@aws-sdk/middleware-user-agent': 3.716.0 + '@aws-sdk/region-config-resolver': 3.714.0 + '@aws-sdk/types': 3.714.0 + '@aws-sdk/util-endpoints': 3.714.0 + '@aws-sdk/util-user-agent-browser': 3.714.0 + '@aws-sdk/util-user-agent-node': 3.716.0 + '@smithy/config-resolver': 3.0.13 + '@smithy/core': 2.5.5 + '@smithy/fetch-http-handler': 4.1.2 + '@smithy/hash-node': 3.0.11 + '@smithy/invalid-dependency': 3.0.11 + '@smithy/middleware-content-length': 3.0.13 + '@smithy/middleware-endpoint': 3.2.6 + '@smithy/middleware-retry': 3.0.31 + '@smithy/middleware-serde': 3.0.11 + '@smithy/middleware-stack': 3.0.11 + '@smithy/node-config-provider': 3.1.12 + '@smithy/node-http-handler': 3.3.2 + '@smithy/protocol-http': 4.1.8 + '@smithy/smithy-client': 3.5.1 + '@smithy/types': 3.7.2 + '@smithy/url-parser': 3.0.11 + '@smithy/util-base64': 3.0.0 + '@smithy/util-body-length-browser': 3.0.0 + '@smithy/util-body-length-node': 3.0.0 + '@smithy/util-defaults-mode-browser': 3.0.31 + '@smithy/util-defaults-mode-node': 3.0.31 + '@smithy/util-endpoints': 2.1.7 + '@smithy/util-middleware': 3.0.11 + '@smithy/util-retry': 3.0.11 + '@smithy/util-utf8': 3.0.0 + '@smithy/util-waiter': 3.2.0 + tslib: 2.6.2 + transitivePeerDependencies: + - aws-crt + dev: false + /@aws-sdk/client-sqs@3.454.0: resolution: {integrity: sha512-eBviLavFxmXAbqL/wPlVqYnmS/hYUPj63ilQvFuj8zM3WYy0DX7GgvYXz5AUWswGsEk/4F88QFjlBM7N5miepw==} engines: {node: '>=14.0.0'} @@ -2433,6 +2527,56 @@ packages: - aws-crt dev: false + /@aws-sdk/client-sso-oidc@3.716.0(@aws-sdk/client-sts@3.716.0): + resolution: {integrity: sha512-lA4IB9FzR2KjH7EVCo+mHGFKqdViVyeBQEIX9oVratL/l7P0bMS1fMwgfHOc3ACazqNxBxDES7x08ZCp32y6Lw==} + engines: {node: '>=16.0.0'} + peerDependencies: + '@aws-sdk/client-sts': ^3.716.0 + dependencies: + '@aws-crypto/sha256-browser': 5.2.0 + '@aws-crypto/sha256-js': 5.2.0 + '@aws-sdk/client-sts': 3.716.0 + '@aws-sdk/core': 3.716.0 + '@aws-sdk/credential-provider-node': 3.716.0(@aws-sdk/client-sso-oidc@3.716.0)(@aws-sdk/client-sts@3.716.0) + '@aws-sdk/middleware-host-header': 3.714.0 + '@aws-sdk/middleware-logger': 3.714.0 + '@aws-sdk/middleware-recursion-detection': 3.714.0 + '@aws-sdk/middleware-user-agent': 3.716.0 + '@aws-sdk/region-config-resolver': 3.714.0 + '@aws-sdk/types': 3.714.0 + '@aws-sdk/util-endpoints': 3.714.0 + '@aws-sdk/util-user-agent-browser': 3.714.0 + '@aws-sdk/util-user-agent-node': 3.716.0 + '@smithy/config-resolver': 3.0.13 + '@smithy/core': 2.5.5 + '@smithy/fetch-http-handler': 4.1.2 + '@smithy/hash-node': 3.0.11 + '@smithy/invalid-dependency': 3.0.11 + '@smithy/middleware-content-length': 3.0.13 + '@smithy/middleware-endpoint': 3.2.6 + '@smithy/middleware-retry': 3.0.31 + '@smithy/middleware-serde': 3.0.11 + '@smithy/middleware-stack': 3.0.11 + '@smithy/node-config-provider': 3.1.12 + '@smithy/node-http-handler': 3.3.2 + '@smithy/protocol-http': 4.1.8 + '@smithy/smithy-client': 3.5.1 + '@smithy/types': 3.7.2 + '@smithy/url-parser': 3.0.11 + '@smithy/util-base64': 3.0.0 + '@smithy/util-body-length-browser': 3.0.0 + '@smithy/util-body-length-node': 3.0.0 + '@smithy/util-defaults-mode-browser': 3.0.31 + '@smithy/util-defaults-mode-node': 3.0.31 + '@smithy/util-endpoints': 2.1.7 + '@smithy/util-middleware': 3.0.11 + '@smithy/util-retry': 3.0.11 + '@smithy/util-utf8': 3.0.0 + tslib: 2.6.2 + transitivePeerDependencies: + - aws-crt + dev: false + /@aws-sdk/client-sso@3.451.0: resolution: {integrity: sha512-KkYSke3Pdv3MfVH/5fT528+MKjMyPKlcLcd4zQb0x6/7Bl7EHrPh1JZYjzPLHelb+UY5X0qN8+cb8iSu1eiwIQ==} engines: {node: '>=14.0.0'} @@ -2477,6 +2621,52 @@ packages: - aws-crt dev: false + /@aws-sdk/client-sso@3.716.0: + resolution: {integrity: sha512-5Nb0jJXce2TclbjG7WVPufwhgV1TRydz1QnsuBtKU0AdViEpr787YrZhPpGnNIM1Dx+R1H/tmAHZnOoohS6D8g==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-crypto/sha256-browser': 5.2.0 + '@aws-crypto/sha256-js': 5.2.0 + '@aws-sdk/core': 3.716.0 + '@aws-sdk/middleware-host-header': 3.714.0 + '@aws-sdk/middleware-logger': 3.714.0 + '@aws-sdk/middleware-recursion-detection': 3.714.0 + '@aws-sdk/middleware-user-agent': 3.716.0 + '@aws-sdk/region-config-resolver': 3.714.0 + '@aws-sdk/types': 3.714.0 + '@aws-sdk/util-endpoints': 3.714.0 + '@aws-sdk/util-user-agent-browser': 3.714.0 + '@aws-sdk/util-user-agent-node': 3.716.0 + '@smithy/config-resolver': 3.0.13 + '@smithy/core': 2.5.5 + '@smithy/fetch-http-handler': 4.1.2 + '@smithy/hash-node': 3.0.11 + '@smithy/invalid-dependency': 3.0.11 + '@smithy/middleware-content-length': 3.0.13 + '@smithy/middleware-endpoint': 3.2.6 + '@smithy/middleware-retry': 3.0.31 + '@smithy/middleware-serde': 3.0.11 + '@smithy/middleware-stack': 3.0.11 + '@smithy/node-config-provider': 3.1.12 + '@smithy/node-http-handler': 3.3.2 + '@smithy/protocol-http': 4.1.8 + '@smithy/smithy-client': 3.5.1 + '@smithy/types': 3.7.2 + '@smithy/url-parser': 3.0.11 + '@smithy/util-base64': 3.0.0 + '@smithy/util-body-length-browser': 3.0.0 + '@smithy/util-body-length-node': 3.0.0 + '@smithy/util-defaults-mode-browser': 3.0.31 + '@smithy/util-defaults-mode-node': 3.0.31 + '@smithy/util-endpoints': 2.1.7 + '@smithy/util-middleware': 3.0.11 + '@smithy/util-retry': 3.0.11 + '@smithy/util-utf8': 3.0.0 + tslib: 2.6.2 + transitivePeerDependencies: + - aws-crt + dev: false + /@aws-sdk/client-sts@3.454.0: resolution: {integrity: sha512-0fDvr8WeB6IYO8BUCzcivWmahgGl/zDbaYfakzGnt4mrl5ztYaXE875WI6b7+oFcKMRvN+KLvwu5TtyFuNY+GQ==} engines: {node: '>=14.0.0'} @@ -2525,6 +2715,54 @@ packages: - aws-crt dev: false + /@aws-sdk/client-sts@3.716.0: + resolution: {integrity: sha512-i4SVNsrdXudp8T4bkm7Fi3YWlRnvXCSwvNDqf6nLqSJxqr4CN3VlBELueDyjBK7TAt453/qSif+eNx+bHmwo4Q==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-crypto/sha256-browser': 5.2.0 + '@aws-crypto/sha256-js': 5.2.0 + '@aws-sdk/client-sso-oidc': 3.716.0(@aws-sdk/client-sts@3.716.0) + '@aws-sdk/core': 3.716.0 + '@aws-sdk/credential-provider-node': 3.716.0(@aws-sdk/client-sso-oidc@3.716.0)(@aws-sdk/client-sts@3.716.0) + '@aws-sdk/middleware-host-header': 3.714.0 + '@aws-sdk/middleware-logger': 3.714.0 + '@aws-sdk/middleware-recursion-detection': 3.714.0 + '@aws-sdk/middleware-user-agent': 3.716.0 + '@aws-sdk/region-config-resolver': 3.714.0 + '@aws-sdk/types': 3.714.0 + '@aws-sdk/util-endpoints': 3.714.0 + '@aws-sdk/util-user-agent-browser': 3.714.0 + '@aws-sdk/util-user-agent-node': 3.716.0 + '@smithy/config-resolver': 3.0.13 + '@smithy/core': 2.5.5 + '@smithy/fetch-http-handler': 4.1.2 + '@smithy/hash-node': 3.0.11 + '@smithy/invalid-dependency': 3.0.11 + '@smithy/middleware-content-length': 3.0.13 + '@smithy/middleware-endpoint': 3.2.6 + '@smithy/middleware-retry': 3.0.31 + '@smithy/middleware-serde': 3.0.11 + '@smithy/middleware-stack': 3.0.11 + '@smithy/node-config-provider': 3.1.12 + '@smithy/node-http-handler': 3.3.2 + '@smithy/protocol-http': 4.1.8 + '@smithy/smithy-client': 3.5.1 + '@smithy/types': 3.7.2 + '@smithy/url-parser': 3.0.11 + '@smithy/util-base64': 3.0.0 + '@smithy/util-body-length-browser': 3.0.0 + '@smithy/util-body-length-node': 3.0.0 + '@smithy/util-defaults-mode-browser': 3.0.31 + '@smithy/util-defaults-mode-node': 3.0.31 + '@smithy/util-endpoints': 2.1.7 + '@smithy/util-middleware': 3.0.11 + '@smithy/util-retry': 3.0.11 + '@smithy/util-utf8': 3.0.0 + tslib: 2.6.2 + transitivePeerDependencies: + - aws-crt + dev: false + /@aws-sdk/core@3.451.0: resolution: {integrity: sha512-SamWW2zHEf1ZKe3j1w0Piauryl8BQIlej0TBS18A4ACzhjhWXhCs13bO1S88LvPR5mBFXok3XOT6zPOnKDFktw==} engines: {node: '>=14.0.0'} @@ -2533,6 +2771,23 @@ packages: tslib: 2.6.2 dev: false + /@aws-sdk/core@3.716.0: + resolution: {integrity: sha512-5DkUiTrbyzO8/W4g7UFEqRFpuhgizayHI/Zbh0wtFMcot8801nJV+MP/YMhdjimlvAr/OqYB08FbGsPyWppMTw==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-sdk/types': 3.714.0 + '@smithy/core': 2.5.5 + '@smithy/node-config-provider': 3.1.12 + '@smithy/property-provider': 3.1.11 + '@smithy/protocol-http': 4.1.8 + '@smithy/signature-v4': 4.2.4 + '@smithy/smithy-client': 3.5.1 + '@smithy/types': 3.7.2 + '@smithy/util-middleware': 3.0.11 + fast-xml-parser: 4.4.1 + tslib: 2.6.2 + dev: false + /@aws-sdk/credential-provider-env@3.451.0: resolution: {integrity: sha512-9dAav7DcRgaF7xCJEQR5ER9ErXxnu/tdnVJ+UPmb1NPeIZdESv1A3lxFDEq1Fs8c4/lzAj9BpshGyJVIZwZDKg==} engines: {node: '>=14.0.0'} @@ -2543,6 +2798,33 @@ packages: tslib: 2.6.2 dev: false + /@aws-sdk/credential-provider-env@3.716.0: + resolution: {integrity: sha512-JI2KQUnn2arICwP9F3CnqP1W3nAbm4+meQg/yOhp9X0DMzQiHrHRd4HIrK2vyVgi2/6hGhONY5uLF26yRTA7nQ==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-sdk/core': 3.716.0 + '@aws-sdk/types': 3.714.0 + '@smithy/property-provider': 3.1.11 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + + /@aws-sdk/credential-provider-http@3.716.0: + resolution: {integrity: sha512-CZ04pl2z7igQPysQyH2xKZHM3fLwkemxQbKOlje3TmiS1NwXvcKvERhp9PE/H23kOL7beTM19NMRog/Fka/rlw==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-sdk/core': 3.716.0 + '@aws-sdk/types': 3.714.0 + '@smithy/fetch-http-handler': 4.1.2 + '@smithy/node-http-handler': 3.3.2 + '@smithy/property-provider': 3.1.11 + '@smithy/protocol-http': 4.1.8 + '@smithy/smithy-client': 3.5.1 + '@smithy/types': 3.7.2 + '@smithy/util-stream': 3.3.2 + tslib: 2.6.2 + dev: false + /@aws-sdk/credential-provider-ini@3.451.0: resolution: {integrity: sha512-TySt64Ci5/ZbqFw1F9Z0FIGvYx5JSC9e6gqDnizIYd8eMnn8wFRUscRrD7pIHKfrhvVKN5h0GdYovmMO/FMCBw==} engines: {node: '>=14.0.0'} @@ -2561,6 +2843,30 @@ packages: - aws-crt dev: false + /@aws-sdk/credential-provider-ini@3.716.0(@aws-sdk/client-sso-oidc@3.716.0)(@aws-sdk/client-sts@3.716.0): + resolution: {integrity: sha512-P37We2GtZvdROxiwP0zrpEL81/HuYK1qlYxp5VCj3uV+G4mG8UQN2gMIU/baYrpOQqa0h81RfyQGRFUjVaDVqw==} + engines: {node: '>=16.0.0'} + peerDependencies: + '@aws-sdk/client-sts': ^3.716.0 + dependencies: + '@aws-sdk/client-sts': 3.716.0 + '@aws-sdk/core': 3.716.0 + '@aws-sdk/credential-provider-env': 3.716.0 + '@aws-sdk/credential-provider-http': 3.716.0 + '@aws-sdk/credential-provider-process': 3.716.0 + '@aws-sdk/credential-provider-sso': 3.716.0(@aws-sdk/client-sso-oidc@3.716.0) + '@aws-sdk/credential-provider-web-identity': 3.716.0(@aws-sdk/client-sts@3.716.0) + '@aws-sdk/types': 3.714.0 + '@smithy/credential-provider-imds': 3.2.8 + '@smithy/property-provider': 3.1.11 + '@smithy/shared-ini-file-loader': 3.1.12 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + transitivePeerDependencies: + - '@aws-sdk/client-sso-oidc' + - aws-crt + dev: false + /@aws-sdk/credential-provider-node@3.451.0: resolution: {integrity: sha512-AEwM1WPyxUdKrKyUsKyFqqRFGU70e4qlDyrtBxJnSU9NRLZI8tfEZ67bN7fHSxBUBODgDXpMSlSvJiBLh5/3pw==} engines: {node: '>=14.0.0'} @@ -2580,6 +2886,28 @@ packages: - aws-crt dev: false + /@aws-sdk/credential-provider-node@3.716.0(@aws-sdk/client-sso-oidc@3.716.0)(@aws-sdk/client-sts@3.716.0): + resolution: {integrity: sha512-FGQPK2uKfS53dVvoskN/s/t6m0Po24BGd1PzJdzHBFCOjxbZLM6+8mDMXeyi2hCLVVQOUcuW41kOgmJ0+zMbww==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-sdk/credential-provider-env': 3.716.0 + '@aws-sdk/credential-provider-http': 3.716.0 + '@aws-sdk/credential-provider-ini': 3.716.0(@aws-sdk/client-sso-oidc@3.716.0)(@aws-sdk/client-sts@3.716.0) + '@aws-sdk/credential-provider-process': 3.716.0 + '@aws-sdk/credential-provider-sso': 3.716.0(@aws-sdk/client-sso-oidc@3.716.0) + '@aws-sdk/credential-provider-web-identity': 3.716.0(@aws-sdk/client-sts@3.716.0) + '@aws-sdk/types': 3.714.0 + '@smithy/credential-provider-imds': 3.2.8 + '@smithy/property-provider': 3.1.11 + '@smithy/shared-ini-file-loader': 3.1.12 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + transitivePeerDependencies: + - '@aws-sdk/client-sso-oidc' + - '@aws-sdk/client-sts' + - aws-crt + dev: false + /@aws-sdk/credential-provider-process@3.451.0: resolution: {integrity: sha512-HQywSdKeD5PErcLLnZfSyCJO+6T+ZyzF+Lm/QgscSC+CbSUSIPi//s15qhBRVely/3KBV6AywxwNH+5eYgt4lQ==} engines: {node: '>=14.0.0'} @@ -2591,6 +2919,18 @@ packages: tslib: 2.6.2 dev: false + /@aws-sdk/credential-provider-process@3.716.0: + resolution: {integrity: sha512-0spcu2MWVVHSTHH3WE2E//ttUJPwXRM3BCp+WyI41xLzpNu1Fd8zjOrDpEo0SnGUzsSiRTIJWgkuu/tqv9NJ2A==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-sdk/core': 3.716.0 + '@aws-sdk/types': 3.714.0 + '@smithy/property-provider': 3.1.11 + '@smithy/shared-ini-file-loader': 3.1.12 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@aws-sdk/credential-provider-sso@3.451.0: resolution: {integrity: sha512-Usm/N51+unOt8ID4HnQzxIjUJDrkAQ1vyTOC0gSEEJ7h64NSSPGD5yhN7il5WcErtRd3EEtT1a8/GTC5TdBctg==} engines: {node: '>=14.0.0'} @@ -2606,6 +2946,23 @@ packages: - aws-crt dev: false + /@aws-sdk/credential-provider-sso@3.716.0(@aws-sdk/client-sso-oidc@3.716.0): + resolution: {integrity: sha512-J2IA3WuCpRGGoZm6VHZVFCnrxXP+41iUWb9Ct/1spljegTa1XjiaZ5Jf3+Ubj7WKiyvP9/dgz1L0bu2bYEjliw==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-sdk/client-sso': 3.716.0 + '@aws-sdk/core': 3.716.0 + '@aws-sdk/token-providers': 3.714.0(@aws-sdk/client-sso-oidc@3.716.0) + '@aws-sdk/types': 3.714.0 + '@smithy/property-provider': 3.1.11 + '@smithy/shared-ini-file-loader': 3.1.12 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + transitivePeerDependencies: + - '@aws-sdk/client-sso-oidc' + - aws-crt + dev: false + /@aws-sdk/credential-provider-web-identity@3.451.0: resolution: {integrity: sha512-Xtg3Qw65EfDjWNG7o2xD6sEmumPfsy3WDGjk2phEzVg8s7hcZGxf5wYwe6UY7RJvlEKrU0rFA+AMn6Hfj5oOzg==} engines: {node: '>=14.0.0'} @@ -2616,6 +2973,20 @@ packages: tslib: 2.6.2 dev: false + /@aws-sdk/credential-provider-web-identity@3.716.0(@aws-sdk/client-sts@3.716.0): + resolution: {integrity: sha512-vzgpWKs2gGXZGdbMKRFrMW4PqEFWkGvwWH2T7ZwQv9m+8lQ7P4Dk2uimqu0f37HZAbpn8HFMqRh4CaySjU354A==} + engines: {node: '>=16.0.0'} + peerDependencies: + '@aws-sdk/client-sts': ^3.716.0 + dependencies: + '@aws-sdk/client-sts': 3.716.0 + '@aws-sdk/core': 3.716.0 + '@aws-sdk/types': 3.714.0 + '@smithy/property-provider': 3.1.11 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@aws-sdk/middleware-host-header@3.451.0: resolution: {integrity: sha512-j8a5jAfhWmsK99i2k8oR8zzQgXrsJtgrLxc3js6U+525mcZytoiDndkWTmD5fjJ1byU1U2E5TaPq+QJeDip05Q==} engines: {node: '>=14.0.0'} @@ -2626,6 +2997,16 @@ packages: tslib: 2.6.2 dev: false + /@aws-sdk/middleware-host-header@3.714.0: + resolution: {integrity: sha512-6l68kjNrh5QC8FGX3I3geBDavWN5Tg1RLHJ2HLA8ByGBtJyCwnz3hEkKfaxn0bBx0hF9DzbfjEOUF6cDqy2Kjg==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-sdk/types': 3.714.0 + '@smithy/protocol-http': 4.1.8 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@aws-sdk/middleware-logger@3.451.0: resolution: {integrity: sha512-0kHrYEyVeB2QBfP6TfbI240aRtatLZtcErJbhpiNUb+CQPgEL3crIjgVE8yYiJumZ7f0jyjo8HLPkwD1/2APaw==} engines: {node: '>=14.0.0'} @@ -2635,6 +3016,15 @@ packages: tslib: 2.6.2 dev: false + /@aws-sdk/middleware-logger@3.714.0: + resolution: {integrity: sha512-RkqHlMvQWUaRklU1bMfUuBvdWwxgUtEqpADaHXlGVj3vtEY2UgBjy+57CveC4MByqKIunNvVHBBbjrGVtwY7Lg==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-sdk/types': 3.714.0 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@aws-sdk/middleware-recursion-detection@3.451.0: resolution: {integrity: sha512-J6jL6gJ7orjHGM70KDRcCP7so/J2SnkN4vZ9YRLTeeZY6zvBuHDjX8GCIgSqPn/nXFXckZO8XSnA7u6+3TAT0w==} engines: {node: '>=14.0.0'} @@ -2645,6 +3035,16 @@ packages: tslib: 2.6.2 dev: false + /@aws-sdk/middleware-recursion-detection@3.714.0: + resolution: {integrity: sha512-AVU5ixnh93nqtsfgNc284oXsXaadyHGPHpql/jwgaaqQfEXjS/1/j3j9E/vpacfTTz2Vzo7hAOjnvrOXSEVDaA==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-sdk/types': 3.714.0 + '@smithy/protocol-http': 4.1.8 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@aws-sdk/middleware-sdk-sqs@3.451.0: resolution: {integrity: sha512-GXpFSc9Ji4IAT/OaTkmnDrxzZrrAsJctUAC9vihpgGDof79A1Oz4R+r2uBMTKGxCIFkqyYW5Se7y2ijjTNa3ZA==} engines: {node: '>=14.0.0'} @@ -2690,6 +3090,19 @@ packages: tslib: 2.6.2 dev: false + /@aws-sdk/middleware-user-agent@3.716.0: + resolution: {integrity: sha512-FpAtT6nNKrYdkDZndutEraiRMf+TgDzAGvniqRtZ/YTPA+gIsWrsn+TwMKINR81lFC3nQfb9deS5CFtxd021Ew==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-sdk/core': 3.716.0 + '@aws-sdk/types': 3.714.0 + '@aws-sdk/util-endpoints': 3.714.0 + '@smithy/core': 2.5.5 + '@smithy/protocol-http': 4.1.8 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@aws-sdk/region-config-resolver@3.451.0: resolution: {integrity: sha512-3iMf4OwzrFb4tAAmoROXaiORUk2FvSejnHIw/XHvf/jjR4EqGGF95NZP/n/MeFZMizJWVssrwS412GmoEyoqhg==} engines: {node: '>=14.0.0'} @@ -2701,6 +3114,18 @@ packages: tslib: 2.6.2 dev: false + /@aws-sdk/region-config-resolver@3.714.0: + resolution: {integrity: sha512-HJzsQxgMOAzZrbf/YIqEx30or4tZK1oNAk6Wm6xecUQx+23JXIaePRu1YFUOLBBERQ4QBPpISFurZWBMZ5ibAw==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-sdk/types': 3.714.0 + '@smithy/node-config-provider': 3.1.12 + '@smithy/types': 3.7.2 + '@smithy/util-config-provider': 3.0.0 + '@smithy/util-middleware': 3.0.11 + tslib: 2.6.2 + dev: false + /@aws-sdk/token-providers@3.451.0: resolution: {integrity: sha512-ij1L5iUbn6CwxVOT1PG4NFjsrsKN9c4N1YEM0lkl6DwmaNOscjLKGSNyj9M118vSWsOs1ZDbTwtj++h0O/BWrQ==} engines: {node: '>=14.0.0'} @@ -2746,6 +3171,20 @@ packages: - aws-crt dev: false + /@aws-sdk/token-providers@3.714.0(@aws-sdk/client-sso-oidc@3.716.0): + resolution: {integrity: sha512-vKN064aLE3kl+Zl16Ony3jltHnMddMBT7JRkP1L+lLywhA0PcAKxpdvComul/sTBWnbnwLnaS5NsDUhcWySH8A==} + engines: {node: '>=16.0.0'} + peerDependencies: + '@aws-sdk/client-sso-oidc': ^3.714.0 + dependencies: + '@aws-sdk/client-sso-oidc': 3.716.0(@aws-sdk/client-sts@3.716.0) + '@aws-sdk/types': 3.714.0 + '@smithy/property-provider': 3.1.11 + '@smithy/shared-ini-file-loader': 3.1.12 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@aws-sdk/types@3.451.0: resolution: {integrity: sha512-rhK+qeYwCIs+laJfWCcrYEjay2FR/9VABZJ2NRM89jV/fKqGVQR52E5DQqrI+oEIL5JHMhhnr4N4fyECMS35lw==} engines: {node: '>=14.0.0'} @@ -2754,6 +3193,14 @@ packages: tslib: 2.6.2 dev: false + /@aws-sdk/types@3.714.0: + resolution: {integrity: sha512-ZjpP2gYbSFlxxaUDa1Il5AVvfggvUPbjzzB/l3q0gIE5Thd6xKW+yzEpt2mLZ5s5UaYSABZbF94g8NUOF4CVGA==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@aws-sdk/util-endpoints@3.451.0: resolution: {integrity: sha512-giqLGBTnRIcKkDqwU7+GQhKbtJ5Ku35cjGQIfMyOga6pwTBUbaK0xW1Sdd8sBQ1GhApscnChzI9o/R9x0368vw==} engines: {node: '>=14.0.0'} @@ -2763,6 +3210,16 @@ packages: tslib: 2.6.2 dev: false + /@aws-sdk/util-endpoints@3.714.0: + resolution: {integrity: sha512-Xv+Z2lhe7w7ZZRsgBwBMZgGTVmS+dkkj2S13uNHAx9lhB5ovM8PhK5G/j28xYf6vIibeuHkRAbb7/ozdZIGR+A==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-sdk/types': 3.714.0 + '@smithy/types': 3.7.2 + '@smithy/util-endpoints': 2.1.7 + tslib: 2.6.2 + dev: false + /@aws-sdk/util-locate-window@3.310.0: resolution: {integrity: sha512-qo2t/vBTnoXpjKxlsC2e1gBrRm80M3bId27r0BRB2VniSSe7bL1mmzM+/HFtujm0iAxtPM+aLEflLJlJeDPg0w==} engines: {node: '>=14.0.0'} @@ -2779,6 +3236,15 @@ packages: tslib: 2.6.2 dev: false + /@aws-sdk/util-user-agent-browser@3.714.0: + resolution: {integrity: sha512-OdJJ03cP9/MgIVToPJPCPUImbpZzTcwdIgbXC0tUQPJhbD7b7cB4LdnkhNHko+MptpOrCq4CPY/33EpOjRdofw==} + dependencies: + '@aws-sdk/types': 3.714.0 + '@smithy/types': 3.7.2 + bowser: 2.11.0 + tslib: 2.6.2 + dev: false + /@aws-sdk/util-user-agent-node@3.451.0: resolution: {integrity: sha512-TBzm6P+ql4mkGFAjPlO1CI+w3yUT+NulaiALjl/jNX/nnUp6HsJsVxJf4nVFQTG5KRV0iqMypcs7I3KIhH+LmA==} engines: {node: '>=14.0.0'} @@ -2794,6 +3260,22 @@ packages: tslib: 2.6.2 dev: false + /@aws-sdk/util-user-agent-node@3.716.0: + resolution: {integrity: sha512-3PqaXmQbxrtHKAsPCdp7kn5FrQktj8j3YyuNsqFZ8rWZeEQ88GWlsvE61PTsr2peYCKzpFqYVddef2x1axHU0w==} + engines: {node: '>=16.0.0'} + peerDependencies: + aws-crt: '>=1.0.0' + peerDependenciesMeta: + aws-crt: + optional: true + dependencies: + '@aws-sdk/middleware-user-agent': 3.716.0 + '@aws-sdk/types': 3.714.0 + '@smithy/node-config-provider': 3.1.12 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@aws-sdk/util-utf8-browser@3.259.0: resolution: {integrity: sha512-UvFa/vR+e19XookZF8RzFZBrw2EUkQWxiBW0yYQAhvk3C+QVGl0H3ouca8LDBlBfQKXwmW3huo/59H8rwb1wJw==} dependencies: @@ -14527,6 +15009,14 @@ packages: tslib: 2.6.2 dev: false + /@smithy/abort-controller@3.1.9: + resolution: {integrity: sha512-yiW0WI30zj8ZKoSYNx90no7ugVn3khlyH/z5W8qtKBtVE6awRALbhSG+2SAHA1r6bO/6M9utxYKVZ3PCJ1rWxw==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/config-resolver@2.0.19: resolution: {integrity: sha512-JsghnQ5zjWmjEVY8TFOulLdEOCj09SjRLugrHlkPZTIBBm7PQitCFVLThbsKPZQOP7N3ME1DU1nKUc1UaVnBog==} engines: {node: '>=14.0.0'} @@ -14538,6 +15028,31 @@ packages: tslib: 2.6.2 dev: false + /@smithy/config-resolver@3.0.13: + resolution: {integrity: sha512-Gr/qwzyPaTL1tZcq8WQyHhTZREER5R1Wytmz4WnVGL4onA3dNk6Btll55c8Vr58pLdvWZmtG8oZxJTw3t3q7Jg==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/node-config-provider': 3.1.12 + '@smithy/types': 3.7.2 + '@smithy/util-config-provider': 3.0.0 + '@smithy/util-middleware': 3.0.11 + tslib: 2.6.2 + dev: false + + /@smithy/core@2.5.5: + resolution: {integrity: sha512-G8G/sDDhXA7o0bOvkc7bgai6POuSld/+XhNnWAbpQTpLv2OZPvyqQ58tLPPlz0bSNsXktldDDREIv1LczFeNEw==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/middleware-serde': 3.0.11 + '@smithy/protocol-http': 4.1.8 + '@smithy/types': 3.7.2 + '@smithy/util-body-length-browser': 3.0.0 + '@smithy/util-middleware': 3.0.11 + '@smithy/util-stream': 3.3.2 + '@smithy/util-utf8': 3.0.0 + tslib: 2.6.2 + dev: false + /@smithy/credential-provider-imds@2.1.2: resolution: {integrity: sha512-Y62jBWdoLPSYjr9fFvJf+KwTa1EunjVr6NryTEWCnwIY93OJxwV4t0qxjwdPl/XMsUkq79ppNJSEQN6Ohnhxjw==} engines: {node: '>=14.0.0'} @@ -14549,6 +15064,17 @@ packages: tslib: 2.6.2 dev: false + /@smithy/credential-provider-imds@3.2.8: + resolution: {integrity: sha512-ZCY2yD0BY+K9iMXkkbnjo+08T2h8/34oHd0Jmh6BZUSZwaaGlGCyBT/3wnS7u7Xl33/EEfN4B6nQr3Gx5bYxgw==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/node-config-provider': 3.1.12 + '@smithy/property-provider': 3.1.11 + '@smithy/types': 3.7.2 + '@smithy/url-parser': 3.0.11 + tslib: 2.6.2 + dev: false + /@smithy/eventstream-codec@2.0.14: resolution: {integrity: sha512-g/OU/MeWGfHDygoXgMWfG/Xb0QqDnAGcM9t2FRrVAhleXYRddGOEnfanR5cmHgB9ue52MJsyorqFjckzXsylaA==} dependencies: @@ -14568,6 +15094,16 @@ packages: tslib: 2.6.2 dev: false + /@smithy/fetch-http-handler@4.1.2: + resolution: {integrity: sha512-R7rU7Ae3ItU4rC0c5mB2sP5mJNbCfoDc8I5XlYjIZnquyUwec7fEo78F6DA3SmgJgkU1qTMcZJuGblxZsl10ZA==} + dependencies: + '@smithy/protocol-http': 4.1.8 + '@smithy/querystring-builder': 3.0.11 + '@smithy/types': 3.7.2 + '@smithy/util-base64': 3.0.0 + tslib: 2.6.2 + dev: false + /@smithy/hash-node@2.0.16: resolution: {integrity: sha512-Wbi9A0PacMYUOwjAulQP90Wl3mQ6NDwnyrZQzFjDz+UzjXOSyQMgBrTkUBz+pVoYVlX3DUu24gWMZBcit+wOGg==} engines: {node: '>=14.0.0'} @@ -14578,6 +15114,16 @@ packages: tslib: 2.6.2 dev: false + /@smithy/hash-node@3.0.11: + resolution: {integrity: sha512-emP23rwYyZhQBvklqTtwetkQlqbNYirDiEEwXl2v0GYWMnCzxst7ZaRAnWuy28njp5kAH54lvkdG37MblZzaHA==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/types': 3.7.2 + '@smithy/util-buffer-from': 3.0.0 + '@smithy/util-utf8': 3.0.0 + tslib: 2.6.2 + dev: false + /@smithy/invalid-dependency@2.0.14: resolution: {integrity: sha512-d8ohpwZo9RzTpGlAfsWtfm1SHBSU7+N4iuZ6MzR10xDTujJJWtmXYHK1uzcr7rggbpUTaWyHpPFgnf91q0EFqQ==} dependencies: @@ -14585,6 +15131,13 @@ packages: tslib: 2.6.2 dev: false + /@smithy/invalid-dependency@3.0.11: + resolution: {integrity: sha512-NuQmVPEJjUX6c+UELyVz8kUx8Q539EDeNwbRyu4IIF8MeV7hUtq1FB3SHVyki2u++5XLMFqngeMKk7ccspnNyQ==} + dependencies: + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/is-array-buffer@2.0.0: resolution: {integrity: sha512-z3PjFjMyZNI98JFRJi/U0nGoLWMSJlDjAW4QUX2WNZLas5C0CmVV6LJ01JI0k90l7FvpmixjWxPFmENSClQ7ug==} engines: {node: '>=14.0.0'} @@ -14592,6 +15145,13 @@ packages: tslib: 2.6.2 dev: false + /@smithy/is-array-buffer@3.0.0: + resolution: {integrity: sha512-+Fsu6Q6C4RSJiy81Y8eApjEB5gVtM+oFKTffg+jSuwtvomJJrhUJBu2zS8wjXSgH/g1MKEWrzyChTBe6clb5FQ==} + engines: {node: '>=16.0.0'} + dependencies: + tslib: 2.6.2 + dev: false + /@smithy/md5-js@2.0.16: resolution: {integrity: sha512-YhWt9aKl+EMSNXyUTUo7I01WHf3HcCkPu/Hl2QmTNwrHT49eWaY7hptAMaERZuHFH0V5xHgPKgKZo2I93DFtgQ==} dependencies: @@ -14609,6 +15169,15 @@ packages: tslib: 2.6.2 dev: false + /@smithy/middleware-content-length@3.0.13: + resolution: {integrity: sha512-zfMhzojhFpIX3P5ug7jxTjfUcIPcGjcQYzB9t+rv0g1TX7B0QdwONW+ATouaLoD7h7LOw/ZlXfkq4xJ/g2TrIw==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/protocol-http': 4.1.8 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/middleware-endpoint@2.2.1: resolution: {integrity: sha512-dVDS7HNJl/wb0lpByXor6whqDbb1YlLoaoWYoelyYzLHioXOE7y/0iDwJWtDcN36/tVCw9EPBFZ3aans84jLpg==} engines: {node: '>=14.0.0'} @@ -14622,6 +15191,20 @@ packages: tslib: 2.6.2 dev: false + /@smithy/middleware-endpoint@3.2.6: + resolution: {integrity: sha512-WAqzyulvvSKrT5c6VrQelgNVNNO7BlTQW9Z+s9tcG6G5CaBS1YBpPtT3VuhXLQbewSiGi7oXQROwpw26EG9PLQ==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/core': 2.5.5 + '@smithy/middleware-serde': 3.0.11 + '@smithy/node-config-provider': 3.1.12 + '@smithy/shared-ini-file-loader': 3.1.12 + '@smithy/types': 3.7.2 + '@smithy/url-parser': 3.0.11 + '@smithy/util-middleware': 3.0.11 + tslib: 2.6.2 + dev: false + /@smithy/middleware-retry@2.0.21: resolution: {integrity: sha512-EZS1EXv1k6IJX6hyu/0yNQuPcPaXwG8SWljQHYueyRbOxmqYgoWMWPtfZj0xRRQ4YtLawQSpBgAeiJltq8/MPw==} engines: {node: '>=14.0.0'} @@ -14636,6 +15219,21 @@ packages: uuid: 8.3.2 dev: false + /@smithy/middleware-retry@3.0.31: + resolution: {integrity: sha512-yq9wawrJLYHAYFpChLujxRN4My+SiKXvZk9Ml/CvTdRSA8ew+hvuR5LT+mjSlSBv3c4XJrkN8CWegkBaeD0Vrg==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/node-config-provider': 3.1.12 + '@smithy/protocol-http': 4.1.8 + '@smithy/service-error-classification': 3.0.11 + '@smithy/smithy-client': 3.5.1 + '@smithy/types': 3.7.2 + '@smithy/util-middleware': 3.0.11 + '@smithy/util-retry': 3.0.11 + tslib: 2.6.2 + uuid: 9.0.1 + dev: false + /@smithy/middleware-serde@2.0.14: resolution: {integrity: sha512-hFi3FqoYWDntCYA2IGY6gJ6FKjq2gye+1tfxF2HnIJB5uW8y2DhpRNBSUMoqP+qvYzRqZ6ntv4kgbG+o3pX57g==} engines: {node: '>=14.0.0'} @@ -14644,6 +15242,14 @@ packages: tslib: 2.6.2 dev: false + /@smithy/middleware-serde@3.0.11: + resolution: {integrity: sha512-KzPAeySp/fOoQA82TpnwItvX8BBURecpx6ZMu75EZDkAcnPtO6vf7q4aH5QHs/F1s3/snQaSFbbUMcFFZ086Mw==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/middleware-stack@2.0.8: resolution: {integrity: sha512-7/N59j0zWqVEKExJcA14MrLDZ/IeN+d6nbkN8ucs+eURyaDUXWYlZrQmMOd/TyptcQv0+RDlgag/zSTTV62y/Q==} engines: {node: '>=14.0.0'} @@ -14652,6 +15258,14 @@ packages: tslib: 2.6.2 dev: false + /@smithy/middleware-stack@3.0.11: + resolution: {integrity: sha512-1HGo9a6/ikgOMrTrWL/WiN9N8GSVYpuRQO5kjstAq4CvV59bjqnh7TbdXGQ4vxLD3xlSjfBjq5t1SOELePsLnA==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/node-config-provider@2.1.6: resolution: {integrity: sha512-HLqTs6O78m3M3z1cPLFxddxhEPv5MkVatfPuxoVO3A+cHZanNd/H5I6btcdHy6N2CB1MJ/lihJC92h30SESsBA==} engines: {node: '>=14.0.0'} @@ -14662,6 +15276,16 @@ packages: tslib: 2.6.2 dev: false + /@smithy/node-config-provider@3.1.12: + resolution: {integrity: sha512-O9LVEu5J/u/FuNlZs+L7Ikn3lz7VB9hb0GtPT9MQeiBmtK8RSY3ULmsZgXhe6VAlgTw0YO+paQx4p8xdbs43vQ==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/property-provider': 3.1.11 + '@smithy/shared-ini-file-loader': 3.1.12 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/node-http-handler@2.1.10: resolution: {integrity: sha512-lkALAwtN6odygIM4nB8aHDahINM6WXXjNrZmWQAh0RSossySRT2qa31cFv0ZBuAYVWeprskRk13AFvvLmf1WLw==} engines: {node: '>=14.0.0'} @@ -14673,6 +15297,17 @@ packages: tslib: 2.6.2 dev: false + /@smithy/node-http-handler@3.3.2: + resolution: {integrity: sha512-t4ng1DAd527vlxvOfKFYEe6/QFBcsj7WpNlWTyjorwXXcKw3XlltBGbyHfSJ24QT84nF+agDha9tNYpzmSRZPA==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/abort-controller': 3.1.9 + '@smithy/protocol-http': 4.1.8 + '@smithy/querystring-builder': 3.0.11 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/property-provider@2.0.15: resolution: {integrity: sha512-YbRFBn8oiiC3o1Kn3a4KjGa6k47rCM9++5W9cWqYn9WnkyH+hBWgfJAckuxpyA2Hq6Ys4eFrWzXq6fqHEw7iew==} engines: {node: '>=14.0.0'} @@ -14681,6 +15316,14 @@ packages: tslib: 2.6.2 dev: false + /@smithy/property-provider@3.1.11: + resolution: {integrity: sha512-I/+TMc4XTQ3QAjXfOcUWbSS073oOEAxgx4aZy8jHaf8JQnRkq2SZWw8+PfDtBvLUjcGMdxl+YwtzWe6i5uhL/A==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/protocol-http@3.0.10: resolution: {integrity: sha512-6+tjNk7rXW7YTeGo9qwxXj/2BFpJTe37kTj3EnZCoX/nH+NP/WLA7O83fz8XhkGqsaAhLUPo/bB12vvd47nsmg==} engines: {node: '>=14.0.0'} @@ -14689,6 +15332,14 @@ packages: tslib: 2.6.2 dev: false + /@smithy/protocol-http@4.1.8: + resolution: {integrity: sha512-hmgIAVyxw1LySOwkgMIUN0kjN8TG9Nc85LJeEmEE/cNEe2rkHDUWhnJf2gxcSRFLWsyqWsrZGw40ROjUogg+Iw==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/querystring-builder@2.0.14: resolution: {integrity: sha512-lQ4pm9vTv9nIhl5jt6uVMPludr6syE2FyJmHsIJJuOD7QPIJnrf9HhUGf1iHh9KJ4CUv21tpOU3X6s0rB6uJ0g==} engines: {node: '>=14.0.0'} @@ -14698,6 +15349,15 @@ packages: tslib: 2.6.2 dev: false + /@smithy/querystring-builder@3.0.11: + resolution: {integrity: sha512-u+5HV/9uJaeLj5XTb6+IEF/dokWWkEqJ0XiaRRogyREmKGUgZnNecLucADLdauWFKUNbQfulHFEZEdjwEBjXRg==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/types': 3.7.2 + '@smithy/util-uri-escape': 3.0.0 + tslib: 2.6.2 + dev: false + /@smithy/querystring-parser@2.0.14: resolution: {integrity: sha512-+cbtXWI9tNtQjlgQg3CA+pvL3zKTAxPnG3Pj6MP89CR3vi3QMmD0SOWoq84tqZDnJCxlsusbgIXk1ngMReXo+A==} engines: {node: '>=14.0.0'} @@ -14706,6 +15366,14 @@ packages: tslib: 2.6.2 dev: false + /@smithy/querystring-parser@3.0.11: + resolution: {integrity: sha512-Je3kFvCsFMnso1ilPwA7GtlbPaTixa3WwC+K21kmMZHsBEOZYQaqxcMqeFFoU7/slFjKDIpiiPydvdJm8Q/MCw==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/service-error-classification@2.0.7: resolution: {integrity: sha512-LLxgW12qGz8doYto15kZ4x1rHjtXl0BnCG6T6Wb8z2DI4PT9cJfOSvzbuLzy7+5I24PAepKgFeWHRd9GYy3Z9w==} engines: {node: '>=14.0.0'} @@ -14713,6 +15381,13 @@ packages: '@smithy/types': 2.6.0 dev: false + /@smithy/service-error-classification@3.0.11: + resolution: {integrity: sha512-QnYDPkyewrJzCyaeI2Rmp7pDwbUETe+hU8ADkXmgNusO1bgHBH7ovXJiYmba8t0fNfJx75fE8dlM6SEmZxheog==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/types': 3.7.2 + dev: false + /@smithy/shared-ini-file-loader@2.2.5: resolution: {integrity: sha512-LHA68Iu7SmNwfAVe8egmjDCy648/7iJR/fK1UnVw+iAOUJoEYhX2DLgVd5pWllqdDiRbQQzgaHLcRokM+UFR1w==} engines: {node: '>=14.0.0'} @@ -14721,6 +15396,14 @@ packages: tslib: 2.6.2 dev: false + /@smithy/shared-ini-file-loader@3.1.12: + resolution: {integrity: sha512-1xKSGI+U9KKdbG2qDvIR9dGrw3CNx+baqJfyr0igKEpjbHL5stsqAesYBzHChYHlelWtb87VnLWlhvfCz13H8Q==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/signature-v4@2.0.16: resolution: {integrity: sha512-ilLY85xS2kZZzTb83diQKYLIYALvart0KnBaKnIRnMBHAGEio5aHSlANQoxVn0VsonwmQ3CnWhnCT0sERD8uTg==} engines: {node: '>=14.0.0'} @@ -14735,6 +15418,20 @@ packages: tslib: 2.6.2 dev: false + /@smithy/signature-v4@4.2.4: + resolution: {integrity: sha512-5JWeMQYg81TgU4cG+OexAWdvDTs5JDdbEZx+Qr1iPbvo91QFGzjy0IkXAKaXUHqmKUJgSHK0ZxnCkgZpzkeNTA==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/is-array-buffer': 3.0.0 + '@smithy/protocol-http': 4.1.8 + '@smithy/types': 3.7.2 + '@smithy/util-hex-encoding': 3.0.0 + '@smithy/util-middleware': 3.0.11 + '@smithy/util-uri-escape': 3.0.0 + '@smithy/util-utf8': 3.0.0 + tslib: 2.6.2 + dev: false + /@smithy/smithy-client@2.1.16: resolution: {integrity: sha512-Lw67+yQSpLl4YkDLUzI2KgS8TXclXmbzSeOJUmRFS4ueT56B4pw3RZRF/SRzvgyxM/HxgkUan8oSHXCujPDafQ==} engines: {node: '>=14.0.0'} @@ -14745,6 +15442,19 @@ packages: tslib: 2.6.2 dev: false + /@smithy/smithy-client@3.5.1: + resolution: {integrity: sha512-PmjskH4Os1Eh3rd5vSsa5uVelZ4DRu+N5CBEgb9AT96hQSJGWSEb6pGxKV/PtKQSIp9ft3+KvnT8ViMKaguzgA==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/core': 2.5.5 + '@smithy/middleware-endpoint': 3.2.6 + '@smithy/middleware-stack': 3.0.11 + '@smithy/protocol-http': 4.1.8 + '@smithy/types': 3.7.2 + '@smithy/util-stream': 3.3.2 + tslib: 2.6.2 + dev: false + /@smithy/types@2.6.0: resolution: {integrity: sha512-PgqxJq2IcdMF9iAasxcqZqqoOXBHufEfmbEUdN1pmJrJltT42b0Sc8UiYSWWzKkciIp9/mZDpzYi4qYG1qqg6g==} engines: {node: '>=14.0.0'} @@ -14752,6 +15462,13 @@ packages: tslib: 2.6.2 dev: false + /@smithy/types@3.7.2: + resolution: {integrity: sha512-bNwBYYmN8Eh9RyjS1p2gW6MIhSO2rl7X9QeLM8iTdcGRP+eDiIWDt66c9IysCc22gefKszZv+ubV9qZc7hdESg==} + engines: {node: '>=16.0.0'} + dependencies: + tslib: 2.6.2 + dev: false + /@smithy/url-parser@2.0.14: resolution: {integrity: sha512-kbu17Y1AFXi5lNlySdDj7ZzmvupyWKCX/0jNZ8ffquRyGdbDZb+eBh0QnWqsSmnZa/ctyWaTf7n4l/pXLExrnw==} dependencies: @@ -14760,6 +15477,14 @@ packages: tslib: 2.6.2 dev: false + /@smithy/url-parser@3.0.11: + resolution: {integrity: sha512-TmlqXkSk8ZPhfc+SQutjmFr5FjC0av3GZP4B/10caK1SbRwe/v+Wzu/R6xEKxoNqL+8nY18s1byiy6HqPG37Aw==} + dependencies: + '@smithy/querystring-parser': 3.0.11 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/util-base64@2.0.1: resolution: {integrity: sha512-DlI6XFYDMsIVN+GH9JtcRp3j02JEVuWIn/QOZisVzpIAprdsxGveFed0bjbMRCqmIFe8uetn5rxzNrBtIGrPIQ==} engines: {node: '>=14.0.0'} @@ -14768,12 +15493,27 @@ packages: tslib: 2.6.2 dev: false + /@smithy/util-base64@3.0.0: + resolution: {integrity: sha512-Kxvoh5Qtt0CDsfajiZOCpJxgtPHXOKwmM+Zy4waD43UoEMA+qPxxa98aE/7ZhdnBFZFXMOiBR5xbcaMhLtznQQ==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/util-buffer-from': 3.0.0 + '@smithy/util-utf8': 3.0.0 + tslib: 2.6.2 + dev: false + /@smithy/util-body-length-browser@2.0.0: resolution: {integrity: sha512-JdDuS4ircJt+FDnaQj88TzZY3+njZ6O+D3uakS32f2VNnDo3vyEuNdBOh/oFd8Df1zSZOuH1HEChk2AOYDezZg==} dependencies: tslib: 2.6.2 dev: false + /@smithy/util-body-length-browser@3.0.0: + resolution: {integrity: sha512-cbjJs2A1mLYmqmyVl80uoLTJhAcfzMOyPgjwAYusWKMdLeNtzmMz9YxNl3/jRLoxSS3wkqkf0jwNdtXWtyEBaQ==} + dependencies: + tslib: 2.6.2 + dev: false + /@smithy/util-body-length-node@2.1.0: resolution: {integrity: sha512-/li0/kj/y3fQ3vyzn36NTLGmUwAICb7Jbe/CsWCktW363gh1MOcpEcSO3mJ344Gv2dqz8YJCLQpb6hju/0qOWw==} engines: {node: '>=14.0.0'} @@ -14781,6 +15521,13 @@ packages: tslib: 2.6.2 dev: false + /@smithy/util-body-length-node@3.0.0: + resolution: {integrity: sha512-Tj7pZ4bUloNUP6PzwhN7K386tmSmEET9QtQg0TgdNOnxhZvCssHji+oZTUIuzxECRfG8rdm2PMw2WCFs6eIYkA==} + engines: {node: '>=16.0.0'} + dependencies: + tslib: 2.6.2 + dev: false + /@smithy/util-buffer-from@2.0.0: resolution: {integrity: sha512-/YNnLoHsR+4W4Vf2wL5lGv0ksg8Bmk3GEGxn2vEQt52AQaPSCuaO5PM5VM7lP1K9qHRKHwrPGktqVoAHKWHxzw==} engines: {node: '>=14.0.0'} @@ -14789,6 +15536,14 @@ packages: tslib: 2.6.2 dev: false + /@smithy/util-buffer-from@3.0.0: + resolution: {integrity: sha512-aEOHCgq5RWFbP+UDPvPot26EJHjOC+bRgse5A8V3FSShqd5E5UN4qc7zkwsvJPPAVsf73QwYcHN1/gt/rtLwQA==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/is-array-buffer': 3.0.0 + tslib: 2.6.2 + dev: false + /@smithy/util-config-provider@2.0.0: resolution: {integrity: sha512-xCQ6UapcIWKxXHEU4Mcs2s7LcFQRiU3XEluM2WcCjjBtQkUN71Tb+ydGmJFPxMUrW/GWMgQEEGipLym4XG0jZg==} engines: {node: '>=14.0.0'} @@ -14796,6 +15551,13 @@ packages: tslib: 2.6.2 dev: false + /@smithy/util-config-provider@3.0.0: + resolution: {integrity: sha512-pbjk4s0fwq3Di/ANL+rCvJMKM5bzAQdE5S/6RL5NXgMExFAi6UgQMPOm5yPaIWPpr+EOXKXRonJ3FoxKf4mCJQ==} + engines: {node: '>=16.0.0'} + dependencies: + tslib: 2.6.2 + dev: false + /@smithy/util-defaults-mode-browser@2.0.20: resolution: {integrity: sha512-QJtnbTIl0/BbEASkx1MUFf6EaoWqWW1/IM90N++8NNscePvPf77GheYfpoPis6CBQawUWq8QepTP2QUSAdrVkw==} engines: {node: '>= 10.0.0'} @@ -14807,6 +15569,17 @@ packages: tslib: 2.6.2 dev: false + /@smithy/util-defaults-mode-browser@3.0.31: + resolution: {integrity: sha512-eO+zkbqrPnmsagqzrmF7IJrCoU2wTQXWVYxMPqA9Oue55kw9WEvhyuw2XQzTVTCRcYsg6KgmV3YYhLlWQJfK1A==} + engines: {node: '>= 10.0.0'} + dependencies: + '@smithy/property-provider': 3.1.11 + '@smithy/smithy-client': 3.5.1 + '@smithy/types': 3.7.2 + bowser: 2.11.0 + tslib: 2.6.2 + dev: false + /@smithy/util-defaults-mode-node@2.0.26: resolution: {integrity: sha512-lGFPOFCHv1ql019oegYqa54BZH7HREw6EBqjDLbAr0wquMX0BDi2sg8TJ6Eq+JGLijkZbJB73m4+aK8OFAapMg==} engines: {node: '>= 10.0.0'} @@ -14820,6 +15593,19 @@ packages: tslib: 2.6.2 dev: false + /@smithy/util-defaults-mode-node@3.0.31: + resolution: {integrity: sha512-0/nJfpSpbGZOs6qs42wCe2TdjobbnnD4a3YUUlvTXSQqLy4qa63luDaV04hGvqSHP7wQ7/WGehbvHkDhMZd1MQ==} + engines: {node: '>= 10.0.0'} + dependencies: + '@smithy/config-resolver': 3.0.13 + '@smithy/credential-provider-imds': 3.2.8 + '@smithy/node-config-provider': 3.1.12 + '@smithy/property-provider': 3.1.11 + '@smithy/smithy-client': 3.5.1 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/util-endpoints@1.0.5: resolution: {integrity: sha512-K7qNuCOD5K/90MjHvHm9kJldrfm40UxWYQxNEShMFxV/lCCCRIg8R4uu1PFAxRvPxNpIdcrh1uK6I1ISjDXZJw==} engines: {node: '>= 14.0.0'} @@ -14829,6 +15615,15 @@ packages: tslib: 2.6.2 dev: false + /@smithy/util-endpoints@2.1.7: + resolution: {integrity: sha512-tSfcqKcN/Oo2STEYCABVuKgJ76nyyr6skGl9t15hs+YaiU06sgMkN7QYjo0BbVw+KT26zok3IzbdSOksQ4YzVw==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/node-config-provider': 3.1.12 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/util-hex-encoding@2.0.0: resolution: {integrity: sha512-c5xY+NUnFqG6d7HFh1IFfrm3mGl29lC+vF+geHv4ToiuJCBmIfzx6IeHLg+OgRdPFKDXIw6pvi+p3CsscaMcMA==} engines: {node: '>=14.0.0'} @@ -14836,6 +15631,13 @@ packages: tslib: 2.6.2 dev: false + /@smithy/util-hex-encoding@3.0.0: + resolution: {integrity: sha512-eFndh1WEK5YMUYvy3lPlVmYY/fZcQE1D8oSf41Id2vCeIkKJXPcYDCZD+4+xViI6b1XSd7tE+s5AmXzz5ilabQ==} + engines: {node: '>=16.0.0'} + dependencies: + tslib: 2.6.2 + dev: false + /@smithy/util-middleware@2.0.7: resolution: {integrity: sha512-tRINOTlf1G9B0ECarFQAtTgMhpnrMPSa+5j4ZEwEawCLfTFTavk6757sxhE4RY5RMlD/I3x+DCS8ZUiR8ho9Pw==} engines: {node: '>=14.0.0'} @@ -14844,6 +15646,14 @@ packages: tslib: 2.6.2 dev: false + /@smithy/util-middleware@3.0.11: + resolution: {integrity: sha512-dWpyc1e1R6VoXrwLoLDd57U1z6CwNSdkM69Ie4+6uYh2GC7Vg51Qtan7ITzczuVpqezdDTKJGJB95fFvvjU/ow==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/util-retry@2.0.7: resolution: {integrity: sha512-fIe5yARaF0+xVT1XKcrdnHKTJ1Vc4+3e3tLDjCuIcE9b6fkBzzGFY7AFiX4M+vj6yM98DrwkuZeHf7/hmtVp0Q==} engines: {node: '>= 14.0.0'} @@ -14853,6 +15663,15 @@ packages: tslib: 2.6.2 dev: false + /@smithy/util-retry@3.0.11: + resolution: {integrity: sha512-hJUC6W7A3DQgaee3Hp9ZFcOxVDZzmBIRBPlUAk8/fSOEl7pE/aX7Dci0JycNOnm9Mfr0KV2XjIlUOcGWXQUdVQ==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/service-error-classification': 3.0.11 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@smithy/util-stream@2.0.21: resolution: {integrity: sha512-0BUE16d7n1x7pi1YluXJdB33jOTyBChT0j/BlOkFa9uxfg6YqXieHxjHNuCdJRARa7AZEj32LLLEPJ1fSa4inA==} engines: {node: '>=14.0.0'} @@ -14867,6 +15686,20 @@ packages: tslib: 2.6.2 dev: false + /@smithy/util-stream@3.3.2: + resolution: {integrity: sha512-sInAqdiVeisUGYAv/FrXpmJ0b4WTFmciTRqzhb7wVuem9BHvhIG7tpiYHLDWrl2stOokNZpTTGqz3mzB2qFwXg==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/fetch-http-handler': 4.1.2 + '@smithy/node-http-handler': 3.3.2 + '@smithy/types': 3.7.2 + '@smithy/util-base64': 3.0.0 + '@smithy/util-buffer-from': 3.0.0 + '@smithy/util-hex-encoding': 3.0.0 + '@smithy/util-utf8': 3.0.0 + tslib: 2.6.2 + dev: false + /@smithy/util-uri-escape@2.0.0: resolution: {integrity: sha512-ebkxsqinSdEooQduuk9CbKcI+wheijxEb3utGXkCoYQkJnwTnLbH1JXGimJtUkQwNQbsbuYwG2+aFVyZf5TLaw==} engines: {node: '>=14.0.0'} @@ -14874,6 +15707,13 @@ packages: tslib: 2.6.2 dev: false + /@smithy/util-uri-escape@3.0.0: + resolution: {integrity: sha512-LqR7qYLgZTD7nWLBecUi4aqolw8Mhza9ArpNEQ881MJJIU2sE5iHCK6TdyqqzcDLy0OPe10IY4T8ctVdtynubg==} + engines: {node: '>=16.0.0'} + dependencies: + tslib: 2.6.2 + dev: false + /@smithy/util-utf8@2.0.2: resolution: {integrity: sha512-qOiVORSPm6Ce4/Yu6hbSgNHABLP2VMv8QOC3tTDNHHlWY19pPyc++fBTbZPtx6egPXi4HQxKDnMxVxpbtX2GoA==} engines: {node: '>=14.0.0'} @@ -14882,6 +15722,23 @@ packages: tslib: 2.6.2 dev: false + /@smithy/util-utf8@3.0.0: + resolution: {integrity: sha512-rUeT12bxFnplYDe815GXbq/oixEGHfRFFtcTF3YdDi/JaENIM6aSYYLJydG83UNzLXeRI5K8abYd/8Sp/QM0kA==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/util-buffer-from': 3.0.0 + tslib: 2.6.2 + dev: false + + /@smithy/util-waiter@3.2.0: + resolution: {integrity: sha512-PpjSboaDUE6yl+1qlg3Si57++e84oXdWGbuFUSAciXsVfEZJJJupR2Nb0QuXHiunt2vGR+1PTizOMvnUPaG2Qg==} + engines: {node: '>=16.0.0'} + dependencies: + '@smithy/abort-controller': 3.1.9 + '@smithy/types': 3.7.2 + tslib: 2.6.2 + dev: false + /@socket.io/component-emitter@3.1.0: resolution: {integrity: sha512-+9jVqKhRSpsc591z5vX+X5Yyw+he/HCB4iQ/RYxw35CEPaY1gnsNE43nf9n9AaYjAQrTiI/mOwKUKdUs9vf7Xg==} @@ -15770,6 +16627,12 @@ packages: /@types/node@20.4.2: resolution: {integrity: sha512-Dd0BYtWgnWJKwO1jkmTrzofjK2QXXcai0dmtzvIBhcA+RsG5h8R3xlyta0kGOZRNfL9GuRtb1knmPEhQrePCEw==} + /@types/nodemailer@6.4.17: + resolution: {integrity: sha512-I9CCaIp6DTldEg7vyUTZi8+9Vo0hi1/T8gv3C89yk1rSAAzoKQ8H8ki/jBYJSFoH/BisgLP8tkZMlQ91CIquww==} + dependencies: + '@types/node': 18.19.20 + dev: true + /@types/normalize-package-data@2.4.1: resolution: {integrity: sha512-Gj7cI7z+98M282Tqmp2K5EIsoouUEzbBJhQQzDE3jSIRk6r9gsz0oUokqIUR4u1R3dMHo0pDHM7sNOHyhulypw==} @@ -21071,6 +21934,13 @@ packages: strnum: 1.0.5 dev: false + /fast-xml-parser@4.4.1: + resolution: {integrity: sha512-xkjOecfnKGkSsOwtZ5Pz7Us/T6mrbPQrq0nh+aCO5V9nk5NLWmasAHumTKjiPJPWANe+kAZ84Jc8ooJkzZ88Sw==} + hasBin: true + dependencies: + strnum: 1.0.5 + dev: false + /fastest-stable-stringify@2.0.2: resolution: {integrity: sha512-bijHueCGd0LqqNK9b5oCMHc0MluJAx0cwqASgbWMvkO01lCYgIhacVRLcaDz3QnyYIRNJRDwMb41VuT6pHJ91Q==} dev: false @@ -24568,6 +25438,11 @@ packages: /node-releases@2.0.18: resolution: {integrity: sha512-d9VeXT4SJ7ZeOqGX6R5EM022wpL+eWPooLI+5UpWn2jCT1aosUQEhQP214x33Wkwx3JQMvIm+tIoVOdodFS40g==} + /nodemailer@6.9.16: + resolution: {integrity: sha512-psAuZdTIRN08HKVd/E8ObdV6NO7NTBY3KsC30F7M4H1OnmLCUNaS56FpYxyb26zWLSyYF9Ozch9KYHhHegsiOQ==} + engines: {node: '>=6.0.0'} + dev: false + /non.geist@1.0.2: resolution: {integrity: sha512-oGCfo7Ub5bJmCOAt4CMAsCrVal/JXkQtxgBcpXzdU3lQib9c5hHdr62I8vI6TtdlsLcaYAPD/HRfZNdBUobwFg==} dev: false @@ -30406,6 +31281,11 @@ packages: resolution: {integrity: sha512-MXcSTerfPa4uqyzStbRoTgt5XIe3x5+42+q1sDuy3R5MDk66URdLMOZe5aPX/SQd+kuYAh0FdP/pO28IkQyTeg==} hasBin: true + /uuid@9.0.1: + resolution: {integrity: sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==} + hasBin: true + dev: false + /uvu@0.5.6: resolution: {integrity: sha512-+g8ENReyr8YsOc6fv/NVJs2vFdHBnBNdfE49rshrTzDWOlUx4Gq7KOS2GD8eqhy2j+Ejq29+SbKH8yjkAqXqoA==} engines: {node: '>=8'} From 330f6c548e3f02acbf3cd00d588a8f17e3e2fc4e Mon Sep 17 00:00:00 2001 From: James Ritchie Date: Mon, 30 Dec 2024 17:49:00 +0000 Subject: [PATCH 2/4] Softened the language in the Pro upgrade modal (#1574) --- .../resources.orgs.$organizationSlug.select-plan.tsx | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/apps/webapp/app/routes/resources.orgs.$organizationSlug.select-plan.tsx b/apps/webapp/app/routes/resources.orgs.$organizationSlug.select-plan.tsx index 4f71288991..1ac03e1ac7 100644 --- a/apps/webapp/app/routes/resources.orgs.$organizationSlug.select-plan.tsx +++ b/apps/webapp/app/routes/resources.orgs.$organizationSlug.select-plan.tsx @@ -661,19 +661,19 @@ export function TierPro({ - Upgrade plan? + Upgrade plan
- Are you sure you want to upgrade to the Pro plan? You will be charged the new - plan price for the remainder of this month on a pro rata basis. + Upgrade to get instant access to all the Pro features. You will be charged the + new plan price for the remainder of this month on a pro rata basis.
- } - defaultValue="help" - /> + +
+
+ Get setup in 3 minutes +
+ + I'm stuck! + + } + defaultValue="help" + /> +
+ + + + + You'll notice a new folder in your project called{" "} + trigger. We've added a very simple example task + in here to help you get started. + + + + + + + + + This page will automatically refresh. +
- - - - - You’ll notice a new folder in your project called{" "} - trigger. We’ve added a very simple example task - in here to help you get started. - - - - - - - - - This page will automatically refresh. - - +
); } @@ -484,26 +491,28 @@ function UserHasNoTasks() { } > {open ? ( -
- Get setup in 3 minutes - - - - You'll need to open a terminal at the root of your project. - - - - - - - - - - - - This page will automatically refresh. - -
+ +
+ Get setup in 3 minutes + + + + You'll need to open a terminal at the root of your project. + + + + + + + + + + + + This page will automatically refresh. + +
+
) : ( "Your DEV environment isn't setup yet." )}