@appwarden/middleware 2.0.0 → 3.0.1

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 CHANGED
@@ -1,6 +1,6 @@
1
1
  # @appwarden/middleware
2
2
 
3
- ![Test Coverage](https://img.shields.io/badge/coverage-95.82%25-brightgreen)
3
+ ![Test Coverage](https://img.shields.io/badge/coverage-95.95%25-brightgreen)
4
4
  [![npm version](https://img.shields.io/npm/v/@appwarden/middleware.svg)](https://www.npmjs.com/package/@appwarden/middleware)
5
5
  [![npm provenance](https://img.shields.io/badge/npm-provenance-green)](https://docs.npmjs.com/generating-provenance-statements)
6
6
  [![License: MIT](https://img.shields.io/badge/License-MIT-blue.svg)](https://opensource.org/licenses/MIT)
@@ -0,0 +1,50 @@
1
+ import {
2
+ getErrors
3
+ } from "./chunk-B5IE7V77.js";
4
+ import {
5
+ printMessage
6
+ } from "./chunk-7UTT3M2S.js";
7
+
8
+ // src/utils/build-lock-page-url.ts
9
+ function normalizeLockPageSlug(lockPageSlug) {
10
+ return lockPageSlug.startsWith("/") ? lockPageSlug : `/${lockPageSlug}`;
11
+ }
12
+ function buildLockPageUrl(lockPageSlug, requestUrl) {
13
+ const normalizedSlug = normalizeLockPageSlug(lockPageSlug);
14
+ return new URL(normalizedSlug, requestUrl);
15
+ }
16
+ function normalizeTrailingSlash(path) {
17
+ if (path === "/") return path;
18
+ return path.endsWith("/") ? path.slice(0, -1) : path;
19
+ }
20
+ function isOnLockPage(lockPageSlug, requestUrl) {
21
+ const normalizedSlug = normalizeTrailingSlash(
22
+ normalizeLockPageSlug(lockPageSlug)
23
+ );
24
+ const url = typeof requestUrl === "string" ? new URL(requestUrl) : requestUrl;
25
+ const normalizedPathname = normalizeTrailingSlash(url.pathname);
26
+ return normalizedPathname === normalizedSlug;
27
+ }
28
+
29
+ // src/utils/validate-config.ts
30
+ function validateConfig(config, schema) {
31
+ const result = schema.safeParse(config);
32
+ const hasErrors = !result.success;
33
+ if (hasErrors) {
34
+ const mappedErrors = getErrors(result.error);
35
+ if (mappedErrors.length > 0) {
36
+ for (const error of mappedErrors) {
37
+ console.error(printMessage(error));
38
+ }
39
+ } else {
40
+ console.error(printMessage(result.error.message));
41
+ }
42
+ }
43
+ return hasErrors;
44
+ }
45
+
46
+ export {
47
+ buildLockPageUrl,
48
+ isOnLockPage,
49
+ validateConfig
50
+ };
@@ -1,9 +1,3 @@
1
- // src/utils/build-lock-page-url.ts
2
- function buildLockPageUrl(lockPageSlug, requestUrl) {
3
- const normalizedSlug = lockPageSlug.startsWith("/") ? lockPageSlug : `/${lockPageSlug}`;
4
- return new URL(normalizedSlug, requestUrl);
5
- }
6
-
7
1
  // src/utils/create-redirect.ts
8
2
  var TEMPORARY_REDIRECT_STATUS = 302;
9
3
  var createRedirect = (url) => {
@@ -16,7 +10,6 @@ var createRedirect = (url) => {
16
10
  };
17
11
 
18
12
  export {
19
- buildLockPageUrl,
20
13
  TEMPORARY_REDIRECT_STATUS,
21
14
  createRedirect
22
15
  };
@@ -1,11 +1,13 @@
1
+ import { Runtime } from '@astrojs/cloudflare';
2
+ import { APIContext, MiddlewareHandler } from 'astro';
3
+
1
4
  /**
2
5
  * Cloudflare runtime context provided by Astro on Cloudflare Workers.
3
- * This is the shape of `context.locals.runtime` when using @astrojs/cloudflare adapter.
6
+ * This is extracted from the locals object when using @astrojs/cloudflare adapter.
7
+ *
8
+ * Note: Uses generic CloudflareEnv which should be defined in the user's project.
4
9
  */
5
- interface AstroCloudflareRuntime {
6
- env: CloudflareEnv;
7
- ctx: ExecutionContext;
8
- }
10
+ type AstroCloudflareRuntime = Runtime<CloudflareEnv>["runtime"];
9
11
  /**
10
12
  * Configuration for the Appwarden middleware.
11
13
  */
@@ -26,24 +28,18 @@ interface AstroAppwardenConfig {
26
28
  type AstroConfigFn = (runtime: AstroCloudflareRuntime) => AstroAppwardenConfig;
27
29
  /**
28
30
  * Astro middleware context type.
29
- * This matches Astro's APIContext shape for middleware.
31
+ * Re-exported from Astro's official APIContext type for type compatibility.
32
+ *
33
+ * @deprecated Use `APIContext` from 'astro' directly. This alias is kept for backward compatibility.
30
34
  */
31
- interface AstroMiddlewareContext {
32
- /** The incoming request */
33
- request: Request;
34
- /** Object for storing request-specific data */
35
- locals: {
36
- runtime?: AstroCloudflareRuntime;
37
- [key: string]: unknown;
38
- };
39
- /** Helper to create redirect responses */
40
- redirect: (path: string, status?: number) => Response;
41
- }
35
+ type AstroMiddlewareContext = APIContext;
42
36
  /**
43
37
  * Astro middleware function signature.
44
- * This matches the onRequest export type in Astro's middleware system.
38
+ * This is an alias for Astro's official MiddlewareHandler type for type compatibility.
39
+ *
40
+ * @deprecated Use `MiddlewareHandler` from 'astro' directly. This alias is kept for backward compatibility.
45
41
  */
46
- type AstroMiddlewareFunction = (context: AstroMiddlewareContext, next: () => Promise<Response>) => Promise<Response>;
42
+ type AstroMiddlewareFunction = MiddlewareHandler;
47
43
  /**
48
44
  * Creates an Appwarden middleware function for Astro.
49
45
  *
@@ -67,6 +63,6 @@ type AstroMiddlewareFunction = (context: AstroMiddlewareContext, next: () => Pro
67
63
  * @param configFn - A function that receives the Cloudflare runtime and returns the config
68
64
  * @returns An Astro middleware function
69
65
  */
70
- declare function createAppwardenMiddleware(configFn: AstroConfigFn): AstroMiddlewareFunction;
66
+ declare function createAppwardenMiddleware(configFn: AstroConfigFn): MiddlewareHandler;
71
67
 
72
68
  export { type AstroAppwardenConfig, type AstroCloudflareRuntime, type AstroConfigFn, type AstroMiddlewareContext, type AstroMiddlewareFunction, createAppwardenMiddleware };
@@ -1,11 +1,12 @@
1
1
  import {
2
2
  TEMPORARY_REDIRECT_STATUS,
3
- buildLockPageUrl,
4
3
  createRedirect
5
- } from "../chunk-N6AUTMZO.js";
4
+ } from "../chunk-6M7BE3AW.js";
6
5
  import {
6
+ buildLockPageUrl,
7
+ isOnLockPage,
7
8
  validateConfig
8
- } from "../chunk-6PUA5YXP.js";
9
+ } from "../chunk-4JGYMZTR.js";
9
10
  import {
10
11
  checkLockStatus
11
12
  } from "../chunk-5DEXVBY6.js";
@@ -34,7 +35,8 @@ var AstroCloudflareConfigSchema = z.object({
34
35
  // src/adapters/astro-cloudflare.ts
35
36
  function createAppwardenMiddleware(configFn) {
36
37
  return async (context, next) => {
37
- const { request, locals } = context;
38
+ const { request } = context;
39
+ const locals = context.locals;
38
40
  try {
39
41
  const runtime = locals.runtime;
40
42
  if (!runtime) {
@@ -53,6 +55,9 @@ function createAppwardenMiddleware(configFn) {
53
55
  if (hasError) {
54
56
  return next();
55
57
  }
58
+ if (isOnLockPage(config.lockPageSlug, request.url)) {
59
+ return next();
60
+ }
56
61
  const result = await checkLockStatus({
57
62
  request,
58
63
  appwardenApiToken: config.appwardenApiToken,
@@ -1,10 +1,11 @@
1
1
  import {
2
- TEMPORARY_REDIRECT_STATUS,
3
- buildLockPageUrl
4
- } from "../chunk-N6AUTMZO.js";
2
+ TEMPORARY_REDIRECT_STATUS
3
+ } from "../chunk-6M7BE3AW.js";
5
4
  import {
5
+ buildLockPageUrl,
6
+ isOnLockPage,
6
7
  validateConfig
7
- } from "../chunk-6PUA5YXP.js";
8
+ } from "../chunk-4JGYMZTR.js";
8
9
  import {
9
10
  checkLockStatus
10
11
  } from "../chunk-5DEXVBY6.js";
@@ -49,6 +50,9 @@ function createAppwardenMiddleware(configFn) {
49
50
  if (hasError) {
50
51
  return NextResponse.next();
51
52
  }
53
+ if (isOnLockPage(config.lockPageSlug, request.url)) {
54
+ return NextResponse.next();
55
+ }
52
56
  const result = await checkLockStatus({
53
57
  request,
54
58
  appwardenApiToken: config.appwardenApiToken,
@@ -1,10 +1,11 @@
1
1
  import {
2
- buildLockPageUrl,
3
2
  createRedirect
4
- } from "../chunk-N6AUTMZO.js";
3
+ } from "../chunk-6M7BE3AW.js";
5
4
  import {
5
+ buildLockPageUrl,
6
+ isOnLockPage,
6
7
  validateConfig
7
- } from "../chunk-6PUA5YXP.js";
8
+ } from "../chunk-4JGYMZTR.js";
8
9
  import {
9
10
  checkLockStatus
10
11
  } from "../chunk-5DEXVBY6.js";
@@ -52,6 +53,9 @@ function createAppwardenMiddleware(configFn) {
52
53
  if (hasError) {
53
54
  return next();
54
55
  }
56
+ if (isOnLockPage(config.lockPageSlug, request.url)) {
57
+ return next();
58
+ }
55
59
  const result = await checkLockStatus({
56
60
  request,
57
61
  appwardenApiToken: config.appwardenApiToken,
@@ -1,10 +1,11 @@
1
1
  import {
2
- buildLockPageUrl,
3
2
  createRedirect
4
- } from "../chunk-N6AUTMZO.js";
3
+ } from "../chunk-6M7BE3AW.js";
5
4
  import {
5
+ buildLockPageUrl,
6
+ isOnLockPage,
6
7
  validateConfig
7
- } from "../chunk-6PUA5YXP.js";
8
+ } from "../chunk-4JGYMZTR.js";
8
9
  import {
9
10
  checkLockStatus
10
11
  } from "../chunk-5DEXVBY6.js";
@@ -55,6 +56,9 @@ function createAppwardenMiddleware(configFn) {
55
56
  if (hasError) {
56
57
  return next();
57
58
  }
59
+ if (isOnLockPage(config.lockPageSlug, request.url)) {
60
+ return next();
61
+ }
58
62
  const result = await checkLockStatus({
59
63
  request,
60
64
  appwardenApiToken: config.appwardenApiToken,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@appwarden/middleware",
3
- "version": "2.0.0",
3
+ "version": "3.0.1",
4
4
  "description": "Instantly shut off access your app deployed on Cloudflare or Vercel",
5
5
  "type": "module",
6
6
  "license": "MIT",
@@ -63,11 +63,19 @@
63
63
  "zod": "^3.25.76"
64
64
  },
65
65
  "peerDependencies": {
66
+ "@astrojs/cloudflare": ">=11.0.0",
66
67
  "@opennextjs/cloudflare": ">=1.0.0",
67
68
  "@vercel/functions": ">=1.0.0",
69
+ "astro": ">=4.0.0",
68
70
  "next": ">=14"
69
71
  },
70
72
  "peerDependenciesMeta": {
73
+ "astro": {
74
+ "optional": true
75
+ },
76
+ "@astrojs/cloudflare": {
77
+ "optional": true
78
+ },
71
79
  "next": {
72
80
  "optional": true
73
81
  },
@@ -94,7 +102,8 @@
94
102
  "jws@=4.0.0": ">=4.0.1",
95
103
  "@smithy/config-resolver@<4.4.0": ">=4.4.0",
96
104
  "@isaacs/brace-expansion@<=5.0.0": ">=5.0.1",
97
- "npm@<=11.8.0": ">=11.9.0"
105
+ "npm@<=11.8.0": ">=11.9.0",
106
+ "wrangler@>=4.0.0 <4.59.1": ">=4.59.1"
98
107
  }
99
108
  }
100
109
  }
package/vercel.js CHANGED
@@ -3,8 +3,9 @@ import {
3
3
  isValidCacheUrl
4
4
  } from "./chunk-QEFORWCW.js";
5
5
  import {
6
+ isOnLockPage,
6
7
  validateConfig
7
- } from "./chunk-6PUA5YXP.js";
8
+ } from "./chunk-4JGYMZTR.js";
8
9
  import {
9
10
  LockValue,
10
11
  MemoryCache
@@ -210,6 +211,9 @@ function createAppwardenMiddleware(config) {
210
211
  if (!parsedConfig.lockPageSlug) {
211
212
  return NextResponse.next();
212
213
  }
214
+ if (isOnLockPage(parsedConfig.lockPageSlug, request.url)) {
215
+ return NextResponse.next();
216
+ }
213
217
  const provider = isCacheUrl.edgeConfig(parsedConfig.cacheUrl) ? "edge-config" : "upstash";
214
218
  const cacheValue = memoryCache.get(APPWARDEN_CACHE_KEY);
215
219
  const shouldRecheck = MemoryCache.isExpired(cacheValue);
package/chunk-6PUA5YXP.js DELETED
@@ -1,27 +0,0 @@
1
- import {
2
- getErrors
3
- } from "./chunk-B5IE7V77.js";
4
- import {
5
- printMessage
6
- } from "./chunk-7UTT3M2S.js";
7
-
8
- // src/utils/validate-config.ts
9
- function validateConfig(config, schema) {
10
- const result = schema.safeParse(config);
11
- const hasErrors = !result.success;
12
- if (hasErrors) {
13
- const mappedErrors = getErrors(result.error);
14
- if (mappedErrors.length > 0) {
15
- for (const error of mappedErrors) {
16
- console.error(printMessage(error));
17
- }
18
- } else {
19
- console.error(printMessage(result.error.message));
20
- }
21
- }
22
- return hasErrors;
23
- }
24
-
25
- export {
26
- validateConfig
27
- };