alchemy 0.25.0 → 0.26.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 +7 -0
- package/lib/ai/astro-file.d.ts.map +1 -1
- package/lib/ai/astro-file.js +2 -1
- package/lib/ai/astro-file.js.map +1 -1
- package/lib/ai/client.d.ts.map +1 -1
- package/lib/ai/client.js +3 -2
- package/lib/ai/client.js.map +1 -1
- package/lib/alchemy.d.ts +7 -0
- package/lib/alchemy.d.ts.map +1 -1
- package/lib/alchemy.js +19 -3
- package/lib/alchemy.js.map +1 -1
- package/lib/apply.d.ts.map +1 -1
- package/lib/apply.js +63 -5
- package/lib/apply.js.map +1 -1
- package/lib/aws/control/client.js +4 -3
- package/lib/aws/control/client.js.map +1 -1
- package/lib/aws/control/properties.d.ts +6 -0
- package/lib/aws/control/properties.d.ts.map +1 -1
- package/lib/aws/control/properties.js +48 -0
- package/lib/aws/control/properties.js.map +1 -1
- package/lib/aws/control/resource.d.ts.map +1 -1
- package/lib/aws/control/resource.js +3 -2
- package/lib/aws/control/resource.js.map +1 -1
- package/lib/aws/control/types.d.ts +3969 -4862
- package/lib/aws/control/types.d.ts.map +1 -1
- package/lib/aws/control/types.js.map +1 -1
- package/lib/aws/function.d.ts.map +1 -1
- package/lib/aws/function.js +9 -8
- package/lib/aws/function.js.map +1 -1
- package/lib/aws/oidc/oidc-provider.d.ts.map +1 -1
- package/lib/aws/oidc/oidc-provider.js +3 -2
- package/lib/aws/oidc/oidc-provider.js.map +1 -1
- package/lib/aws/queue.d.ts.map +1 -1
- package/lib/aws/queue.js +3 -2
- package/lib/aws/queue.js.map +1 -1
- package/lib/aws/role.d.ts.map +1 -1
- package/lib/aws/role.js +3 -1
- package/lib/aws/role.js.map +1 -1
- package/lib/aws/ssm-parameter.d.ts.map +1 -1
- package/lib/aws/ssm-parameter.js +2 -1
- package/lib/aws/ssm-parameter.js.map +1 -1
- package/lib/cloudflare/account-api-token.d.ts.map +1 -1
- package/lib/cloudflare/account-api-token.js +3 -2
- package/lib/cloudflare/account-api-token.js.map +1 -1
- package/lib/cloudflare/ai-gateway.d.ts.map +1 -1
- package/lib/cloudflare/ai-gateway.js +4 -3
- package/lib/cloudflare/ai-gateway.js.map +1 -1
- package/lib/cloudflare/api-error.d.ts +0 -9
- package/lib/cloudflare/api-error.d.ts.map +1 -1
- package/lib/cloudflare/api-error.js +24 -0
- package/lib/cloudflare/api-error.js.map +1 -1
- package/lib/cloudflare/api.d.ts.map +1 -1
- package/lib/cloudflare/api.js +5 -4
- package/lib/cloudflare/api.js.map +1 -1
- package/lib/cloudflare/assets.d.ts.map +1 -1
- package/lib/cloudflare/assets.js +26 -6
- package/lib/cloudflare/assets.js.map +1 -1
- package/lib/cloudflare/astro.d.ts +63 -0
- package/lib/cloudflare/astro.d.ts.map +1 -0
- package/lib/cloudflare/astro.js +133 -0
- package/lib/cloudflare/astro.js.map +1 -0
- package/lib/cloudflare/auth.d.ts.map +1 -1
- package/lib/cloudflare/auth.js +3 -2
- package/lib/cloudflare/auth.js.map +1 -1
- package/lib/cloudflare/bindings.d.ts +23 -2
- package/lib/cloudflare/bindings.d.ts.map +1 -1
- package/lib/cloudflare/bindings.js.map +1 -1
- package/lib/cloudflare/bound.d.ts +7 -1
- package/lib/cloudflare/bound.d.ts.map +1 -1
- package/lib/cloudflare/bucket.d.ts.map +1 -1
- package/lib/cloudflare/bucket.js +12 -8
- package/lib/cloudflare/bucket.js.map +1 -1
- package/lib/cloudflare/bundle/bundle-worker.d.ts.map +1 -1
- package/lib/cloudflare/bundle/bundle-worker.js +2 -1
- package/lib/cloudflare/bundle/bundle-worker.js.map +1 -1
- package/lib/cloudflare/bundle/nodejs-compat-mode.d.ts.map +1 -1
- package/lib/cloudflare/bundle/nodejs-compat-mode.js +2 -1
- package/lib/cloudflare/bundle/nodejs-compat-mode.js.map +1 -1
- package/lib/cloudflare/custom-domain.d.ts.map +1 -1
- package/lib/cloudflare/custom-domain.js +10 -9
- package/lib/cloudflare/custom-domain.js.map +1 -1
- package/lib/cloudflare/d1-database.d.ts.map +1 -1
- package/lib/cloudflare/d1-database.js +11 -10
- package/lib/cloudflare/d1-database.js.map +1 -1
- package/lib/cloudflare/d1-export.d.ts.map +1 -1
- package/lib/cloudflare/d1-export.js +2 -1
- package/lib/cloudflare/d1-export.js.map +1 -1
- package/lib/cloudflare/d1-import.d.ts.map +1 -1
- package/lib/cloudflare/d1-import.js +2 -1
- package/lib/cloudflare/d1-import.js.map +1 -1
- package/lib/cloudflare/d1-migrations.d.ts.map +1 -1
- package/lib/cloudflare/d1-migrations.js +2 -1
- package/lib/cloudflare/d1-migrations.js.map +1 -1
- package/lib/cloudflare/dns-records.d.ts.map +1 -1
- package/lib/cloudflare/dns-records.js +5 -4
- package/lib/cloudflare/dns-records.js.map +1 -1
- package/lib/cloudflare/do-state-store/worker.d.ts.map +1 -1
- package/lib/cloudflare/do-state-store/worker.js +4 -0
- package/lib/cloudflare/do-state-store/worker.js.map +1 -1
- package/lib/cloudflare/email-address.d.ts +79 -0
- package/lib/cloudflare/email-address.d.ts.map +1 -0
- package/lib/cloudflare/email-address.js +112 -0
- package/lib/cloudflare/email-address.js.map +1 -0
- package/lib/cloudflare/email-catch-all.d.ts +123 -0
- package/lib/cloudflare/email-catch-all.d.ts.map +1 -0
- package/lib/cloudflare/email-catch-all.js +124 -0
- package/lib/cloudflare/email-catch-all.js.map +1 -0
- package/lib/cloudflare/email-routing.d.ts +89 -0
- package/lib/cloudflare/email-routing.d.ts.map +1 -0
- package/lib/cloudflare/email-routing.js +120 -0
- package/lib/cloudflare/email-routing.js.map +1 -0
- package/lib/cloudflare/email-rule.d.ts +196 -0
- package/lib/cloudflare/email-rule.d.ts.map +1 -0
- package/lib/cloudflare/email-rule.js +153 -0
- package/lib/cloudflare/email-rule.js.map +1 -0
- package/lib/cloudflare/hyperdrive.d.ts.map +1 -1
- package/lib/cloudflare/hyperdrive.js +5 -4
- package/lib/cloudflare/hyperdrive.js.map +1 -1
- package/lib/cloudflare/images.d.ts +60 -0
- package/lib/cloudflare/images.d.ts.map +1 -0
- package/lib/cloudflare/images.js +60 -0
- package/lib/cloudflare/images.js.map +1 -0
- package/lib/cloudflare/index.d.ts +9 -0
- package/lib/cloudflare/index.d.ts.map +1 -1
- package/lib/cloudflare/index.js +9 -0
- package/lib/cloudflare/index.js.map +1 -1
- package/lib/cloudflare/kv-namespace.d.ts.map +1 -1
- package/lib/cloudflare/kv-namespace.js +2 -1
- package/lib/cloudflare/kv-namespace.js.map +1 -1
- package/lib/cloudflare/pipeline.d.ts +7 -0
- package/lib/cloudflare/pipeline.d.ts.map +1 -1
- package/lib/cloudflare/pipeline.js +28 -2
- package/lib/cloudflare/pipeline.js.map +1 -1
- package/lib/cloudflare/queue-consumer.d.ts.map +1 -1
- package/lib/cloudflare/queue-consumer.js +2 -1
- package/lib/cloudflare/queue-consumer.js.map +1 -1
- package/lib/cloudflare/queue.d.ts.map +1 -1
- package/lib/cloudflare/queue.js +0 -8
- package/lib/cloudflare/queue.js.map +1 -1
- package/lib/cloudflare/route.d.ts +26 -1
- package/lib/cloudflare/route.d.ts.map +1 -1
- package/lib/cloudflare/route.js +84 -16
- package/lib/cloudflare/route.js.map +1 -1
- package/lib/cloudflare/secret.d.ts +137 -0
- package/lib/cloudflare/secret.d.ts.map +1 -0
- package/lib/cloudflare/secret.js +122 -0
- package/lib/cloudflare/secret.js.map +1 -0
- package/lib/cloudflare/secrets-store.d.ts +145 -0
- package/lib/cloudflare/secrets-store.d.ts.map +1 -0
- package/lib/cloudflare/secrets-store.js +213 -0
- package/lib/cloudflare/secrets-store.js.map +1 -0
- package/lib/cloudflare/sveltekit.d.ts +49 -0
- package/lib/cloudflare/sveltekit.d.ts.map +1 -0
- package/lib/cloudflare/sveltekit.js +56 -0
- package/lib/cloudflare/sveltekit.js.map +1 -0
- package/lib/cloudflare/user.d.ts.map +1 -1
- package/lib/cloudflare/user.js +2 -1
- package/lib/cloudflare/user.js.map +1 -1
- package/lib/cloudflare/vectorize-index.d.ts.map +1 -1
- package/lib/cloudflare/vectorize-index.js +6 -5
- package/lib/cloudflare/vectorize-index.js.map +1 -1
- package/lib/cloudflare/vectorize-metadata-index.d.ts.map +1 -1
- package/lib/cloudflare/vectorize-metadata-index.js +2 -1
- package/lib/cloudflare/vectorize-metadata-index.js.map +1 -1
- package/lib/cloudflare/website.d.ts.map +1 -1
- package/lib/cloudflare/website.js +7 -2
- package/lib/cloudflare/website.js.map +1 -1
- package/lib/cloudflare/worker-assets.d.ts +18 -0
- package/lib/cloudflare/worker-assets.d.ts.map +1 -1
- package/lib/cloudflare/worker-assets.js +61 -67
- package/lib/cloudflare/worker-assets.js.map +1 -1
- package/lib/cloudflare/worker-metadata.d.ts.map +1 -1
- package/lib/cloudflare/worker-metadata.js +16 -1
- package/lib/cloudflare/worker-metadata.js.map +1 -1
- package/lib/cloudflare/worker.d.ts +31 -1
- package/lib/cloudflare/worker.d.ts.map +1 -1
- package/lib/cloudflare/worker.js +34 -8
- package/lib/cloudflare/worker.js.map +1 -1
- package/lib/cloudflare/wrangler.json.d.ts +14 -0
- package/lib/cloudflare/wrangler.json.d.ts.map +1 -1
- package/lib/cloudflare/wrangler.json.js +23 -0
- package/lib/cloudflare/wrangler.json.js.map +1 -1
- package/lib/cloudflare/zone.d.ts.map +1 -1
- package/lib/cloudflare/zone.js +4 -3
- package/lib/cloudflare/zone.js.map +1 -1
- package/lib/destroy.d.ts.map +1 -1
- package/lib/destroy.js +30 -13
- package/lib/destroy.js.map +1 -1
- package/lib/dns/godaddy.d.ts.map +1 -1
- package/lib/dns/godaddy.js +3 -2
- package/lib/dns/godaddy.js.map +1 -1
- package/lib/dns/import-dns.d.ts.map +1 -1
- package/lib/dns/import-dns.js +2 -1
- package/lib/dns/import-dns.js.map +1 -1
- package/lib/esbuild/bundle.d.ts +1 -1
- package/lib/esbuild/bundle.d.ts.map +1 -1
- package/lib/esbuild/bundle.js +2 -1
- package/lib/esbuild/bundle.js.map +1 -1
- package/lib/fs/copy-file.d.ts.map +1 -1
- package/lib/fs/copy-file.js +2 -1
- package/lib/fs/copy-file.js.map +1 -1
- package/lib/fs/file.d.ts.map +1 -1
- package/lib/fs/file.js +2 -1
- package/lib/fs/file.js.map +1 -1
- package/lib/github/client.d.ts.map +1 -1
- package/lib/github/client.js +11 -10
- package/lib/github/client.js.map +1 -1
- package/lib/github/repository-environment.d.ts.map +1 -1
- package/lib/github/repository-environment.js +5 -4
- package/lib/github/repository-environment.js.map +1 -1
- package/lib/github/secret.d.ts.map +1 -1
- package/lib/github/secret.js +7 -6
- package/lib/github/secret.js.map +1 -1
- package/lib/index.d.ts +2 -1
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +1 -0
- package/lib/index.js.map +1 -1
- package/lib/neon/project.d.ts.map +1 -1
- package/lib/neon/project.js +3 -2
- package/lib/neon/project.js.map +1 -1
- package/lib/planetscale/api.d.ts +53 -0
- package/lib/planetscale/api.d.ts.map +1 -0
- package/lib/planetscale/api.js +84 -0
- package/lib/planetscale/api.js.map +1 -0
- package/lib/planetscale/branch.d.ts +129 -0
- package/lib/planetscale/branch.d.ts.map +1 -0
- package/lib/planetscale/branch.js +161 -0
- package/lib/planetscale/branch.js.map +1 -0
- package/lib/planetscale/database.d.ts +143 -0
- package/lib/planetscale/database.d.ts.map +1 -0
- package/lib/planetscale/database.js +184 -0
- package/lib/planetscale/database.js.map +1 -0
- package/lib/planetscale/index.d.ts +5 -0
- package/lib/planetscale/index.d.ts.map +1 -0
- package/lib/planetscale/index.js +5 -0
- package/lib/planetscale/index.js.map +1 -0
- package/lib/planetscale/utils.d.ts +15 -0
- package/lib/planetscale/utils.d.ts.map +1 -0
- package/lib/planetscale/utils.js +95 -0
- package/lib/planetscale/utils.js.map +1 -0
- package/lib/resource.js +7 -1
- package/lib/resource.js.map +1 -1
- package/lib/runtime/plugin.d.ts.map +1 -1
- package/lib/runtime/plugin.js +2 -1
- package/lib/runtime/plugin.js.map +1 -1
- package/lib/scope.d.ts +13 -2
- package/lib/scope.d.ts.map +1 -1
- package/lib/scope.js +53 -10
- package/lib/scope.js.map +1 -1
- package/lib/sentry/client-key.d.ts.map +1 -1
- package/lib/sentry/client-key.js +5 -4
- package/lib/sentry/client-key.js.map +1 -1
- package/lib/sentry/project.d.ts.map +1 -1
- package/lib/sentry/project.js +5 -4
- package/lib/sentry/project.js.map +1 -1
- package/lib/sentry/team.d.ts.map +1 -1
- package/lib/sentry/team.js +5 -4
- package/lib/sentry/team.js.map +1 -1
- package/lib/stripe/card.d.ts.map +1 -1
- package/lib/stripe/card.js +2 -1
- package/lib/stripe/card.js.map +1 -1
- package/lib/stripe/client.d.ts.map +1 -1
- package/lib/stripe/client.js +3 -2
- package/lib/stripe/client.js.map +1 -1
- package/lib/stripe/coupon.d.ts.map +1 -1
- package/lib/stripe/coupon.js +2 -1
- package/lib/stripe/coupon.js.map +1 -1
- package/lib/stripe/customer.d.ts.map +1 -1
- package/lib/stripe/customer.js +2 -1
- package/lib/stripe/customer.js.map +1 -1
- package/lib/stripe/entitlements-feature.d.ts.map +1 -1
- package/lib/stripe/entitlements-feature.js +2 -1
- package/lib/stripe/entitlements-feature.js.map +1 -1
- package/lib/stripe/file.d.ts.map +1 -1
- package/lib/stripe/file.js +2 -1
- package/lib/stripe/file.js.map +1 -1
- package/lib/stripe/meter.d.ts.map +1 -1
- package/lib/stripe/meter.js +4 -2
- package/lib/stripe/meter.js.map +1 -1
- package/lib/stripe/portal-configuration.d.ts.map +1 -1
- package/lib/stripe/portal-configuration.js +2 -1
- package/lib/stripe/portal-configuration.js.map +1 -1
- package/lib/stripe/price.d.ts.map +1 -1
- package/lib/stripe/price.js +2 -1
- package/lib/stripe/price.js.map +1 -1
- package/lib/stripe/product-feature.d.ts.map +1 -1
- package/lib/stripe/product-feature.js +2 -1
- package/lib/stripe/product-feature.js.map +1 -1
- package/lib/stripe/product.d.ts.map +1 -1
- package/lib/stripe/product.js +2 -1
- package/lib/stripe/product.js.map +1 -1
- package/lib/stripe/promotion-code.d.ts.map +1 -1
- package/lib/stripe/promotion-code.js +2 -1
- package/lib/stripe/promotion-code.js.map +1 -1
- package/lib/stripe/shipping-rate.d.ts.map +1 -1
- package/lib/stripe/shipping-rate.js +2 -1
- package/lib/stripe/shipping-rate.js.map +1 -1
- package/lib/stripe/tax-rate.d.ts.map +1 -1
- package/lib/stripe/tax-rate.js +2 -1
- package/lib/stripe/tax-rate.js.map +1 -1
- package/lib/stripe/webhook.d.ts.map +1 -1
- package/lib/stripe/webhook.js +3 -2
- package/lib/stripe/webhook.js.map +1 -1
- package/lib/test/bun.d.ts.map +1 -1
- package/lib/test/bun.js +6 -1
- package/lib/test/bun.js.map +1 -1
- package/lib/test/prune.js +7 -1
- package/lib/test/prune.js.map +1 -1
- package/lib/test/vitest.d.ts.map +1 -1
- package/lib/test/vitest.js +2 -0
- package/lib/test/vitest.js.map +1 -1
- package/lib/upstash/redis.d.ts.map +1 -1
- package/lib/upstash/redis.js +2 -1
- package/lib/upstash/redis.js.map +1 -1
- package/lib/util/async-queue.d.ts +35 -0
- package/lib/util/async-queue.d.ts.map +1 -0
- package/lib/util/async-queue.js +87 -0
- package/lib/util/async-queue.js.map +1 -0
- package/lib/util/cli.d.ts +37 -0
- package/lib/util/cli.d.ts.map +1 -0
- package/lib/util/cli.js +90 -0
- package/lib/util/cli.js.map +1 -0
- package/lib/util/ignore-matcher.d.ts +94 -0
- package/lib/util/ignore-matcher.d.ts.map +1 -0
- package/lib/util/ignore-matcher.js +616 -0
- package/lib/util/ignore-matcher.js.map +1 -0
- package/lib/util/logger.d.ts +3 -0
- package/lib/util/logger.d.ts.map +1 -0
- package/lib/util/logger.js +15 -0
- package/lib/util/logger.js.map +1 -0
- package/lib/util/retry.d.ts.map +1 -1
- package/lib/util/retry.js +0 -1
- package/lib/util/retry.js.map +1 -1
- package/lib/util/safe-fetch.d.ts.map +1 -1
- package/lib/util/safe-fetch.js +2 -1
- package/lib/util/safe-fetch.js.map +1 -1
- package/lib/util/telemetry/client.d.ts +32 -0
- package/lib/util/telemetry/client.d.ts.map +1 -0
- package/lib/util/telemetry/client.js +94 -0
- package/lib/util/telemetry/client.js.map +1 -0
- package/lib/util/telemetry/constants.d.ts +4 -0
- package/lib/util/telemetry/constants.d.ts.map +1 -0
- package/lib/util/telemetry/constants.js +8 -0
- package/lib/util/telemetry/constants.js.map +1 -0
- package/lib/util/telemetry/context.d.ts +15 -0
- package/lib/util/telemetry/context.d.ts.map +1 -0
- package/lib/util/telemetry/context.js +128 -0
- package/lib/util/telemetry/context.js.map +1 -0
- package/lib/util/telemetry/index.d.ts +3 -0
- package/lib/util/telemetry/index.d.ts.map +1 -0
- package/lib/util/telemetry/index.js +3 -0
- package/lib/util/telemetry/index.js.map +1 -0
- package/lib/util/telemetry/types.d.ts +59 -0
- package/lib/util/telemetry/types.d.ts.map +1 -0
- package/lib/util/telemetry/types.js +1 -0
- package/lib/util/telemetry/types.js.map +1 -0
- package/lib/util/xdg-paths.d.ts +9 -0
- package/lib/util/xdg-paths.d.ts.map +1 -0
- package/lib/util/xdg-paths.js +41 -0
- package/lib/util/xdg-paths.js.map +1 -0
- package/lib/vercel/project.d.ts.map +1 -1
- package/lib/vercel/project.js +2 -1
- package/lib/vercel/project.js.map +1 -1
- package/lib/web/astro.d.ts.map +1 -1
- package/lib/web/astro.js +2 -1
- package/lib/web/astro.js.map +1 -1
- package/lib/web/shadcn.d.ts.map +1 -1
- package/lib/web/shadcn.js +2 -1
- package/lib/web/shadcn.js.map +1 -1
- package/lib/web/vite.d.ts.map +1 -1
- package/lib/web/vite.js +3 -2
- package/lib/web/vite.js.map +1 -1
- package/lib/web/vitepress/dependencies.d.ts.map +1 -1
- package/lib/web/vitepress/dependencies.js +2 -1
- package/lib/web/vitepress/dependencies.js.map +1 -1
- package/lib/web/vitepress/vitepress.d.ts.map +1 -1
- package/lib/web/vitepress/vitepress.js +2 -1
- package/lib/web/vitepress/vitepress.js.map +1 -1
- package/package.json +6 -4
- package/src/ai/astro-file.ts +2 -1
- package/src/ai/client.ts +3 -2
- package/src/alchemy.ts +28 -3
- package/src/apply.ts +66 -5
- package/src/aws/control/client.ts +4 -4
- package/src/aws/control/properties.ts +48 -0
- package/src/aws/control/resource.ts +3 -2
- package/src/aws/control/types.ts +3988 -6301
- package/src/aws/function.ts +9 -8
- package/src/aws/oidc/oidc-provider.ts +3 -2
- package/src/aws/queue.ts +3 -2
- package/src/aws/role.ts +3 -1
- package/src/aws/ssm-parameter.ts +2 -1
- package/src/cloudflare/account-api-token.ts +3 -2
- package/src/cloudflare/ai-gateway.ts +4 -3
- package/src/cloudflare/api-error.ts +36 -0
- package/src/cloudflare/api.ts +9 -4
- package/src/cloudflare/assets.ts +30 -6
- package/src/cloudflare/astro.ts +176 -0
- package/src/cloudflare/auth.ts +3 -2
- package/src/cloudflare/bindings.ts +27 -0
- package/src/cloudflare/bound.ts +31 -17
- package/src/cloudflare/bucket.ts +15 -8
- package/src/cloudflare/bundle/bundle-worker.ts +2 -1
- package/src/cloudflare/bundle/nodejs-compat-mode.ts +2 -1
- package/src/cloudflare/custom-domain.ts +10 -9
- package/src/cloudflare/d1-database.ts +11 -10
- package/src/cloudflare/d1-export.ts +2 -1
- package/src/cloudflare/d1-import.ts +2 -1
- package/src/cloudflare/d1-migrations.ts +2 -1
- package/src/cloudflare/dns-records.ts +5 -4
- package/src/cloudflare/do-state-store/worker.ts +4 -0
- package/src/cloudflare/email-address.ts +203 -0
- package/src/cloudflare/email-catch-all.ts +248 -0
- package/src/cloudflare/email-routing.ts +230 -0
- package/src/cloudflare/email-rule.ts +322 -0
- package/src/cloudflare/hyperdrive.ts +5 -4
- package/src/cloudflare/images.ts +59 -0
- package/src/cloudflare/index.ts +9 -0
- package/src/cloudflare/kv-namespace.ts +2 -1
- package/src/cloudflare/pipeline.ts +38 -2
- package/src/cloudflare/queue-consumer.ts +2 -1
- package/src/cloudflare/queue.ts +0 -12
- package/src/cloudflare/route.ts +118 -18
- package/src/cloudflare/secret.ts +253 -0
- package/src/cloudflare/secrets-store.ts +420 -0
- package/src/cloudflare/sveltekit.ts +72 -0
- package/src/cloudflare/user.ts +2 -1
- package/src/cloudflare/vectorize-index.ts +6 -5
- package/src/cloudflare/vectorize-metadata-index.ts +2 -1
- package/src/cloudflare/website.ts +76 -66
- package/src/cloudflare/worker-assets.ts +95 -89
- package/src/cloudflare/worker-metadata.ts +14 -1
- package/src/cloudflare/worker.ts +76 -9
- package/src/cloudflare/wrangler.json.ts +42 -0
- package/src/cloudflare/zone.ts +4 -3
- package/src/destroy.ts +35 -17
- package/src/dns/godaddy.ts +3 -2
- package/src/dns/import-dns.ts +2 -1
- package/src/esbuild/bundle.ts +2 -1
- package/src/fs/copy-file.ts +2 -1
- package/src/fs/file.ts +3 -1
- package/src/github/client.ts +11 -10
- package/src/github/repository-environment.ts +5 -4
- package/src/github/secret.ts +7 -6
- package/src/index.ts +2 -1
- package/src/neon/project.ts +3 -2
- package/src/planetscale/api.ts +115 -0
- package/src/planetscale/branch.ts +352 -0
- package/src/planetscale/database.ts +394 -0
- package/src/planetscale/index.ts +4 -0
- package/src/planetscale/utils.ts +189 -0
- package/src/resource.ts +7 -1
- package/src/runtime/plugin.ts +2 -1
- package/src/scope.ts +64 -13
- package/src/sentry/client-key.ts +5 -4
- package/src/sentry/project.ts +5 -4
- package/src/sentry/team.ts +5 -4
- package/src/stripe/card.ts +2 -1
- package/src/stripe/client.ts +3 -2
- package/src/stripe/coupon.ts +2 -1
- package/src/stripe/customer.ts +2 -1
- package/src/stripe/entitlements-feature.ts +2 -1
- package/src/stripe/file.ts +2 -1
- package/src/stripe/meter.ts +4 -2
- package/src/stripe/portal-configuration.ts +2 -1
- package/src/stripe/price.ts +2 -1
- package/src/stripe/product-feature.ts +2 -1
- package/src/stripe/product.ts +2 -1
- package/src/stripe/promotion-code.ts +2 -1
- package/src/stripe/shipping-rate.ts +2 -1
- package/src/stripe/tax-rate.ts +2 -1
- package/src/stripe/webhook.ts +3 -2
- package/src/test/bun.ts +6 -1
- package/src/test/prune.ts +7 -1
- package/src/test/vitest.ts +2 -0
- package/src/upstash/redis.ts +2 -1
- package/src/util/async-queue.ts +97 -0
- package/src/util/cli.tsx +221 -0
- package/src/util/ignore-matcher.ts +873 -0
- package/src/util/logger.ts +17 -0
- package/src/util/retry.ts +0 -1
- package/src/util/safe-fetch.ts +2 -1
- package/src/util/telemetry/client.ts +127 -0
- package/src/util/telemetry/constants.ts +13 -0
- package/src/util/telemetry/context.ts +154 -0
- package/src/util/telemetry/index.ts +2 -0
- package/src/util/telemetry/types.ts +83 -0
- package/src/util/xdg-paths.ts +48 -0
- package/src/vercel/project.ts +2 -1
- package/src/web/astro.ts +2 -1
- package/src/web/shadcn.ts +2 -1
- package/src/web/vite.ts +3 -2
- package/src/web/vitepress/dependencies.ts +2 -1
- package/src/web/vitepress/vitepress.ts +2 -1
|
@@ -0,0 +1,420 @@
|
|
|
1
|
+
import type { Context } from "../context.ts";
|
|
2
|
+
import { Resource, ResourceKind } from "../resource.ts";
|
|
3
|
+
import { bind } from "../runtime/bind.ts";
|
|
4
|
+
import { secret, type Secret } from "../secret.ts";
|
|
5
|
+
import { handleApiError } from "./api-error.ts";
|
|
6
|
+
import {
|
|
7
|
+
createCloudflareApi,
|
|
8
|
+
type CloudflareApi,
|
|
9
|
+
type CloudflareApiOptions,
|
|
10
|
+
} from "./api.ts";
|
|
11
|
+
import type { Bound } from "./bound.ts";
|
|
12
|
+
|
|
13
|
+
/**
|
|
14
|
+
* Properties for creating or updating a Secrets Store
|
|
15
|
+
*/
|
|
16
|
+
export interface SecretsStoreProps<
|
|
17
|
+
S extends Record<string, Secret> | undefined = undefined,
|
|
18
|
+
> extends CloudflareApiOptions {
|
|
19
|
+
/**
|
|
20
|
+
* Name of the secrets store
|
|
21
|
+
*
|
|
22
|
+
* @default id
|
|
23
|
+
*/
|
|
24
|
+
name?: string;
|
|
25
|
+
|
|
26
|
+
/**
|
|
27
|
+
* Secrets to store in the secrets store
|
|
28
|
+
* Maps secret names to secret values (string) or Secret instances
|
|
29
|
+
*
|
|
30
|
+
* @example
|
|
31
|
+
* ```ts
|
|
32
|
+
* const store = await SecretsStore("my-store", {
|
|
33
|
+
* secrets: {
|
|
34
|
+
* API_KEY: "my-api-key-value",
|
|
35
|
+
* DATABASE_URL: alchemy.secret(process.env.DATABASE_URL)
|
|
36
|
+
* }
|
|
37
|
+
* });
|
|
38
|
+
* ```
|
|
39
|
+
*/
|
|
40
|
+
secrets?: { [K in keyof S]: string | Secret };
|
|
41
|
+
|
|
42
|
+
/**
|
|
43
|
+
* Whether to adopt an existing store with the same name if it exists
|
|
44
|
+
* If true and a store with the same name exists, it will be adopted rather than creating a new one
|
|
45
|
+
*
|
|
46
|
+
* @default false
|
|
47
|
+
*/
|
|
48
|
+
adopt?: boolean;
|
|
49
|
+
|
|
50
|
+
/**
|
|
51
|
+
* Whether to delete the store.
|
|
52
|
+
* If set to false, the store will remain but the resource will be removed from state
|
|
53
|
+
*
|
|
54
|
+
* @default true
|
|
55
|
+
*/
|
|
56
|
+
delete?: boolean;
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
export function isSecretsStore(
|
|
60
|
+
resource: Resource,
|
|
61
|
+
): resource is SecretsStore<any> {
|
|
62
|
+
return resource[ResourceKind] === "cloudflare::SecretsStore";
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
export interface SecretsStore<
|
|
66
|
+
S extends Record<string, Secret> | undefined = undefined,
|
|
67
|
+
> extends Resource<"cloudflare::SecretsStore">,
|
|
68
|
+
Omit<SecretsStoreProps<S>, "delete"> {
|
|
69
|
+
/**
|
|
70
|
+
* The binding type for Cloudflare Workers
|
|
71
|
+
*/
|
|
72
|
+
type: "secrets_store";
|
|
73
|
+
|
|
74
|
+
/**
|
|
75
|
+
* The unique identifier of the secrets store
|
|
76
|
+
*/
|
|
77
|
+
id: string;
|
|
78
|
+
|
|
79
|
+
/**
|
|
80
|
+
* The name of the secrets store
|
|
81
|
+
*/
|
|
82
|
+
name: string;
|
|
83
|
+
|
|
84
|
+
/**
|
|
85
|
+
* The secrets stored in this secrets store
|
|
86
|
+
* Maps secret names to Secret instances created with alchemy.secret()
|
|
87
|
+
*/
|
|
88
|
+
secrets?: S;
|
|
89
|
+
|
|
90
|
+
/**
|
|
91
|
+
* Timestamp when the secrets store was created
|
|
92
|
+
*/
|
|
93
|
+
createdAt: number;
|
|
94
|
+
|
|
95
|
+
/**
|
|
96
|
+
* Timestamp when the secrets store was last modified
|
|
97
|
+
*/
|
|
98
|
+
modifiedAt: number;
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
export type SecretsStoreWithBinding<
|
|
102
|
+
S extends Record<string, Secret> | undefined = undefined,
|
|
103
|
+
> = SecretsStore<S> & Bound<SecretsStore<S>>;
|
|
104
|
+
|
|
105
|
+
/**
|
|
106
|
+
* A Cloudflare Secrets Store is a secure, centralized location for storing account-level secrets.
|
|
107
|
+
*
|
|
108
|
+
* @see https://developers.cloudflare.com/secrets-store/
|
|
109
|
+
*
|
|
110
|
+
* @example
|
|
111
|
+
* // Create a basic secrets store
|
|
112
|
+
* const store = await SecretsStore("my-secrets", {
|
|
113
|
+
* name: "production-secrets"
|
|
114
|
+
* });
|
|
115
|
+
*
|
|
116
|
+
* @example
|
|
117
|
+
* // Create a secrets store with initial secrets
|
|
118
|
+
* const store = await SecretsStore("my-secrets", {
|
|
119
|
+
* name: "production-secrets",
|
|
120
|
+
* secrets: {
|
|
121
|
+
* API_KEY: alchemy.secret(process.env.API_KEY),
|
|
122
|
+
* DATABASE_URL: alchemy.secret(process.env.DATABASE_URL),
|
|
123
|
+
* JWT_SECRET: alchemy.secret(process.env.JWT_SECRET)
|
|
124
|
+
* }
|
|
125
|
+
* });
|
|
126
|
+
*
|
|
127
|
+
* @example
|
|
128
|
+
* // Adopt an existing store if it already exists
|
|
129
|
+
* const existingStore = await SecretsStore("existing-store", {
|
|
130
|
+
* name: "existing-secrets-store",
|
|
131
|
+
* adopt: true,
|
|
132
|
+
* secrets: {
|
|
133
|
+
* NEW_SECRET: alchemy.secret("new-value")
|
|
134
|
+
* }
|
|
135
|
+
* });
|
|
136
|
+
*
|
|
137
|
+
* @example
|
|
138
|
+
* // When removing from Alchemy state, keep the store in Cloudflare
|
|
139
|
+
* const preservedStore = await SecretsStore("preserve-store", {
|
|
140
|
+
* name: "preserved-secrets-store",
|
|
141
|
+
* delete: false
|
|
142
|
+
* });
|
|
143
|
+
*
|
|
144
|
+
* @example
|
|
145
|
+
* // Use in a Worker binding to access secrets
|
|
146
|
+
* const worker = await Worker("my-worker", {
|
|
147
|
+
* bindings: {
|
|
148
|
+
* SECRETS: store
|
|
149
|
+
* },
|
|
150
|
+
* code: `
|
|
151
|
+
* export default {
|
|
152
|
+
* async fetch(request, env) {
|
|
153
|
+
* const apiKey = await env.SECRETS.get("API_KEY");
|
|
154
|
+
* return new Response(apiKey ? "Secret found" : "No secret");
|
|
155
|
+
* }
|
|
156
|
+
* }
|
|
157
|
+
* `
|
|
158
|
+
* });
|
|
159
|
+
*/
|
|
160
|
+
export async function SecretsStore<
|
|
161
|
+
const S extends Record<string, Secret> | undefined = undefined,
|
|
162
|
+
>(
|
|
163
|
+
name: string,
|
|
164
|
+
props: SecretsStoreProps<S> = {} as SecretsStoreProps<S>,
|
|
165
|
+
): Promise<SecretsStoreWithBinding<S>> {
|
|
166
|
+
// Convert string values to Secret instances
|
|
167
|
+
const normalizedProps: SecretsStoreProps<S> = {
|
|
168
|
+
...props,
|
|
169
|
+
secrets: props.secrets
|
|
170
|
+
? (Object.fromEntries(
|
|
171
|
+
Object.entries(props.secrets).map(([key, value]) => [
|
|
172
|
+
key,
|
|
173
|
+
typeof value === "string" ? secret(value) : value,
|
|
174
|
+
]),
|
|
175
|
+
) as S)
|
|
176
|
+
: undefined,
|
|
177
|
+
};
|
|
178
|
+
|
|
179
|
+
const store = await _SecretsStore(name, normalizedProps);
|
|
180
|
+
const binding = await bind(store);
|
|
181
|
+
return {
|
|
182
|
+
...store,
|
|
183
|
+
get: binding.get,
|
|
184
|
+
} as SecretsStoreWithBinding<S>;
|
|
185
|
+
}
|
|
186
|
+
|
|
187
|
+
const _SecretsStore = Resource("cloudflare::SecretsStore", async function <
|
|
188
|
+
S extends Record<string, Secret> | undefined = undefined,
|
|
189
|
+
>(this: Context<SecretsStore<S>>, id: string, props: SecretsStoreProps<S>): Promise<
|
|
190
|
+
SecretsStore<S>
|
|
191
|
+
> {
|
|
192
|
+
const api = await createCloudflareApi(props);
|
|
193
|
+
|
|
194
|
+
const name = props.name ?? id;
|
|
195
|
+
|
|
196
|
+
if (this.phase === "delete") {
|
|
197
|
+
const storeId = this.output?.id;
|
|
198
|
+
if (storeId && props.delete !== false) {
|
|
199
|
+
await deleteSecretsStore(api, storeId);
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
return this.destroy();
|
|
203
|
+
}
|
|
204
|
+
|
|
205
|
+
let storeId = this.phase === "update" ? this.output?.id || "" : "";
|
|
206
|
+
let createdAt =
|
|
207
|
+
this.phase === "update" ? this.output?.createdAt || Date.now() : Date.now();
|
|
208
|
+
|
|
209
|
+
if (this.phase === "update" && storeId) {
|
|
210
|
+
const currentSecrets = props.secrets || {};
|
|
211
|
+
const existingSecretNames = await listSecrets(api, storeId);
|
|
212
|
+
|
|
213
|
+
const secretsToDelete = existingSecretNames.filter(
|
|
214
|
+
(name) => !(name in currentSecrets),
|
|
215
|
+
);
|
|
216
|
+
|
|
217
|
+
if (secretsToDelete.length > 0) {
|
|
218
|
+
await deleteSecrets(api, storeId, secretsToDelete);
|
|
219
|
+
}
|
|
220
|
+
|
|
221
|
+
await insertSecrets(api, storeId, props);
|
|
222
|
+
} else {
|
|
223
|
+
try {
|
|
224
|
+
const { id } = await createSecretsStore(api, {
|
|
225
|
+
...props,
|
|
226
|
+
name,
|
|
227
|
+
});
|
|
228
|
+
createdAt = Date.now();
|
|
229
|
+
storeId = id;
|
|
230
|
+
} catch (error) {
|
|
231
|
+
if (
|
|
232
|
+
props.adopt &&
|
|
233
|
+
error instanceof Error &&
|
|
234
|
+
error.message.includes("already exists")
|
|
235
|
+
) {
|
|
236
|
+
console.log(`Secrets store '${name}' already exists, adopting it`);
|
|
237
|
+
const existingStore = await findSecretsStoreByName(api, name);
|
|
238
|
+
|
|
239
|
+
if (!existingStore) {
|
|
240
|
+
throw new Error(
|
|
241
|
+
`Failed to find existing secrets store '${name}' for adoption`,
|
|
242
|
+
);
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
storeId = existingStore.id;
|
|
246
|
+
createdAt = existingStore.createdAt || Date.now();
|
|
247
|
+
} else {
|
|
248
|
+
throw error;
|
|
249
|
+
}
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
await insertSecrets(api, storeId, props);
|
|
253
|
+
}
|
|
254
|
+
|
|
255
|
+
return this({
|
|
256
|
+
type: "secrets_store",
|
|
257
|
+
id: storeId,
|
|
258
|
+
name: name,
|
|
259
|
+
secrets: props.secrets as S,
|
|
260
|
+
createdAt: createdAt,
|
|
261
|
+
modifiedAt: Date.now(),
|
|
262
|
+
});
|
|
263
|
+
});
|
|
264
|
+
|
|
265
|
+
export async function createSecretsStore<
|
|
266
|
+
S extends Record<string, Secret> | undefined = undefined,
|
|
267
|
+
>(
|
|
268
|
+
api: CloudflareApi,
|
|
269
|
+
props: SecretsStoreProps<S> & {
|
|
270
|
+
name: string;
|
|
271
|
+
},
|
|
272
|
+
): Promise<{ id: string }> {
|
|
273
|
+
const createResponse = await api.post(
|
|
274
|
+
`/accounts/${api.accountId}/secrets_store/stores`,
|
|
275
|
+
{
|
|
276
|
+
name: props.name,
|
|
277
|
+
},
|
|
278
|
+
);
|
|
279
|
+
|
|
280
|
+
if (!createResponse.ok) {
|
|
281
|
+
await handleApiError(createResponse, "create", "secrets_store", props.name);
|
|
282
|
+
}
|
|
283
|
+
|
|
284
|
+
return { id: ((await createResponse.json()) as any).result.id };
|
|
285
|
+
}
|
|
286
|
+
|
|
287
|
+
export async function deleteSecretsStore(api: CloudflareApi, storeId: string) {
|
|
288
|
+
const deleteResponse = await api.delete(
|
|
289
|
+
`/accounts/${api.accountId}/secrets_store/stores/${storeId}`,
|
|
290
|
+
);
|
|
291
|
+
|
|
292
|
+
if (!deleteResponse.ok && deleteResponse.status !== 404) {
|
|
293
|
+
await handleApiError(deleteResponse, "delete", "secrets_store", storeId);
|
|
294
|
+
}
|
|
295
|
+
}
|
|
296
|
+
|
|
297
|
+
export async function findSecretsStoreByName(
|
|
298
|
+
api: CloudflareApi,
|
|
299
|
+
name: string,
|
|
300
|
+
): Promise<{ id: string; createdAt?: number } | null> {
|
|
301
|
+
const response = await api.get(
|
|
302
|
+
`/accounts/${api.accountId}/secrets_store/stores`,
|
|
303
|
+
);
|
|
304
|
+
|
|
305
|
+
if (!response.ok) {
|
|
306
|
+
await handleApiError(response, "list", "secrets_store", "all");
|
|
307
|
+
}
|
|
308
|
+
|
|
309
|
+
const data = (await response.json()) as {
|
|
310
|
+
result: Array<{
|
|
311
|
+
id: string;
|
|
312
|
+
name: string;
|
|
313
|
+
created: string;
|
|
314
|
+
modified: string;
|
|
315
|
+
}>;
|
|
316
|
+
success: boolean;
|
|
317
|
+
errors: any[];
|
|
318
|
+
};
|
|
319
|
+
|
|
320
|
+
const stores = data.result;
|
|
321
|
+
|
|
322
|
+
const match = stores.find((store) => store.name === name);
|
|
323
|
+
if (match) {
|
|
324
|
+
return {
|
|
325
|
+
id: match.id,
|
|
326
|
+
createdAt: match.created ? new Date(match.created).getTime() : undefined,
|
|
327
|
+
};
|
|
328
|
+
}
|
|
329
|
+
|
|
330
|
+
return null;
|
|
331
|
+
}
|
|
332
|
+
|
|
333
|
+
export async function insertSecrets<
|
|
334
|
+
S extends Record<string, Secret> | undefined = undefined,
|
|
335
|
+
>(api: CloudflareApi, storeId: string, props: SecretsStoreProps<S>) {
|
|
336
|
+
if (props.secrets && Object.keys(props.secrets).length > 0) {
|
|
337
|
+
const secretEntries = Object.entries(props.secrets);
|
|
338
|
+
|
|
339
|
+
const BATCH_SIZE = 100;
|
|
340
|
+
|
|
341
|
+
for (let i = 0; i < secretEntries.length; i += BATCH_SIZE) {
|
|
342
|
+
const batch = secretEntries.slice(i, i + BATCH_SIZE);
|
|
343
|
+
|
|
344
|
+
const bulkPayload = batch.map(([name, secretValue]) => ({
|
|
345
|
+
name,
|
|
346
|
+
value: (secretValue as Secret).unencrypted,
|
|
347
|
+
scopes: [],
|
|
348
|
+
}));
|
|
349
|
+
|
|
350
|
+
const bulkResponse = await api.post(
|
|
351
|
+
`/accounts/${api.accountId}/secrets_store/stores/${storeId}/secrets`,
|
|
352
|
+
bulkPayload,
|
|
353
|
+
);
|
|
354
|
+
|
|
355
|
+
if (!bulkResponse.ok) {
|
|
356
|
+
const errorData: any = await bulkResponse.json().catch(() => ({
|
|
357
|
+
errors: [{ message: bulkResponse.statusText }],
|
|
358
|
+
}));
|
|
359
|
+
const errorMessage =
|
|
360
|
+
errorData.errors?.[0]?.message || bulkResponse.statusText;
|
|
361
|
+
|
|
362
|
+
throw new Error(`Error creating secrets batch: ${errorMessage}`);
|
|
363
|
+
}
|
|
364
|
+
}
|
|
365
|
+
}
|
|
366
|
+
}
|
|
367
|
+
|
|
368
|
+
export async function deleteSecrets(
|
|
369
|
+
api: CloudflareApi,
|
|
370
|
+
storeId: string,
|
|
371
|
+
secretNames: string[],
|
|
372
|
+
) {
|
|
373
|
+
if (secretNames.length > 0) {
|
|
374
|
+
const deleteResponse = await api.delete(
|
|
375
|
+
`/accounts/${api.accountId}/secrets_store/stores/${storeId}/secrets`,
|
|
376
|
+
{
|
|
377
|
+
body: JSON.stringify(secretNames),
|
|
378
|
+
headers: {
|
|
379
|
+
"Content-Type": "application/json",
|
|
380
|
+
},
|
|
381
|
+
},
|
|
382
|
+
);
|
|
383
|
+
|
|
384
|
+
if (!deleteResponse.ok && deleteResponse.status !== 404) {
|
|
385
|
+
await handleApiError(
|
|
386
|
+
deleteResponse,
|
|
387
|
+
"delete",
|
|
388
|
+
"secrets",
|
|
389
|
+
secretNames.join(", "),
|
|
390
|
+
);
|
|
391
|
+
}
|
|
392
|
+
}
|
|
393
|
+
}
|
|
394
|
+
|
|
395
|
+
export async function listSecrets(
|
|
396
|
+
api: CloudflareApi,
|
|
397
|
+
storeId: string,
|
|
398
|
+
): Promise<string[]> {
|
|
399
|
+
const response = await api.get(
|
|
400
|
+
`/accounts/${api.accountId}/secrets_store/stores/${storeId}/secrets`,
|
|
401
|
+
);
|
|
402
|
+
|
|
403
|
+
if (!response.ok) {
|
|
404
|
+
await handleApiError(response, "list", "secrets", "all");
|
|
405
|
+
}
|
|
406
|
+
|
|
407
|
+
const data = (await response.json()) as {
|
|
408
|
+
result: Array<{
|
|
409
|
+
id: string;
|
|
410
|
+
name: string;
|
|
411
|
+
created: string;
|
|
412
|
+
modified: string;
|
|
413
|
+
status: string;
|
|
414
|
+
}>;
|
|
415
|
+
success: boolean;
|
|
416
|
+
errors: any[];
|
|
417
|
+
};
|
|
418
|
+
|
|
419
|
+
return data.result.map((secret) => secret.name);
|
|
420
|
+
}
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
import { join } from "node:path";
|
|
2
|
+
import type { Assets } from "./assets.ts";
|
|
3
|
+
import type { Bindings } from "./bindings.ts";
|
|
4
|
+
import { Website, type WebsiteProps } from "./website.ts";
|
|
5
|
+
import type { Worker } from "./worker.ts";
|
|
6
|
+
|
|
7
|
+
export interface SvelteKitProps<B extends Bindings> extends WebsiteProps<B> {}
|
|
8
|
+
|
|
9
|
+
// don't allow the ASSETS to be overriden
|
|
10
|
+
export type SvelteKit<B extends Bindings> = B extends { ASSETS: any }
|
|
11
|
+
? never
|
|
12
|
+
: Worker<B & { ASSETS: Assets }>;
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* Deploy a SvelteKit application to Cloudflare Workers with automatically configured defaults.
|
|
16
|
+
*
|
|
17
|
+
* This resource handles the deployment of SvelteKit applications with optimized settings for
|
|
18
|
+
* Cloudflare Workers, including proper build commands and compatibility flags. It expects
|
|
19
|
+
* the SvelteKit app to be configured with the @sveltejs/adapter-cloudflare adapter.
|
|
20
|
+
*
|
|
21
|
+
* For local development, SvelteKit provides excellent built-in dev server support with
|
|
22
|
+
* emulated platform.env bindings for Cloudflare-specific APIs.
|
|
23
|
+
*
|
|
24
|
+
* @see https://svelte.dev/docs/kit/adapter-cloudflare - Official SvelteKit Cloudflare adapter docs
|
|
25
|
+
*
|
|
26
|
+
* @example
|
|
27
|
+
* // Deploy a basic SvelteKit application
|
|
28
|
+
* const svelteApp = await SvelteKit("my-svelte-app");
|
|
29
|
+
*
|
|
30
|
+
* @example
|
|
31
|
+
* // Deploy with Cloudflare bindings
|
|
32
|
+
* import { D1Database, KVNamespace, R2Bucket } from "alchemy/cloudflare";
|
|
33
|
+
*
|
|
34
|
+
* const database = await D1Database("svelte-db");
|
|
35
|
+
* const sessions = await KVNamespace("sessions");
|
|
36
|
+
* const storage = await R2Bucket("app-storage");
|
|
37
|
+
*
|
|
38
|
+
* const svelteApp = await SvelteKit("svelte-with-bindings", {
|
|
39
|
+
* bindings: {
|
|
40
|
+
* DB: database,
|
|
41
|
+
* AUTH_STORE: sessions,
|
|
42
|
+
* STORAGE: storage
|
|
43
|
+
* }
|
|
44
|
+
* });
|
|
45
|
+
*
|
|
46
|
+
* @param id - Unique identifier for the SvelteKit application
|
|
47
|
+
* @param props - Configuration properties for the SvelteKit deployment
|
|
48
|
+
* @returns A Cloudflare Worker resource representing the deployed SvelteKit application
|
|
49
|
+
*/
|
|
50
|
+
export async function SvelteKit<B extends Bindings>(
|
|
51
|
+
id: string,
|
|
52
|
+
props?: Partial<SvelteKitProps<B>>,
|
|
53
|
+
): Promise<SvelteKit<B>> {
|
|
54
|
+
if (props?.compatibilityDate) {
|
|
55
|
+
const providedDate = new Date(props.compatibilityDate);
|
|
56
|
+
const minDate = new Date("2024-09-23");
|
|
57
|
+
if (providedDate < minDate) {
|
|
58
|
+
throw new Error(
|
|
59
|
+
`SvelteKit compatibility date must be >= 2024-09-23 for nodejs_compat support, got ${props.compatibilityDate}`,
|
|
60
|
+
);
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
return Website(id, {
|
|
65
|
+
...props,
|
|
66
|
+
command: props?.command ?? "bun run build",
|
|
67
|
+
main: props?.main ?? join(".svelte-kit", "cloudflare", "_worker.js"),
|
|
68
|
+
assets: props?.assets ?? join(".svelte-kit", "cloudflare"),
|
|
69
|
+
compatibilityFlags: ["nodejs_compat", ...(props?.compatibilityFlags ?? [])],
|
|
70
|
+
compatibilityDate: props?.compatibilityDate,
|
|
71
|
+
});
|
|
72
|
+
}
|
package/src/cloudflare/user.ts
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import type { Secret } from "../secret.ts";
|
|
2
|
+
import { logger } from "../util/logger.ts";
|
|
2
3
|
import { CloudflareApiError } from "./api-error.ts";
|
|
3
4
|
import {
|
|
4
5
|
getCloudflareAuthHeaders,
|
|
@@ -127,7 +128,7 @@ export async function getUserEmailFromApiKey(apiKey: string): Promise<string> {
|
|
|
127
128
|
emailCache[apiKey] = data.result.email;
|
|
128
129
|
return data.result.email;
|
|
129
130
|
} catch (error) {
|
|
130
|
-
|
|
131
|
+
logger.error("Error retrieving email from Cloudflare API:", error);
|
|
131
132
|
throw new Error(
|
|
132
133
|
"Failed to automatically discover email for API Key authentication",
|
|
133
134
|
);
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import type { Context } from "../context.ts";
|
|
2
2
|
import { Resource, ResourceKind } from "../resource.ts";
|
|
3
3
|
import { bind } from "../runtime/bind.ts";
|
|
4
|
+
import { logger } from "../util/logger.ts";
|
|
4
5
|
import { CloudflareApiError, handleApiError } from "./api-error.ts";
|
|
5
6
|
import {
|
|
6
7
|
createCloudflareApi,
|
|
@@ -145,7 +146,7 @@ const _VectorizeIndex = Resource(
|
|
|
145
146
|
const indexName = props.name || id;
|
|
146
147
|
|
|
147
148
|
if (this.phase === "delete") {
|
|
148
|
-
|
|
149
|
+
logger.log("Deleting Vectorize index:", indexName);
|
|
149
150
|
if (props.delete !== false) {
|
|
150
151
|
// Delete Vectorize index
|
|
151
152
|
await deleteIndex(api, indexName);
|
|
@@ -157,7 +158,7 @@ const _VectorizeIndex = Resource(
|
|
|
157
158
|
let indexData: CloudflareVectorizeResponse;
|
|
158
159
|
|
|
159
160
|
if (this.phase === "create") {
|
|
160
|
-
|
|
161
|
+
logger.log("Creating Vectorize index:", indexName);
|
|
161
162
|
try {
|
|
162
163
|
indexData = await createIndex(api, indexName, {
|
|
163
164
|
...props,
|
|
@@ -170,7 +171,7 @@ const _VectorizeIndex = Resource(
|
|
|
170
171
|
error instanceof CloudflareApiError &&
|
|
171
172
|
error.message.includes("already exists")
|
|
172
173
|
) {
|
|
173
|
-
|
|
174
|
+
logger.log(`Index ${indexName} already exists, adopting it`);
|
|
174
175
|
// Find the existing index
|
|
175
176
|
indexData = await getIndex(api, indexName);
|
|
176
177
|
} else {
|
|
@@ -182,7 +183,7 @@ const _VectorizeIndex = Resource(
|
|
|
182
183
|
if (props.delete !== this.props.delete) {
|
|
183
184
|
// Only allow changing the delete property
|
|
184
185
|
if (!this.quiet) {
|
|
185
|
-
|
|
186
|
+
logger.warn(
|
|
186
187
|
`Attempted to update Vectorize index ${indexName} but only the delete property can be changed.`,
|
|
187
188
|
);
|
|
188
189
|
}
|
|
@@ -200,7 +201,7 @@ const _VectorizeIndex = Resource(
|
|
|
200
201
|
props.metric === this.props.metric
|
|
201
202
|
) {
|
|
202
203
|
if (!this.quiet) {
|
|
203
|
-
|
|
204
|
+
logger.warn(
|
|
204
205
|
`Attempted to update Vectorize index ${indexName} but it was a no-op.`,
|
|
205
206
|
);
|
|
206
207
|
}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import type { Context } from "../context.ts";
|
|
2
2
|
import { Resource, ResourceKind } from "../resource.ts";
|
|
3
|
+
import { logger } from "../util/logger.ts";
|
|
3
4
|
import { CloudflareApiError, handleApiError } from "./api-error.ts";
|
|
4
5
|
import {
|
|
5
6
|
createCloudflareApi,
|
|
@@ -121,7 +122,7 @@ export const VectorizeMetadataIndex = Resource(
|
|
|
121
122
|
) {
|
|
122
123
|
// Update operation is not supported
|
|
123
124
|
if (!this.scope.quiet) {
|
|
124
|
-
|
|
125
|
+
logger.warn(
|
|
125
126
|
`Attempted to update Vectorize metadata index ${this.props.propertyName} but it was a no-op.`,
|
|
126
127
|
);
|
|
127
128
|
}
|