@lytjs/runtime-edge 6.5.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 ADDED
@@ -0,0 +1,104 @@
1
+ # @lytjs/runtime-edge
2
+
3
+ LytJS 边缘运行时支持,为边缘计算环境提供完整的支持。
4
+
5
+ ## 安装
6
+
7
+ ```bash
8
+ pnpm add @lytjs/runtime-edge
9
+ ```
10
+
11
+ ## 快速开始
12
+
13
+ ### 边缘路由器
14
+
15
+ ```typescript
16
+ import { createEdgeRouter } from '@lytjs/runtime-edge';
17
+
18
+ const router = createEdgeRouter({
19
+ basePath: '/api',
20
+ });
21
+
22
+ router.get('/users', (req, ctx) => {
23
+ return new Response(JSON.stringify({ users: [] }), {
24
+ status: 200,
25
+ headers: { 'Content-Type': 'application/json' },
26
+ });
27
+ });
28
+
29
+ export default {
30
+ async fetch(request, env, ctx) {
31
+ return router.handle(request, ctx);
32
+ },
33
+ };
34
+ ```
35
+
36
+ ### 边缘缓存
37
+
38
+ ```typescript
39
+ import { createEdgeCache } from '@lytjs/runtime-edge';
40
+
41
+ const cache = createEdgeCache();
42
+
43
+ // 设置缓存
44
+ await cache.set('key', { data: 'value' }, { ttl: 60000 });
45
+
46
+ // 获取缓存
47
+ const value = await cache.get('key');
48
+ ```
49
+
50
+ ### 响应辅助工具
51
+
52
+ ```typescript
53
+ import { jsonResponse, textResponse, htmlResponse, redirectResponse } from '@lytjs/runtime-edge';
54
+
55
+ // JSON 响应
56
+ return jsonResponse({ success: true }, 200);
57
+
58
+ // 文本响应
59
+ return textResponse('Hello World', 200);
60
+
61
+ // HTML 响应
62
+ return htmlResponse('<html><body>Hello</body></html>', 200);
63
+
64
+ // 重定向响应
65
+ return redirectResponse('https://example.com', 302);
66
+ ```
67
+
68
+ ## 特性
69
+
70
+ - 边缘函数支持
71
+ - 边缘路由器
72
+ - 内存缓存
73
+ - 响应辅助工具
74
+ - 零外部依赖
75
+
76
+ ## API
77
+
78
+ ### createEdgeRouter(options)
79
+
80
+ 创建边缘路由器实例。
81
+
82
+ ### createEdgeCache()
83
+
84
+ 创建边缘缓存实例。
85
+
86
+ ### jsonResponse(data, status)
87
+
88
+ 创建 JSON 响应。
89
+
90
+ ### textResponse(text, status)
91
+
92
+ 创建文本响应。
93
+
94
+ ### htmlResponse(html, status)
95
+
96
+ 创建 HTML 响应。
97
+
98
+ ### redirectResponse(url, status)
99
+
100
+ 创建重定向响应。
101
+
102
+ ## 许可证
103
+
104
+ MIT
package/dist/index.cjs ADDED
@@ -0,0 +1,179 @@
1
+ "use strict";
2
+ var __defProp = Object.defineProperty;
3
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
+ var __getOwnPropNames = Object.getOwnPropertyNames;
5
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
6
+ var __export = (target, all) => {
7
+ for (var name in all)
8
+ __defProp(target, name, { get: all[name], enumerable: true });
9
+ };
10
+ var __copyProps = (to, from, except, desc) => {
11
+ if (from && typeof from === "object" || typeof from === "function") {
12
+ for (let key of __getOwnPropNames(from))
13
+ if (!__hasOwnProp.call(to, key) && key !== except)
14
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
15
+ }
16
+ return to;
17
+ };
18
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
19
+
20
+ // src/index.ts
21
+ var index_exports = {};
22
+ __export(index_exports, {
23
+ createEdgeCache: () => createEdgeCache,
24
+ createEdgeRouter: () => createEdgeRouter,
25
+ htmlResponse: () => htmlResponse,
26
+ jsonResponse: () => jsonResponse,
27
+ redirectResponse: () => redirectResponse,
28
+ textResponse: () => textResponse
29
+ });
30
+ module.exports = __toCommonJS(index_exports);
31
+ function createEdgeCache() {
32
+ const cache = /* @__PURE__ */ new Map();
33
+ return {
34
+ async get(key) {
35
+ const entry = cache.get(key);
36
+ if (!entry) return null;
37
+ if (entry.expires && Date.now() > entry.expires) {
38
+ cache.delete(key);
39
+ return null;
40
+ }
41
+ return entry.value;
42
+ },
43
+ async set(key, value, options = {}) {
44
+ const ttl = options.ttl ?? 6e4;
45
+ const entry = {
46
+ value,
47
+ expires: Date.now() + ttl
48
+ };
49
+ cache.set(key, entry);
50
+ },
51
+ async delete(key) {
52
+ cache.delete(key);
53
+ },
54
+ async clear() {
55
+ cache.clear();
56
+ },
57
+ async has(key) {
58
+ const entry = cache.get(key);
59
+ if (!entry) return false;
60
+ if (entry.expires && Date.now() > entry.expires) {
61
+ cache.delete(key);
62
+ return false;
63
+ }
64
+ return true;
65
+ }
66
+ };
67
+ }
68
+ function createEdgeRouter(options = {}) {
69
+ const routes = [];
70
+ const basePath = options.basePath ?? "";
71
+ function addRoute(method, path, handler) {
72
+ const fullPath = basePath + path;
73
+ routes.push({ path: fullPath, handler, method });
74
+ }
75
+ function match(request) {
76
+ const url = new URL(request.url);
77
+ const path = url.pathname;
78
+ const method = request.method.toUpperCase();
79
+ for (const route of routes) {
80
+ if (route.method === method && route.path === path) {
81
+ return route;
82
+ }
83
+ }
84
+ return null;
85
+ }
86
+ async function handle(request, context) {
87
+ const route = match(request);
88
+ if (!route) {
89
+ return {
90
+ status: 404,
91
+ statusText: "Not Found",
92
+ headers: { "Content-Type": "text/plain" }
93
+ };
94
+ }
95
+ try {
96
+ const response = await route.handler(
97
+ request,
98
+ context ?? {
99
+ waitUntil: () => {
100
+ },
101
+ passThroughOnException: () => {
102
+ }
103
+ }
104
+ );
105
+ return response;
106
+ } catch (error) {
107
+ console.error("Edge handler error:", error);
108
+ return {
109
+ status: 500,
110
+ statusText: "Internal Server Error",
111
+ headers: { "Content-Type": "text/plain" }
112
+ };
113
+ }
114
+ }
115
+ return {
116
+ get: (path, handler) => addRoute("GET", path, handler),
117
+ post: (path, handler) => addRoute("POST", path, handler),
118
+ put: (path, handler) => addRoute("PUT", path, handler),
119
+ delete: (path, handler) => addRoute("DELETE", path, handler),
120
+ patch: (path, handler) => addRoute("PATCH", path, handler),
121
+ match,
122
+ handle
123
+ };
124
+ }
125
+ function jsonResponse(data, status = 200) {
126
+ return {
127
+ status,
128
+ statusText: "OK",
129
+ headers: { "Content-Type": "application/json" },
130
+ body: new ReadableStream({
131
+ start(controller) {
132
+ controller.enqueue(new TextEncoder().encode(JSON.stringify(data)));
133
+ controller.close();
134
+ }
135
+ })
136
+ };
137
+ }
138
+ function textResponse(text, status = 200) {
139
+ return {
140
+ status,
141
+ statusText: "OK",
142
+ headers: { "Content-Type": "text/plain" },
143
+ body: new ReadableStream({
144
+ start(controller) {
145
+ controller.enqueue(new TextEncoder().encode(text));
146
+ controller.close();
147
+ }
148
+ })
149
+ };
150
+ }
151
+ function htmlResponse(html, status = 200) {
152
+ return {
153
+ status,
154
+ statusText: "OK",
155
+ headers: { "Content-Type": "text/html" },
156
+ body: new ReadableStream({
157
+ start(controller) {
158
+ controller.enqueue(new TextEncoder().encode(html));
159
+ controller.close();
160
+ }
161
+ })
162
+ };
163
+ }
164
+ function redirectResponse(location, status = 302) {
165
+ return {
166
+ status,
167
+ statusText: "Found",
168
+ headers: { Location: location }
169
+ };
170
+ }
171
+ // Annotate the CommonJS export names for ESM import in node:
172
+ 0 && (module.exports = {
173
+ createEdgeCache,
174
+ createEdgeRouter,
175
+ htmlResponse,
176
+ jsonResponse,
177
+ redirectResponse,
178
+ textResponse
179
+ });
@@ -0,0 +1,89 @@
1
+ /**
2
+ * @lytjs/runtime-edge - Type definitions
3
+ */
4
+ interface EdgeRequest {
5
+ url: string;
6
+ method: string;
7
+ headers: Record<string, string>;
8
+ body?: ReadableStream;
9
+ signal?: AbortSignal;
10
+ }
11
+ interface EdgeResponse {
12
+ status: number;
13
+ statusText: string;
14
+ headers: Record<string, string>;
15
+ body?: ReadableStream;
16
+ }
17
+ interface EdgeContext {
18
+ waitUntil(promise: Promise<unknown>): void;
19
+ passThroughOnException(): void;
20
+ }
21
+ interface EdgeHandler {
22
+ (request: EdgeRequest, context: EdgeContext): Promise<EdgeResponse> | EdgeResponse;
23
+ }
24
+ interface EdgeRouterOptions {
25
+ basePath?: string;
26
+ }
27
+ interface EdgeRoute {
28
+ path: string;
29
+ handler: EdgeHandler;
30
+ method: string;
31
+ }
32
+ interface EdgeRouter {
33
+ get(path: string, handler: EdgeHandler): void;
34
+ post(path: string, handler: EdgeHandler): void;
35
+ put(path: string, handler: EdgeHandler): void;
36
+ delete(path: string, handler: EdgeHandler): void;
37
+ patch(path: string, handler: EdgeHandler): void;
38
+ match(request: EdgeRequest): EdgeRoute | null;
39
+ handle(request: EdgeRequest, context?: EdgeContext): Promise<EdgeResponse>;
40
+ }
41
+ interface EdgeCacheOptions {
42
+ ttl?: number;
43
+ swr?: boolean;
44
+ staleWhileRevalidate?: number;
45
+ }
46
+ interface EdgeCacheEntry<T = unknown> {
47
+ value: T;
48
+ expires: number;
49
+ }
50
+ interface EdgeCache {
51
+ get<T>(key: string): Promise<T | null>;
52
+ set<T>(key: string, value: T, options?: EdgeCacheOptions): Promise<void>;
53
+ delete(key: string): Promise<void>;
54
+ clear(): Promise<void>;
55
+ has(key: string): Promise<boolean>;
56
+ }
57
+
58
+ /**
59
+ * @lytjs/runtime-edge - LytJS edge runtime support
60
+ *
61
+ * Provides utilities for running LytJS in edge computing environments
62
+ */
63
+
64
+ /**
65
+ * 创建内存边缘缓存
66
+ */
67
+ declare function createEdgeCache(): EdgeCache;
68
+ /**
69
+ * 创建边缘路由器
70
+ */
71
+ declare function createEdgeRouter(options?: EdgeRouterOptions): EdgeRouter;
72
+ /**
73
+ * 创建 JSON 响应
74
+ */
75
+ declare function jsonResponse(data: unknown, status?: number): EdgeResponse;
76
+ /**
77
+ * 创建文本响应
78
+ */
79
+ declare function textResponse(text: string, status?: number): EdgeResponse;
80
+ /**
81
+ * 创建 HTML 响应
82
+ */
83
+ declare function htmlResponse(html: string, status?: number): EdgeResponse;
84
+ /**
85
+ * 创建重定向响应
86
+ */
87
+ declare function redirectResponse(location: string, status?: number): EdgeResponse;
88
+
89
+ export { type EdgeCache, type EdgeCacheEntry, type EdgeCacheOptions, type EdgeContext, type EdgeHandler, type EdgeRequest, type EdgeResponse, type EdgeRoute, type EdgeRouter, type EdgeRouterOptions, createEdgeCache, createEdgeRouter, htmlResponse, jsonResponse, redirectResponse, textResponse };
@@ -0,0 +1,89 @@
1
+ /**
2
+ * @lytjs/runtime-edge - Type definitions
3
+ */
4
+ interface EdgeRequest {
5
+ url: string;
6
+ method: string;
7
+ headers: Record<string, string>;
8
+ body?: ReadableStream;
9
+ signal?: AbortSignal;
10
+ }
11
+ interface EdgeResponse {
12
+ status: number;
13
+ statusText: string;
14
+ headers: Record<string, string>;
15
+ body?: ReadableStream;
16
+ }
17
+ interface EdgeContext {
18
+ waitUntil(promise: Promise<unknown>): void;
19
+ passThroughOnException(): void;
20
+ }
21
+ interface EdgeHandler {
22
+ (request: EdgeRequest, context: EdgeContext): Promise<EdgeResponse> | EdgeResponse;
23
+ }
24
+ interface EdgeRouterOptions {
25
+ basePath?: string;
26
+ }
27
+ interface EdgeRoute {
28
+ path: string;
29
+ handler: EdgeHandler;
30
+ method: string;
31
+ }
32
+ interface EdgeRouter {
33
+ get(path: string, handler: EdgeHandler): void;
34
+ post(path: string, handler: EdgeHandler): void;
35
+ put(path: string, handler: EdgeHandler): void;
36
+ delete(path: string, handler: EdgeHandler): void;
37
+ patch(path: string, handler: EdgeHandler): void;
38
+ match(request: EdgeRequest): EdgeRoute | null;
39
+ handle(request: EdgeRequest, context?: EdgeContext): Promise<EdgeResponse>;
40
+ }
41
+ interface EdgeCacheOptions {
42
+ ttl?: number;
43
+ swr?: boolean;
44
+ staleWhileRevalidate?: number;
45
+ }
46
+ interface EdgeCacheEntry<T = unknown> {
47
+ value: T;
48
+ expires: number;
49
+ }
50
+ interface EdgeCache {
51
+ get<T>(key: string): Promise<T | null>;
52
+ set<T>(key: string, value: T, options?: EdgeCacheOptions): Promise<void>;
53
+ delete(key: string): Promise<void>;
54
+ clear(): Promise<void>;
55
+ has(key: string): Promise<boolean>;
56
+ }
57
+
58
+ /**
59
+ * @lytjs/runtime-edge - LytJS edge runtime support
60
+ *
61
+ * Provides utilities for running LytJS in edge computing environments
62
+ */
63
+
64
+ /**
65
+ * 创建内存边缘缓存
66
+ */
67
+ declare function createEdgeCache(): EdgeCache;
68
+ /**
69
+ * 创建边缘路由器
70
+ */
71
+ declare function createEdgeRouter(options?: EdgeRouterOptions): EdgeRouter;
72
+ /**
73
+ * 创建 JSON 响应
74
+ */
75
+ declare function jsonResponse(data: unknown, status?: number): EdgeResponse;
76
+ /**
77
+ * 创建文本响应
78
+ */
79
+ declare function textResponse(text: string, status?: number): EdgeResponse;
80
+ /**
81
+ * 创建 HTML 响应
82
+ */
83
+ declare function htmlResponse(html: string, status?: number): EdgeResponse;
84
+ /**
85
+ * 创建重定向响应
86
+ */
87
+ declare function redirectResponse(location: string, status?: number): EdgeResponse;
88
+
89
+ export { type EdgeCache, type EdgeCacheEntry, type EdgeCacheOptions, type EdgeContext, type EdgeHandler, type EdgeRequest, type EdgeResponse, type EdgeRoute, type EdgeRouter, type EdgeRouterOptions, createEdgeCache, createEdgeRouter, htmlResponse, jsonResponse, redirectResponse, textResponse };
package/dist/index.mjs ADDED
@@ -0,0 +1,149 @@
1
+ // src/index.ts
2
+ function createEdgeCache() {
3
+ const cache = /* @__PURE__ */ new Map();
4
+ return {
5
+ async get(key) {
6
+ const entry = cache.get(key);
7
+ if (!entry) return null;
8
+ if (entry.expires && Date.now() > entry.expires) {
9
+ cache.delete(key);
10
+ return null;
11
+ }
12
+ return entry.value;
13
+ },
14
+ async set(key, value, options = {}) {
15
+ const ttl = options.ttl ?? 6e4;
16
+ const entry = {
17
+ value,
18
+ expires: Date.now() + ttl
19
+ };
20
+ cache.set(key, entry);
21
+ },
22
+ async delete(key) {
23
+ cache.delete(key);
24
+ },
25
+ async clear() {
26
+ cache.clear();
27
+ },
28
+ async has(key) {
29
+ const entry = cache.get(key);
30
+ if (!entry) return false;
31
+ if (entry.expires && Date.now() > entry.expires) {
32
+ cache.delete(key);
33
+ return false;
34
+ }
35
+ return true;
36
+ }
37
+ };
38
+ }
39
+ function createEdgeRouter(options = {}) {
40
+ const routes = [];
41
+ const basePath = options.basePath ?? "";
42
+ function addRoute(method, path, handler) {
43
+ const fullPath = basePath + path;
44
+ routes.push({ path: fullPath, handler, method });
45
+ }
46
+ function match(request) {
47
+ const url = new URL(request.url);
48
+ const path = url.pathname;
49
+ const method = request.method.toUpperCase();
50
+ for (const route of routes) {
51
+ if (route.method === method && route.path === path) {
52
+ return route;
53
+ }
54
+ }
55
+ return null;
56
+ }
57
+ async function handle(request, context) {
58
+ const route = match(request);
59
+ if (!route) {
60
+ return {
61
+ status: 404,
62
+ statusText: "Not Found",
63
+ headers: { "Content-Type": "text/plain" }
64
+ };
65
+ }
66
+ try {
67
+ const response = await route.handler(
68
+ request,
69
+ context ?? {
70
+ waitUntil: () => {
71
+ },
72
+ passThroughOnException: () => {
73
+ }
74
+ }
75
+ );
76
+ return response;
77
+ } catch (error) {
78
+ console.error("Edge handler error:", error);
79
+ return {
80
+ status: 500,
81
+ statusText: "Internal Server Error",
82
+ headers: { "Content-Type": "text/plain" }
83
+ };
84
+ }
85
+ }
86
+ return {
87
+ get: (path, handler) => addRoute("GET", path, handler),
88
+ post: (path, handler) => addRoute("POST", path, handler),
89
+ put: (path, handler) => addRoute("PUT", path, handler),
90
+ delete: (path, handler) => addRoute("DELETE", path, handler),
91
+ patch: (path, handler) => addRoute("PATCH", path, handler),
92
+ match,
93
+ handle
94
+ };
95
+ }
96
+ function jsonResponse(data, status = 200) {
97
+ return {
98
+ status,
99
+ statusText: "OK",
100
+ headers: { "Content-Type": "application/json" },
101
+ body: new ReadableStream({
102
+ start(controller) {
103
+ controller.enqueue(new TextEncoder().encode(JSON.stringify(data)));
104
+ controller.close();
105
+ }
106
+ })
107
+ };
108
+ }
109
+ function textResponse(text, status = 200) {
110
+ return {
111
+ status,
112
+ statusText: "OK",
113
+ headers: { "Content-Type": "text/plain" },
114
+ body: new ReadableStream({
115
+ start(controller) {
116
+ controller.enqueue(new TextEncoder().encode(text));
117
+ controller.close();
118
+ }
119
+ })
120
+ };
121
+ }
122
+ function htmlResponse(html, status = 200) {
123
+ return {
124
+ status,
125
+ statusText: "OK",
126
+ headers: { "Content-Type": "text/html" },
127
+ body: new ReadableStream({
128
+ start(controller) {
129
+ controller.enqueue(new TextEncoder().encode(html));
130
+ controller.close();
131
+ }
132
+ })
133
+ };
134
+ }
135
+ function redirectResponse(location, status = 302) {
136
+ return {
137
+ status,
138
+ statusText: "Found",
139
+ headers: { Location: location }
140
+ };
141
+ }
142
+ export {
143
+ createEdgeCache,
144
+ createEdgeRouter,
145
+ htmlResponse,
146
+ jsonResponse,
147
+ redirectResponse,
148
+ textResponse
149
+ };
package/package.json ADDED
@@ -0,0 +1,48 @@
1
+ {
2
+ "name": "@lytjs/runtime-edge",
3
+ "version": "6.5.0",
4
+ "description": "LytJS edge runtime support for serverless and edge computing environments",
5
+ "type": "module",
6
+ "main": "./dist/index.cjs",
7
+ "module": "./dist/index.mjs",
8
+ "types": "./dist/index.d.ts",
9
+ "exports": {
10
+ ".": {
11
+ "types": "./dist/index.d.ts",
12
+ "import": "./dist/index.mjs",
13
+ "require": "./dist/index.cjs"
14
+ },
15
+ "./package.json": "./package.json"
16
+ },
17
+ "files": [
18
+ "dist"
19
+ ],
20
+ "sideEffects": false,
21
+ "scripts": {
22
+ "build": "tsup",
23
+ "dev": "tsup --watch",
24
+ "test": "vitest run",
25
+ "type-check": "tsc --noEmit",
26
+ "lint": "eslint \"src/**/*.ts\"",
27
+ "clean": "rm -rf dist"
28
+ },
29
+ "dependencies": {},
30
+ "devDependencies": {
31
+ "tsup": "^8.0.0",
32
+ "typescript": "^5.4.0",
33
+ "vitest": "^3.0.0"
34
+ },
35
+ "license": "MIT",
36
+ "repository": {
37
+ "type": "git",
38
+ "url": "https://gitee.com/lytjs/lytjs.git",
39
+ "directory": "packages/ecosystem/packages/runtime-edge"
40
+ },
41
+ "keywords": [
42
+ "lytjs",
43
+ "edge",
44
+ "serverless",
45
+ "runtime",
46
+ "edge-functions"
47
+ ]
48
+ }