Skip to content

Commit

Permalink
Clean up
Browse files Browse the repository at this point in the history
  • Loading branch information
ruchernchong committed Nov 16, 2023
1 parent 2d51fdd commit 21391d8
Show file tree
Hide file tree
Showing 7 changed files with 38 additions and 71 deletions.
49 changes: 14 additions & 35 deletions packages/core/src/car.ts
Original file line number Diff line number Diff line change
@@ -1,40 +1,20 @@
export * as Car from "./car";
import fetch from "node-fetch";
import fs from "fs";
import AdmZip from "adm-zip";
import * as d3 from "d3";
import { Car } from "./types";
import db from "../../config/db";
import { FUEL_TYPE } from "./config";
import { filterDataLast12Months } from "./lib/filterDataLast12Months";
import { sortByMake } from "./lib/sortByMake";

export const list = async () => {
const tempDir: string = "/tmp";
const zipFileName: string = `Monthly New Registration of Cars by Make.zip`;
const zipFilePath: string = `${tempDir}/${zipFileName}`;
const csvFileName: string = `M03-Car_Regn_by_make.csv`;
const csvFilePath: string = `${tempDir}/${csvFileName}`;
const zipUrl: string = `https://datamall.lta.gov.sg/content/dam/datamall/datasets/Facts_Figures/Vehicle Registration/${zipFileName}`;

const response = await fetch(zipUrl);
if (!response.ok) {
throw new Error(`Failed to download the ZIP file: ${response.statusText}`);
}
const data = await response.buffer();
fs.writeFileSync(zipFilePath, data);

const zip = new AdmZip(zipFilePath);
zip.extractAllTo(`${tempDir}`, true);

const csvData = fs.readFileSync(csvFilePath, "utf-8");
const parsedData = d3.csvParse(csvData);

const electricCars: Car[] = parsedData
.filter(
({ fuel_type, number }) =>
fuel_type === FUEL_TYPE.ELECTRIC && +number !== 0,
)
.reduce((result: Car[], { month, make, fuel_type, number }) => {
import type { CarType } from "./types";

export const electric = async (): Promise<CarType[]> => {
let electricCars = await db
.collection("cars")
.find({
fuel_type: FUEL_TYPE.ELECTRIC,
})
.toArray();

return electricCars
.reduce((result: any[], { _id, month, make, fuel_type, number }) => {
const existingCar = result.find(
(car) => car.month === month && car.make === make,
);
Expand All @@ -43,6 +23,7 @@ export const list = async () => {
existingCar.number += Number(number);
} else {
result.push({
_id,
month,
make,
fuel_type,
Expand All @@ -55,6 +36,4 @@ export const list = async () => {
.map((car) => ({ ...car, number: +car.number }))
.filter(filterDataLast12Months)
.sort(sortByMake);

return electricCars;
};
4 changes: 2 additions & 2 deletions packages/core/src/lib/filterDataLast12Months.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { isWithinInterval, parseISO, subMonths } from "date-fns";
import type { Car } from "../types";
import type { CarType } from "../types";

export const filterDataLast12Months = (data: Car) => {
export const filterDataLast12Months = (data: CarType) => {
const currentDate = new Date();

const startDate = subMonths(currentDate, 12);
Expand Down
8 changes: 5 additions & 3 deletions packages/core/src/lib/sortByMake.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
import type { Car } from "../types";
import type { CarType } from "../types";

export const sortByMake = (a: Pick<Car, "make">, b: Pick<Car, "make">) =>
a.make.localeCompare(b.make);
export const sortByMake = (
a: Pick<CarType, "make">,
b: Pick<CarType, "make">,
) => a.make.localeCompare(b.make);
2 changes: 1 addition & 1 deletion packages/core/src/types/index.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { FUEL_TYPE } from "../config";

export interface Car {
export interface CarType {
month: string;
make: string;
fuel_type: FUEL_TYPE | string;
Expand Down
28 changes: 9 additions & 19 deletions packages/functions/src/car.ts
Original file line number Diff line number Diff line change
@@ -1,35 +1,25 @@
import { ApiHandler, useQueryParams } from "sst/node/api";
import { ApiHandler } from "sst/node/api";
import { Car } from "@lta-datasets-updater/core/car";
import db from "../../config/db";
import { FUEL_TYPE } from "@lta-datasets-updater/core/config";
import db from "../../config/db";

export const list = ApiHandler(async (_evt) => {
const params = useQueryParams();
const cars = await Car.list();

const filteredCars =
Object.keys(params).length > 0
? cars.filter(({ month }) => {
const [year] = month.split("-");

return year === params.year;
})
: cars;
export const electric = ApiHandler(async (_evt) => {
const electricCars = await Car.electric();

return {
statusCode: 200,
body: JSON.stringify(filteredCars),
body: JSON.stringify(electricCars),
};
});

export const electric = ApiHandler(async (_evt) => {
const electricCars = await db
export const petrol = ApiHandler(async (_evt) => {
const petrolCars = await db
.collection("cars")
.find({ fuel_type: FUEL_TYPE.ELECTRIC })
.find({ fuel_type: { $ne: FUEL_TYPE.PETROL } })
.toArray();

return {
statusCode: 200,
body: JSON.stringify(electricCars),
body: JSON.stringify(petrolCars),
};
});
14 changes: 4 additions & 10 deletions packages/functions/src/datasets.ts
Original file line number Diff line number Diff line change
@@ -1,17 +1,11 @@
import { ApiHandler } from "sst/node/api";
import { FUEL_TYPE } from "@lta-datasets-updater/core/config";
import db from "../../config/db";
import { Datasets } from "@lta-datasets-updater/core/datasets";

export const handler = ApiHandler(async (event, context) => {
context.callbackWaitsForEmptyEventLoop = false;

const cars = await db
.collection("cars")
.find({ fuel_type: FUEL_TYPE.ELECTRIC })
.toArray();
export const updater = ApiHandler(async (event, context) => {
await Datasets.updater();

return {
statusCode: 200,
body: JSON.stringify(cars),
body: JSON.stringify("Data has been successfully updated"),
};
});
4 changes: 3 additions & 1 deletion stacks/MyStack.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,10 +32,12 @@ export const api = ({ stack }: StackContext) => {
allowOrigins: ["https://singapore-ev-trends.ruchern.xyz"],
},
routes: {
"GET /": "packages/functions/src/car.list",
"GET /": "packages/functions/src/car.electric",
"GET /car/electric": "packages/functions/src/car.electric",
"GET /car/petrol": "packages/functions/src/car.petrol",
"GET /todo": "packages/functions/src/todo.list",
"POST /todo": "packages/functions/src/todo.create",
"GET /updater": "packages/functions/src/datasets.updater",
},
});

Expand Down

0 comments on commit 21391d8

Please sign in to comment.