nyte 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (78) hide show
  1. package/LICENSE +13 -0
  2. package/README.md +59 -0
  3. package/dist/adapters/express.d.ts +7 -0
  4. package/dist/adapters/express.js +63 -0
  5. package/dist/adapters/factory.d.ts +23 -0
  6. package/dist/adapters/factory.js +121 -0
  7. package/dist/adapters/fastify.d.ts +25 -0
  8. package/dist/adapters/fastify.js +61 -0
  9. package/dist/adapters/native.d.ts +8 -0
  10. package/dist/adapters/native.js +200 -0
  11. package/dist/api/console.d.ts +81 -0
  12. package/dist/api/console.js +318 -0
  13. package/dist/api/http.d.ts +180 -0
  14. package/dist/api/http.js +469 -0
  15. package/dist/bin/nytejs.d.ts +2 -0
  16. package/dist/bin/nytejs.js +277 -0
  17. package/dist/builder.d.ts +32 -0
  18. package/dist/builder.js +634 -0
  19. package/dist/client/DefaultNotFound.d.ts +1 -0
  20. package/dist/client/DefaultNotFound.js +79 -0
  21. package/dist/client/client.d.ts +4 -0
  22. package/dist/client/client.js +27 -0
  23. package/dist/client/clientRouter.d.ts +58 -0
  24. package/dist/client/clientRouter.js +132 -0
  25. package/dist/client/entry.client.d.ts +1 -0
  26. package/dist/client/entry.client.js +455 -0
  27. package/dist/client/rpc.d.ts +8 -0
  28. package/dist/client/rpc.js +97 -0
  29. package/dist/components/Link.d.ts +7 -0
  30. package/dist/components/Link.js +13 -0
  31. package/dist/global/global.d.ts +117 -0
  32. package/dist/global/global.js +17 -0
  33. package/dist/helpers.d.ts +20 -0
  34. package/dist/helpers.js +604 -0
  35. package/dist/hotReload.d.ts +32 -0
  36. package/dist/hotReload.js +545 -0
  37. package/dist/index.d.ts +18 -0
  38. package/dist/index.js +515 -0
  39. package/dist/loaders.d.ts +1 -0
  40. package/dist/loaders.js +138 -0
  41. package/dist/renderer.d.ts +14 -0
  42. package/dist/renderer.js +380 -0
  43. package/dist/router.d.ts +101 -0
  44. package/dist/router.js +659 -0
  45. package/dist/rpc/server.d.ts +11 -0
  46. package/dist/rpc/server.js +166 -0
  47. package/dist/rpc/types.d.ts +22 -0
  48. package/dist/rpc/types.js +20 -0
  49. package/dist/types/framework.d.ts +37 -0
  50. package/dist/types/framework.js +2 -0
  51. package/dist/types.d.ts +218 -0
  52. package/dist/types.js +2 -0
  53. package/package.json +87 -0
  54. package/src/adapters/express.ts +87 -0
  55. package/src/adapters/factory.ts +112 -0
  56. package/src/adapters/fastify.ts +104 -0
  57. package/src/adapters/native.ts +245 -0
  58. package/src/api/console.ts +348 -0
  59. package/src/api/http.ts +535 -0
  60. package/src/bin/nytejs.js +331 -0
  61. package/src/builder.js +690 -0
  62. package/src/client/DefaultNotFound.tsx +119 -0
  63. package/src/client/client.ts +24 -0
  64. package/src/client/clientRouter.ts +153 -0
  65. package/src/client/entry.client.tsx +529 -0
  66. package/src/client/rpc.ts +101 -0
  67. package/src/components/Link.tsx +38 -0
  68. package/src/global/global.ts +171 -0
  69. package/src/helpers.ts +657 -0
  70. package/src/hotReload.ts +566 -0
  71. package/src/index.ts +582 -0
  72. package/src/loaders.js +160 -0
  73. package/src/renderer.tsx +421 -0
  74. package/src/router.ts +732 -0
  75. package/src/rpc/server.ts +190 -0
  76. package/src/rpc/types.ts +45 -0
  77. package/src/types/framework.ts +58 -0
  78. package/src/types.ts +288 -0
@@ -0,0 +1,166 @@
1
+ "use strict";
2
+ /*
3
+ * This file is part of the Nyte.js Project.
4
+ * Copyright (c) 2026 itsmuzin
5
+ *
6
+ * Licensed under the Apache License, Version 2.0 (the "License");
7
+ * you may not use this file except in compliance with the License.
8
+ * You may obtain a copy of the License at
9
+ *
10
+ * http://www.apache.org/licenses/LICENSE-2.0
11
+ *
12
+ * Unless required by applicable law or agreed to in writing, software
13
+ * distributed under the License is distributed on an "AS IS" BASIS,
14
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ * See the License for the specific language governing permissions and
16
+ * limitations under the License.
17
+ */
18
+ var __importDefault = (this && this.__importDefault) || function (mod) {
19
+ return (mod && mod.__esModule) ? mod : { "default": mod };
20
+ };
21
+ Object.defineProperty(exports, "__esModule", { value: true });
22
+ exports.executeRpc = executeRpc;
23
+ const fs_1 = __importDefault(require("fs"));
24
+ const path_1 = __importDefault(require("path"));
25
+ const http_1 = require("../api/http");
26
+ const DEFAULT_ALLOWED_SERVER_DIRS = ['src/backend'];
27
+ function normalizeToPosix(p) {
28
+ return p.replace(/\\/g, '/');
29
+ }
30
+ function isDisallowedPathInput(file) {
31
+ if (!file)
32
+ return true;
33
+ if (file.includes('\u0000'))
34
+ return true;
35
+ // disallow protocol-like or absolute paths (Windows drive letters included)
36
+ if (/^[a-zA-Z]+:/.test(file))
37
+ return true;
38
+ if (file.startsWith('/') || file.startsWith('\\'))
39
+ return true;
40
+ return false;
41
+ }
42
+ function validatePayload(payload) {
43
+ return (payload &&
44
+ typeof payload === 'object' &&
45
+ typeof payload.file === 'string' &&
46
+ typeof payload.fn === 'string' &&
47
+ Array.isArray(payload.args));
48
+ }
49
+ function tryResolveWithinAllowedDirs(projectDir, allowedDirs, requestedFile) {
50
+ const req = requestedFile.replace(/\\/g, '/').replace(/^\.(?:\/|\\)/, '');
51
+ for (const d of allowedDirs) {
52
+ const baseAbs = path_1.default.resolve(projectDir, d);
53
+ // Interpret client path as relative to src/web (where it's typically authored)
54
+ const fromWebAbs = path_1.default.resolve(projectDir, 'src/web', req);
55
+ // Map: <project>/src/backend/* (coming from ../../backend/* from web code)
56
+ const mappedFromWebAbs = fromWebAbs.replace(path_1.default.resolve(projectDir, 'backend') + path_1.default.sep, path_1.default.resolve(projectDir, 'src', 'backend') + path_1.default.sep);
57
+ // Also accept callers passing a backend-relative path like "./auth" or "auth"
58
+ const fromBackendAbs = path_1.default.resolve(baseAbs, req);
59
+ const candidateAbsList = [mappedFromWebAbs, fromBackendAbs];
60
+ for (const candidateAbs of candidateAbsList) {
61
+ const baseWithSep = baseAbs.endsWith(path_1.default.sep) ? baseAbs : baseAbs + path_1.default.sep;
62
+ if (!candidateAbs.startsWith(baseWithSep) && candidateAbs !== baseAbs)
63
+ continue;
64
+ if (!fs_1.default.existsSync(baseAbs))
65
+ continue;
66
+ return candidateAbs;
67
+ }
68
+ }
69
+ return null;
70
+ }
71
+ function toCookies(cookieHeader) {
72
+ if (!cookieHeader)
73
+ return {};
74
+ const out = {};
75
+ for (const part of cookieHeader.split(';')) {
76
+ const idx = part.indexOf('=');
77
+ if (idx === -1)
78
+ continue;
79
+ const k = part.slice(0, idx).trim();
80
+ const v = part.slice(idx + 1).trim();
81
+ if (k)
82
+ out[k] = v;
83
+ }
84
+ return out;
85
+ }
86
+ // Keep this for fallback when ctx.request isn't provided
87
+ function buildRpcRequestFromPayload(payload) {
88
+ const headers = {};
89
+ const rawHeaders = payload.request?.headers || {};
90
+ for (const [k, v] of Object.entries(rawHeaders)) {
91
+ headers[k.toLowerCase()] = v;
92
+ }
93
+ const cookieHeader = headers['cookie'] ?? undefined;
94
+ const req = {
95
+ method: payload.request?.method || 'RPC',
96
+ url: payload.request?.url || 'http://localhost/_rpc',
97
+ headers,
98
+ body: null,
99
+ query: {},
100
+ params: {},
101
+ cookies: payload.request?.cookies || toCookies(cookieHeader),
102
+ raw: null
103
+ };
104
+ return new http_1.NyteRequest(req);
105
+ }
106
+ async function executeRpc(ctx, payload) {
107
+ try {
108
+ if (!validatePayload(payload)) {
109
+ return { success: false, error: 'Invalid RPC payload' };
110
+ }
111
+ const fileInput = payload.file;
112
+ if (isDisallowedPathInput(fileInput)) {
113
+ return { success: false, error: 'Invalid file path' };
114
+ }
115
+ const allowedDirs = (ctx.allowedServerDirs || [...DEFAULT_ALLOWED_SERVER_DIRS]).map(normalizeToPosix);
116
+ const absFile = tryResolveWithinAllowedDirs(ctx.projectDir, allowedDirs, fileInput);
117
+ if (!absFile) {
118
+ return { success: false, error: 'File not allowed for RPC' };
119
+ }
120
+ if (!absFile.startsWith(path_1.default.resolve(ctx.projectDir) + path_1.default.sep)) {
121
+ return { success: false, error: 'Invalid file path' };
122
+ }
123
+ // Ensure fresh code in dev
124
+ try {
125
+ const resolved = require.resolve(absFile);
126
+ if (require.cache[resolved])
127
+ delete require.cache[resolved];
128
+ }
129
+ catch {
130
+ // ignore
131
+ }
132
+ let mod;
133
+ try {
134
+ mod = require(absFile);
135
+ }
136
+ catch {
137
+ // try again letting require do extension resolution from absFile without explicit extension
138
+ try {
139
+ mod = require(absFile);
140
+ }
141
+ catch {
142
+ return { success: false, error: 'RPC file not found' };
143
+ }
144
+ }
145
+ // Support multiple TS/CJS interop shapes:
146
+ // - module.exports.fn
147
+ // - exports.fn
148
+ // - module.exports.default (function)
149
+ // - module.exports.default.fn
150
+ const fnName = payload.fn;
151
+ const fnValue = (mod && typeof mod[fnName] === 'function' && mod[fnName]) ||
152
+ (mod?.default && typeof mod.default === 'function' && fnName === 'default' && mod.default) ||
153
+ (mod?.default && typeof mod.default[fnName] === 'function' && mod.default[fnName]) ||
154
+ undefined;
155
+ if (typeof fnValue !== 'function') {
156
+ return { success: false, error: `RPC function not found: ${fnName}` };
157
+ }
158
+ const rpcRequest = ctx.request ? new http_1.NyteRequest(ctx.request) : buildRpcRequestFromPayload(payload);
159
+ const result = await fnValue(rpcRequest, ...payload.args);
160
+ return { success: true, return: result };
161
+ }
162
+ catch (err) {
163
+ const message = typeof err?.message === 'string' ? err.message : 'Unknown RPC error';
164
+ return { success: false, error: message };
165
+ }
166
+ }
@@ -0,0 +1,22 @@
1
+ export declare const RPC_ENDPOINT: "/api/rpc";
2
+ export type RpcArgs = unknown[];
3
+ export interface RpcRequestPayload {
4
+ file: string;
5
+ fn: string;
6
+ args: RpcArgs;
7
+ request?: {
8
+ url?: string;
9
+ method?: string;
10
+ headers?: Record<string, string>;
11
+ cookies?: Record<string, string>;
12
+ };
13
+ }
14
+ export type RpcSuccessResponse = {
15
+ success: true;
16
+ return: unknown;
17
+ };
18
+ export type RpcErrorResponse = {
19
+ success: false;
20
+ error: string;
21
+ };
22
+ export type RpcResponsePayload = RpcSuccessResponse | RpcErrorResponse;
@@ -0,0 +1,20 @@
1
+ "use strict";
2
+ /*
3
+ * This file is part of the Nyte.js Project.
4
+ * Copyright (c) 2026 itsmuzin
5
+ *
6
+ * Licensed under the Apache License, Version 2.0 (the "License");
7
+ * you may not use this file except in compliance with the License.
8
+ * You may obtain a copy of the License at
9
+ *
10
+ * http://www.apache.org/licenses/LICENSE-2.0
11
+ *
12
+ * Unless required by applicable law or agreed to in writing, software
13
+ * distributed under the License is distributed on an "AS IS" BASIS,
14
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ * See the License for the specific language governing permissions and
16
+ * limitations under the License.
17
+ */
18
+ Object.defineProperty(exports, "__esModule", { value: true });
19
+ exports.RPC_ENDPOINT = void 0;
20
+ exports.RPC_ENDPOINT = '/api/rpc';
@@ -0,0 +1,37 @@
1
+ export interface GenericRequest {
2
+ method: string;
3
+ url: string;
4
+ headers: Record<string, string | string[]>;
5
+ body?: any;
6
+ query?: Record<string, any>;
7
+ params?: Record<string, string>;
8
+ cookies?: Record<string, string>;
9
+ raw?: any;
10
+ }
11
+ export interface GenericResponse {
12
+ status(code: number): GenericResponse;
13
+ header(name: string, value: string): GenericResponse;
14
+ cookie(name: string, value: string, options?: CookieOptions): GenericResponse;
15
+ clearCookie(name: string, options?: CookieOptions): GenericResponse;
16
+ json(data: any): void;
17
+ text(data: string): void;
18
+ send(data: any): void;
19
+ redirect(url: string): void;
20
+ raw?: any;
21
+ }
22
+ export interface CookieOptions {
23
+ domain?: string;
24
+ expires?: Date;
25
+ httpOnly?: boolean;
26
+ maxAge?: number;
27
+ path?: string;
28
+ secure?: boolean;
29
+ signed?: boolean;
30
+ sameSite?: boolean | 'lax' | 'strict' | 'none';
31
+ }
32
+ export type FrameworkType = 'express' | 'fastify' | 'native';
33
+ export interface FrameworkAdapter {
34
+ type: FrameworkType;
35
+ parseRequest(req: any): GenericRequest;
36
+ createResponse(res: any): GenericResponse;
37
+ }
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1,218 @@
1
+ import type { ComponentType } from 'react';
2
+ import type { GenericRequest } from './types/framework';
3
+ import { NyteRequest, NyteResponse } from "./api/http";
4
+ import { WebSocket } from 'ws';
5
+ import { IncomingMessage } from 'http';
6
+ export interface WebSocketContext {
7
+ ws: WebSocket;
8
+ req: IncomingMessage;
9
+ nyteReq: NyteRequest;
10
+ url: URL;
11
+ params: Record<string, string>;
12
+ query: Record<string, string>;
13
+ send: (data: any) => void;
14
+ close: (code?: number, reason?: string) => void;
15
+ broadcast: (data: any, exclude?: WebSocket[]) => void;
16
+ }
17
+ export interface NyteOptions {
18
+ dev?: boolean;
19
+ hostname?: string;
20
+ port?: number;
21
+ dir?: string;
22
+ framework?: 'express' | 'fastify' | 'native';
23
+ ssl?: {
24
+ redirectPort: number;
25
+ key: string;
26
+ cert: string;
27
+ ca?: string;
28
+ };
29
+ }
30
+ /**
31
+ * Interface para as configurações avançadas do servidor NyteJS.
32
+ * Essas configurações podem ser definidas no arquivo nytejs.config.js
33
+ */
34
+ export interface NyteConfig {
35
+ /**
36
+ * Limita o número máximo de headers HTTP permitidos por requisição.
37
+ * Padrão: 100
38
+ */
39
+ maxHeadersCount?: number;
40
+ /**
41
+ * Timeout em milissegundos para receber os headers HTTP.
42
+ * Padrão: 60000 (60 segundos)
43
+ */
44
+ headersTimeout?: number;
45
+ /**
46
+ * Timeout em milissegundos para uma requisição completa.
47
+ * Padrão: 30000 (30 segundos)
48
+ */
49
+ requestTimeout?: number;
50
+ /**
51
+ * Timeout geral do servidor em milissegundos.
52
+ * Padrão: 35000 (35 segundos)
53
+ */
54
+ serverTimeout?: number;
55
+ /**
56
+ * Timeout por requisição individual em milissegundos.
57
+ * Padrão: 30000 (30 segundos)
58
+ */
59
+ individualRequestTimeout?: number;
60
+ /**
61
+ * Tamanho máximo permitido para a URL em caracteres.
62
+ * Padrão: 2048
63
+ */
64
+ maxUrlLength?: number;
65
+ /**
66
+ * Habilita o log de acesso HTTP (ex: GET /api/users 200 15ms).
67
+ * Padrão: false
68
+ */
69
+ accessLogging?: boolean;
70
+ /**
71
+ * Configurações de CORS (Cross-Origin Resource Sharing).
72
+ * Define quais origens podem acessar seus recursos.
73
+ */
74
+ cors?: {
75
+ /**
76
+ * Origens permitidas. Pode ser:
77
+ * - Uma string específica: 'https://exemplo.com'
78
+ * - Um array de strings: ['https://exemplo.com', 'https://outro.com']
79
+ * - Um wildcard: '*' (permite todas as origens - não recomendado em produção)
80
+ * - Uma função que retorna boolean: (origin) => origin.endsWith('.exemplo.com')
81
+ */
82
+ origin?: string | string[] | ((origin: string) => boolean);
83
+ /**
84
+ * Métodos HTTP permitidos.
85
+ * Padrão: ['GET', 'POST', 'PUT', 'DELETE', 'PATCH', 'OPTIONS']
86
+ */
87
+ methods?: string[];
88
+ /**
89
+ * Headers permitidos nas requisições.
90
+ * Padrão: ['Content-Type', 'Authorization']
91
+ */
92
+ allowedHeaders?: string[];
93
+ /**
94
+ * Headers que serão expostos ao cliente.
95
+ * Padrão: []
96
+ */
97
+ exposedHeaders?: string[];
98
+ /**
99
+ * Permite o envio de credenciais (cookies, headers de autenticação).
100
+ * Padrão: false
101
+ */
102
+ credentials?: boolean;
103
+ /**
104
+ * Tempo em segundos que o navegador deve cachear a resposta preflight.
105
+ * Padrão: 86400 (24 horas)
106
+ */
107
+ maxAge?: number;
108
+ /**
109
+ * Habilita ou desabilita completamente o CORS.
110
+ * Padrão: false
111
+ */
112
+ enabled?: boolean;
113
+ };
114
+ /**
115
+ * Configurações de segurança de headers HTTP.
116
+ */
117
+ security?: {
118
+ /**
119
+ * Content-Security-Policy: Define de onde o navegador pode carregar recursos.
120
+ * Exemplo: "default-src 'self'; script-src 'self' 'unsafe-inline'"
121
+ */
122
+ contentSecurityPolicy?: string;
123
+ /**
124
+ * Permissions-Policy: Controla quais recursos e APIs o navegador pode usar.
125
+ * Exemplo: "geolocation=(), microphone=()"
126
+ */
127
+ permissionsPolicy?: string;
128
+ /**
129
+ * Strict-Transport-Security: Força o uso de HTTPS.
130
+ * Padrão (quando SSL ativo): "max-age=31536000; includeSubDomains"
131
+ * Exemplo: "max-age=63072000; includeSubDomains; preload"
132
+ */
133
+ strictTransportSecurity?: string;
134
+ };
135
+ /**
136
+ * Headers HTTP personalizados que serão adicionados a todas as respostas.
137
+ * Exemplo: { 'X-Custom-Header': 'value', 'X-Powered-By': 'Nyte.js' }
138
+ */
139
+ customHeaders?: Record<string, string>;
140
+ }
141
+ /**
142
+ * Tipo da função de configuração que pode ser exportada no nytejs.config.js
143
+ */
144
+ export type NyteConfigFunction = (phase: string, context: {
145
+ defaultConfig: NyteConfig;
146
+ }) => NyteConfig | Promise<NyteConfig>;
147
+ export interface Metadata {
148
+ title?: string;
149
+ description?: string;
150
+ keywords?: string | string[];
151
+ author?: string;
152
+ favicon?: string;
153
+ viewport?: string;
154
+ themeColor?: string;
155
+ canonical?: string;
156
+ robots?: string;
157
+ openGraph?: {
158
+ title?: string;
159
+ description?: string;
160
+ type?: string;
161
+ url?: string;
162
+ image?: string | {
163
+ url: string;
164
+ width?: number;
165
+ height?: number;
166
+ alt?: string;
167
+ };
168
+ siteName?: string;
169
+ locale?: string;
170
+ };
171
+ twitter?: {
172
+ card?: 'summary' | 'summary_large_image' | 'app' | 'player';
173
+ site?: string;
174
+ creator?: string;
175
+ title?: string;
176
+ description?: string;
177
+ image?: string;
178
+ imageAlt?: string;
179
+ };
180
+ language?: string;
181
+ charset?: string;
182
+ appleTouchIcon?: string;
183
+ manifest?: string;
184
+ other?: Record<string, string>;
185
+ }
186
+ export interface RouteConfig {
187
+ pattern: string;
188
+ component: ComponentType<any>;
189
+ generateMetadata?: (params: any, req: GenericRequest) => Promise<Metadata> | Metadata;
190
+ }
191
+ export type RequestHandler = (req: any, res: any) => Promise<void>;
192
+ /**
193
+ * Define o formato de uma função que manipula uma rota da API.
194
+ */
195
+ export type BackendHandler = (request: NyteRequest, // HWebRequest será importado onde necessário
196
+ params: {
197
+ [key: string]: string;
198
+ }) => Promise<NyteResponse> | NyteResponse;
199
+ export type NyteMiddleware = (request: NyteRequest, // HWebRequest será importado onde necessário
200
+ params: {
201
+ [key: string]: string;
202
+ }, next: () => Promise<NyteResponse>) => Promise<NyteResponse> | NyteResponse;
203
+ /**
204
+ * Define o formato de uma função que manipula uma rota WebSocket.
205
+ */
206
+ export type WebSocketHandler = (context: WebSocketContext) => Promise<void> | void;
207
+ /**
208
+ * Define a estrutura de cada rota da API, com suporte para métodos HTTP e WebSocket.
209
+ */
210
+ export interface BackendRouteConfig {
211
+ pattern: string;
212
+ GET?: BackendHandler;
213
+ POST?: BackendHandler;
214
+ PUT?: BackendHandler;
215
+ DELETE?: BackendHandler;
216
+ WS?: WebSocketHandler;
217
+ middleware?: NyteMiddleware[];
218
+ }
package/dist/types.js ADDED
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
package/package.json ADDED
@@ -0,0 +1,87 @@
1
+ {
2
+ "name": "nyte",
3
+ "version": "1.0.0",
4
+ "description": "Nyte.js is a high-level framework for building web applications with ease and speed. It provides a robust set of tools and features to streamline development and enhance productivity.",
5
+ "main": "dist/index.js",
6
+ "types": "dist/index.d.ts",
7
+ "author": "itsmuzin",
8
+ "license": "Apache-2.0",
9
+ "keywords": [
10
+ "nightjs",
11
+ "nytejs",
12
+ "nyte",
13
+ "framework",
14
+ "web",
15
+ "typescript",
16
+ "react"
17
+ ],
18
+ "files": [
19
+ "dist",
20
+ "README.md",
21
+ "dist/global/global.d.ts",
22
+ "src"
23
+ ],
24
+ "bin": {
25
+ "nyte": "./dist/bin/nytejs.js"
26
+ },
27
+ "exports": {
28
+ ".": {
29
+ "types": "./dist/index.d.ts",
30
+ "import": "./dist/index.js",
31
+ "require": "./dist/index.js"
32
+ },
33
+ "./react": {
34
+ "types": "./dist/client/client.d.ts",
35
+ "import": "./dist/client/client.js",
36
+ "require": "./dist/client/client.js"
37
+ },
38
+ "./helpers": {
39
+ "types": "./dist/helpers.d.ts",
40
+ "import": "./dist/helpers.js",
41
+ "require": "./dist/helpers.js"
42
+ },
43
+ "./global": {
44
+ "types": "./dist/global/global.d.ts"
45
+ },
46
+ "./eslint": {
47
+ "types": "./dist/eslint/index.d.ts",
48
+ "import": "./dist/eslint/index.js",
49
+ "require": "./dist/eslint/index.js"
50
+ }
51
+ },
52
+ "peerDependencies": {
53
+ "react": "^19.2.0",
54
+ "react-dom": "^19.2.0"
55
+ },
56
+ "dependencies": {
57
+ "@fastify/cookie": "^11.0.2",
58
+ "@fastify/formbody": "^8.0.2",
59
+ "boxen": "^8.0.1",
60
+ "chokidar": "^3.5.3",
61
+ "commander": "^14.0.1",
62
+ "cookie-parser": "^1.4.7",
63
+ "esbuild": "^0.25.10",
64
+ "express": "^4.0.0",
65
+ "fastify": "^5.6.1",
66
+ "framer-motion": "^12.23.22",
67
+ "fs-extra": "^11.3.2",
68
+ "ws": "^8.18.1"
69
+ },
70
+ "devDependencies": {
71
+ "@types/express": "^4.17.21",
72
+ "@types/fs-extra": "^11.0.4",
73
+ "@types/node": "^20.19.27",
74
+ "@types/react": "^19.2.0",
75
+ "@types/react-dom": "^19.2.0",
76
+ "@types/ws": "^8.18.1",
77
+ "jest": "^30.1.3",
78
+ "ts-jest": "^29.4.4",
79
+ "@types/jest": "^30.0.0",
80
+ "ts-loader": "^9.5.4",
81
+ "ts-node": "^10.9.2",
82
+ "typescript": "^5.9.3"
83
+ },
84
+ "scripts": {
85
+ "build": "tsc"
86
+ }
87
+ }
@@ -0,0 +1,87 @@
1
+ /*
2
+ * This file is part of the Nyte.js Project.
3
+ * Copyright (c) 2026 itsmuzin
4
+ *
5
+ * Licensed under the Apache License, Version 2.0 (the "License");
6
+ * you may not use this file except in compliance with the License.
7
+ * You may obtain a copy of the License at
8
+ *
9
+ * http://www.apache.org/licenses/LICENSE-2.0
10
+ *
11
+ * Unless required by applicable law or agreed to in writing, software
12
+ * distributed under the License is distributed on an "AS IS" BASIS,
13
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
+ * See the License for the specific language governing permissions and
15
+ * limitations under the License.
16
+ */
17
+ import type { Request as ExpressRequest, Response as ExpressResponse } from 'express';
18
+ import { GenericRequest, GenericResponse, FrameworkAdapter, CookieOptions } from '../types/framework';
19
+
20
+ export class ExpressAdapter implements FrameworkAdapter {
21
+ type = 'express' as const;
22
+
23
+ parseRequest(req: ExpressRequest): GenericRequest {
24
+
25
+ return {
26
+ method: req.method,
27
+ url: req.url,
28
+ headers: req.headers as Record<string, string | string[]>,
29
+ body: req.body,
30
+ query: req.query as Record<string, any>,
31
+ params: req.params,
32
+ cookies: req.cookies || {},
33
+ raw: req,
34
+ };
35
+ }
36
+
37
+ createResponse(res: ExpressResponse): GenericResponse {
38
+ return new ExpressResponseWrapper(res);
39
+ }
40
+ }
41
+
42
+ class ExpressResponseWrapper implements GenericResponse {
43
+ constructor(private res: ExpressResponse) {}
44
+
45
+ get raw() {
46
+ return this.res;
47
+ }
48
+
49
+ status(code: number): GenericResponse {
50
+ this.res.status(code);
51
+ return this;
52
+ }
53
+
54
+ header(name: string, value: string): GenericResponse {
55
+ this.res.setHeader(name, value);
56
+ return this;
57
+ }
58
+
59
+ cookie(name: string, value: string, options?: CookieOptions): GenericResponse {
60
+ this.res.cookie(name, value, options || {});
61
+ return this;
62
+ }
63
+
64
+ clearCookie(name: string, options?: CookieOptions): GenericResponse {
65
+ // Filter out the deprecated 'expires' option to avoid Express deprecation warning
66
+ const { expires, ...filteredOptions } = options || {};
67
+ this.res.clearCookie(name, filteredOptions);
68
+ return this;
69
+ }
70
+
71
+ json(data: any): void {
72
+ this.res.json(data);
73
+ }
74
+
75
+ text(data: string): void {
76
+ this.res.setHeader('Content-Type', 'text/plain; charset=utf-8');
77
+ this.res.send(data);
78
+ }
79
+
80
+ send(data: any): void {
81
+ this.res.send(data);
82
+ }
83
+
84
+ redirect(url: string): void {
85
+ this.res.redirect(url);
86
+ }
87
+ }