Compare commits

...

2 commits

Author SHA1 Message Date
powermaker450 91480fea64 Return 404 on review ID that returns no review 2024-09-13 12:12:07 -04:00
powermaker450 14e9549599 Move all routes behind /api 2024-09-13 12:06:20 -04:00
4 changed files with 64 additions and 19 deletions

View file

@ -2,6 +2,7 @@ import { PostListener, MessagesResponder } from "./routes";
import express from "express"; import express from "express";
import dotenv from "dotenv"; import dotenv from "dotenv";
import { Logger } from "./utils"; import { Logger } from "./utils";
import ApiRoute from "./utils/ApiRoute";
dotenv.config(); dotenv.config();
const app = express(); const app = express();
@ -11,8 +12,10 @@ const post = new PostListener(app);
const query = new MessagesResponder(app); const query = new MessagesResponder(app);
const port = +process.env.PORT || 8080; const port = +process.env.PORT || 8080;
ApiRoute.start(app);
post.start(); post.start();
query.start(); query.start();
logger.log("Loading complete.");
app.listen(port, () => { app.listen(port, () => {
logger.log(`Server started on ${Logger.emp(`http://localhost:${port}`)}`); logger.log(`Server started on ${Logger.emp(`http://localhost:${port}`)}`);

View file

@ -1,17 +1,16 @@
import { userReviewSchema, typeJson } from "../types"; import { userReviewSchema, typeJson } from "../types";
import { Logger, Responder, data } from "../utils"; import { Logger, Responder, data } from "../utils";
import { Express, Request, Response } from "express"; import { Express, Request, Response } from "express";
import ApiRoute from "../utils/ApiRoute";
export class PostListener { export class PostListener extends ApiRoute {
private server: Express;
private readonly logger = new Logger("Post Listener");
constructor(server: Express) { constructor(server: Express) {
this.server = server; // Route always trails a slash, the final result is is "/api/post". See src/utils/ApiRoute.ts
super(server, "/post");
} }
public async start(): Promise<void> { public async start(): Promise<void> {
this.server.post("/post", (req: Request, res: Response) => { this.server.post(this.routeName, (req: Request, res: Response) => {
req.on("data", async (chunk) => { req.on("data", async (chunk) => {
const sender = `${Logger.bold(Logger.emp("Client:"))} ${Logger.emp(req.headers["user-agent"])}`; const sender = `${Logger.bold(Logger.emp("Client:"))} ${Logger.emp(req.headers["user-agent"])}`;
@ -65,6 +64,6 @@ export class PostListener {
}); });
}); });
this.logger.log("Loading complete."); this.complete();
} }
} }

View file

@ -1,17 +1,16 @@
import { Express, Request, Response } from "express"; import { Express, Request, Response } from "express";
import { Logger, data } from "../utils"; import { Logger, Responder, data } from "../utils";
import { IdRequest, typeJson } from "../types"; import { IdRequest, typeJson } from "../types";
import ApiRoute from "../utils/ApiRoute";
export class MessagesResponder { export class MessagesResponder extends ApiRoute {
private server: Express;
private readonly logger = new Logger("Query");
constructor(server: Express) { constructor(server: Express) {
this.server = server; // Route always trails a slash, the final result is "/api/reviews". See src/utils/ApiRoute.ts
super(server, "/reviews");
} }
public async start(): Promise<void> { public async start(): Promise<void> {
this.server.get("/reviews", (req: Request, res: Response) => { this.server.get(this.routeName, (req: Request, res: Response) => {
const receiver = req.headers["user-agent"]; const receiver = req.headers["user-agent"];
const result = data.getReviews(); const result = data.getReviews();
@ -22,17 +21,23 @@ export class MessagesResponder {
this.logger.log(`${Logger.emp(receiver)} <~ "${req.path}"`); this.logger.log(`${Logger.emp(receiver)} <~ "${req.path}"`);
}); });
this.server.get("/reviews/:id", (req: IdRequest, res: Response) => { this.server.get(`${this.routeName}/:id`, (req: IdRequest, res: Response) => {
const receiver = req.headers["user-agent"]; const receiver = req.headers["user-agent"];
const result = data.getReviewById(req.params.id); const result = data.getReviewById(req.params.id);
res.writeHead(200, typeJson); if (Object.keys(result).length) {
res.write(JSON.stringify(result)); res.writeHead(200, typeJson);
res.end(); res.write(JSON.stringify(result));
res.end();
} else {
res.writeHead(404, typeJson);
res.write(Responder.requestError("review not found"));
res.end();
}
this.logger.log(`${Logger.emp(receiver)} <~ "${req.path}"`); this.logger.log(`${Logger.emp(receiver)} <~ "${req.path}"`);
}); });
this.logger.log("Loading complete."); this.complete();
} }
} }

38
src/utils/ApiRoute.ts Normal file
View file

@ -0,0 +1,38 @@
import { Express, Request, Response } from "express";
import { Logger } from "./logger";
import { typeJson } from "../types";
import { Responder } from "./responder";
export default class ApiRoute {
public readonly server: Express;
public readonly routeName: string;
public readonly logger = new Logger("API");
constructor(server: Express, route: string) {
// API Routes are a list of routes, the beginning route should be first
const mainRoute = `/api${route}`;
this.server = server;
this.routeName = mainRoute;
}
// this.complete() should be called when the route is finished initalizing.
// This makes it easy to see what routes
public complete(): void {
this.logger.log("Loaded", Logger.emp(this.routeName));
}
public static async start(server: Express): Promise<void> {
server.post("/api", (req: Request, res: Response) => {
res.writeHead(400, typeJson);
res.write(Responder.success("ok"));
res.end();
});
server.get("/api", (req: Request, res: Response) => {
res.writeHead(400, typeJson);
res.write(Responder.success("ok"));
res.end();
})
}
}