abhijanb 0.1.0 → 0.1.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/auth.ts +71 -0
- package/index.ts +16 -12
- package/package.json +7 -4
- package/socket.ts +12 -5
- package/validate.ts +17 -0
- package/app.ts +0 -14
package/auth.ts
ADDED
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
import jwt from "jsonwebtoken";
|
|
2
|
+
import type { Request, Response, NextFunction } from "express";
|
|
3
|
+
|
|
4
|
+
const ACCESS_SECRET = process.env.JWT_ACCESS_SECRET || "access-secret";
|
|
5
|
+
const REFRESH_SECRET = process.env.JWT_REFRESH_SECRET || "refresh-secret";
|
|
6
|
+
const ACCESS_EXPIRY = "30m";
|
|
7
|
+
const REFRESH_EXPIRY = "30d";
|
|
8
|
+
|
|
9
|
+
/** Sign an access token */
|
|
10
|
+
export function signToken(
|
|
11
|
+
payload: object,
|
|
12
|
+
options?: { secret?: string; expiresIn?: string }
|
|
13
|
+
): string {
|
|
14
|
+
return jwt.sign(payload, options?.secret || ACCESS_SECRET, {
|
|
15
|
+
expiresIn: options?.expiresIn || ACCESS_EXPIRY,
|
|
16
|
+
});
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
/** Sign a refresh token */
|
|
20
|
+
export function signRefreshToken(
|
|
21
|
+
payload: object,
|
|
22
|
+
options?: { secret?: string; expiresIn?: string }
|
|
23
|
+
): string {
|
|
24
|
+
return jwt.sign(payload, options?.secret || REFRESH_SECRET, {
|
|
25
|
+
expiresIn: options?.expiresIn || REFRESH_EXPIRY,
|
|
26
|
+
});
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
/** Verify and decode a token */
|
|
30
|
+
export function verifyToken<T = any>(
|
|
31
|
+
token: string,
|
|
32
|
+
options?: { secret?: string }
|
|
33
|
+
): T {
|
|
34
|
+
return jwt.verify(token, options?.secret || ACCESS_SECRET) as T;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
/** Refresh: verify refresh token → return new access token */
|
|
38
|
+
export function refreshToken(
|
|
39
|
+
token: string,
|
|
40
|
+
options?: { accessSecret?: string; refreshSecret?: string }
|
|
41
|
+
): string {
|
|
42
|
+
const decoded = jwt.verify(
|
|
43
|
+
token,
|
|
44
|
+
options?.refreshSecret || REFRESH_SECRET
|
|
45
|
+
) as jwt.JwtPayload;
|
|
46
|
+
|
|
47
|
+
const { iat, exp, ...payload } = decoded;
|
|
48
|
+
return signToken(payload, { secret: options?.accessSecret });
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
/** Express middleware — verifies Bearer token, attaches decoded payload to `req.user` */
|
|
52
|
+
export function authMiddleware(options?: { secret?: string }) {
|
|
53
|
+
return (req: Request, res: Response, next: NextFunction) => {
|
|
54
|
+
const header = req.headers.authorization;
|
|
55
|
+
|
|
56
|
+
if (!header || !header.startsWith("Bearer ")) {
|
|
57
|
+
res.status(401).json({ error: "Missing or invalid Authorization header" });
|
|
58
|
+
return;
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
const token = header.split(" ")[1];
|
|
62
|
+
|
|
63
|
+
try {
|
|
64
|
+
const decoded = jwt.verify(token, options?.secret || ACCESS_SECRET);
|
|
65
|
+
(req as any).user = decoded;
|
|
66
|
+
next();
|
|
67
|
+
} catch {
|
|
68
|
+
res.status(401).json({ error: "Invalid or expired token" });
|
|
69
|
+
}
|
|
70
|
+
};
|
|
71
|
+
}
|
package/index.ts
CHANGED
|
@@ -1,12 +1,5 @@
|
|
|
1
|
-
/** Express app
|
|
2
|
-
export {
|
|
3
|
-
/** Express types — Request, Response, NextFunction */
|
|
4
|
-
export type { Request, Response, NextFunction } from "./app";
|
|
5
|
-
/** Express utilities — Router, json, urlencoded, expressStatic */
|
|
6
|
-
export { Router, json, urlencoded, expressStatic } from "./app";
|
|
7
|
-
|
|
8
|
-
/** Socket.IO server instance — use for `.on()` / `.emit()` */
|
|
9
|
-
export { io, socket } from "./socket";
|
|
1
|
+
/** Start Socket.IO on an Express app: `startSocket(app)` → returns { server, io, socket } */
|
|
2
|
+
export { startSocket, io, socket } from "./socket";
|
|
10
3
|
/** Socket type — for typing event handlers */
|
|
11
4
|
export type { Socket } from "./socket";
|
|
12
5
|
|
|
@@ -15,6 +8,17 @@ export { limiter } from "./rateLimiter";
|
|
|
15
8
|
/** Factory — create custom rate limiters: `rateLimit({ windowMs: 60000, max: 20 })` */
|
|
16
9
|
export { rateLimit } from "./rateLimiter";
|
|
17
10
|
|
|
18
|
-
/**
|
|
19
|
-
|
|
20
|
-
|
|
11
|
+
/** JWT middleware — verifies Bearer token, attaches decoded payload to `req.user` */
|
|
12
|
+
export { authMiddleware } from "./auth";
|
|
13
|
+
/** Sign an access token: `signToken({ userId: 1 })` */
|
|
14
|
+
export { signToken } from "./auth";
|
|
15
|
+
/** Sign a refresh token: `signRefreshToken({ userId: 1 })` */
|
|
16
|
+
export { signRefreshToken } from "./auth";
|
|
17
|
+
/** Verify and decode a token: `verifyToken<T>(token)` */
|
|
18
|
+
export { verifyToken } from "./auth";
|
|
19
|
+
/** Refresh: verify refresh token → return new access token */
|
|
20
|
+
export { refreshToken } from "./auth";
|
|
21
|
+
|
|
22
|
+
/** Validate data against Zod schema: `validate(schema, data)` → { success, data, errors } */
|
|
23
|
+
export { validate } from "./validate";
|
|
24
|
+
export type { ValidateResult } from "./validate";
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "abhijanb",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.1",
|
|
4
4
|
"module": "index.ts",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"exports": {
|
|
@@ -8,15 +8,18 @@
|
|
|
8
8
|
},
|
|
9
9
|
"types": "./index.ts",
|
|
10
10
|
"dependencies": {
|
|
11
|
-
"express": "^4.21.0",
|
|
12
11
|
"express-rate-limit": "^7.5.0",
|
|
13
|
-
"
|
|
12
|
+
"jsonwebtoken": "^9.0.0",
|
|
13
|
+
"socket.io": "^4.8.0",
|
|
14
|
+
"zod": "^3.22.0"
|
|
14
15
|
},
|
|
15
16
|
"devDependencies": {
|
|
16
17
|
"@types/bun": "latest",
|
|
17
|
-
"@types/express": "^5.0.0"
|
|
18
|
+
"@types/express": "^5.0.0",
|
|
19
|
+
"@types/jsonwebtoken": "^9.0.0"
|
|
18
20
|
},
|
|
19
21
|
"peerDependencies": {
|
|
22
|
+
"express": "^4.21.0",
|
|
20
23
|
"typescript": "^5"
|
|
21
24
|
}
|
|
22
25
|
}
|
package/socket.ts
CHANGED
|
@@ -1,10 +1,17 @@
|
|
|
1
|
+
import http from "http";
|
|
1
2
|
import { Server } from "socket.io";
|
|
2
|
-
import {
|
|
3
|
+
import type { Express } from "express";
|
|
3
4
|
|
|
4
|
-
|
|
5
|
-
|
|
5
|
+
let io: Server;
|
|
6
|
+
let socket: Server;
|
|
7
|
+
|
|
8
|
+
/** Start Socket.IO on an Express app: `startSocket(app)` → returns { server, io, socket } */
|
|
9
|
+
export function startSocket(app: Express) {
|
|
10
|
+
const server = http.createServer(app);
|
|
11
|
+
io = new Server(server);
|
|
12
|
+
socket = io;
|
|
13
|
+
return { server, io, socket };
|
|
14
|
+
}
|
|
6
15
|
|
|
7
|
-
/** Socket.IO server instance — use for `.on()` / `.emit()` */
|
|
8
16
|
export { io, socket };
|
|
9
|
-
/** Socket type — for typing event handlers */
|
|
10
17
|
export type { Socket } from "socket.io";
|
package/validate.ts
ADDED
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
import type { ZodSchema, ZodIssue } from "zod";
|
|
3
|
+
|
|
4
|
+
type ValidateResult<T> =
|
|
5
|
+
| { success: true; data: T; errors: null }
|
|
6
|
+
| { success: false; data: null; errors: ZodIssue[] };
|
|
7
|
+
|
|
8
|
+
/** Validate data against a Zod schema: `validate(schema, data)` → { success, data, errors } */
|
|
9
|
+
export function validate<T>(schema: ZodSchema<T>, data: unknown): ValidateResult<T> {
|
|
10
|
+
const result = schema.safeParse(data);
|
|
11
|
+
if (result.success) {
|
|
12
|
+
return { success: true, data: result.data, errors: null };
|
|
13
|
+
}
|
|
14
|
+
return { success: false, data: null, errors: result.error.issues };
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
export type { ValidateResult };
|
package/app.ts
DELETED
|
@@ -1,14 +0,0 @@
|
|
|
1
|
-
import express from "express";
|
|
2
|
-
import http from "http";
|
|
3
|
-
|
|
4
|
-
const app = express();
|
|
5
|
-
const server = http.createServer(app);
|
|
6
|
-
|
|
7
|
-
/** Express app instance — use for routing and middleware */
|
|
8
|
-
export { app };
|
|
9
|
-
/** HTTP server instance — used by Socket.IO */
|
|
10
|
-
export { server };
|
|
11
|
-
/** Express request type */
|
|
12
|
-
export type { Request, Response, NextFunction } from "express";
|
|
13
|
-
/** Router — create modular route handlers */
|
|
14
|
-
export { Router, json, urlencoded, static as expressStatic } from "express";
|