Skip to content

Commit

Permalink
Upgrade to Node 20 & add Docker support (#3)
Browse files Browse the repository at this point in the history
Deps updated,
Node updated,
Added Docker support,
Removed some no longer needed packages.
  • Loading branch information
Maczuga committed Sep 2, 2024
1 parent 2b6bf73 commit 7d6fea3
Show file tree
Hide file tree
Showing 28 changed files with 629 additions and 480 deletions.
17 changes: 17 additions & 0 deletions .dockerignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Obvious...
node_modules

# Already built files
dist

# Cache
.cache

# IDE
.vs
.idea
.editorconfig

# Environment
.env
.env.local
1 change: 1 addition & 0 deletions .env
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
# Copy this to .env.local and fill in the values
API_KEY=
SECRET_KEY=
STORMFORGE_API_KEY=
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/compilation.yml
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ jobs:
strategy:
matrix:
os: [ubuntu-latest, windows-latest]
node: [ '12', '14', '16' ]
node: ["20"]
runs-on: ${{ matrix.os }}

steps:
Expand Down
45 changes: 45 additions & 0 deletions .github/workflows/docker_build.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
name: Build and Publish Docker Images

on:
push:
branches:
- master
- main
- docker
paths-ignore:
- ".editorconfig"
- "tsm.service"
- "README.md"

jobs:
build-and-push:
runs-on: ubuntu-latest
strategy:
matrix:
include:
- dockerfile: Dockerfile
image: ghcr.io/tauri-wow-community-devs/tsm-app-data-generator:latest

steps:
- name: Checkout code
uses: actions/checkout@v2

- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1

- name: Log in to GitHub Container Registry
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}

- name: Build and push Docker image
uses: docker/build-push-action@v2
with:
context: .
file: ./${{ matrix.dockerfile }}
push: true
tags: ${{ matrix.image }}
cache-from: type=gha, key=docker-${{ matrix.dockerfile }}-${{ matrix.image }}
cache-to: type=gha, key=docker-${{ matrix.dockerfile }}-${{ matrix.image }}, mode=max
1 change: 1 addition & 0 deletions .npmrc
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
engine-strict=true
1 change: 1 addition & 0 deletions .nvmrc
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
20
22 changes: 22 additions & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
FROM node:20-alpine AS builder

WORKDIR /app

# Copy package.json and yarn.lock
COPY package.json yarn.lock ./

# Install dependencies
RUN yarn install --frozen-lockfile

# Copy source files and tsconfig
COPY src ./src
COPY tsconfig.json ./

# Build the project
RUN yarn build

# Remove dev dependencies
RUN yarn install --production --ignore-scripts --prefer-offline

# Start the application
CMD ["node", "dist/index.js"]
10 changes: 10 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,3 +11,13 @@ This tool allows you to generate `AppData.lua` file for MoP TradeSkillMaster_Auc
## Run & debug
Fill all required .env variables and run `yarn run start` to launch the script.
If you prefer the JS version - run `yarn run build` instead of the start command and use files in `dist` folder.

## Docker & You
You can now use Docker to run this script.

Recommended way using docker-compose:

1. Copy `.env` file as `.env.local` and fill all required variables.
2. Run `docker-compose up -d` to start the container.

You can also use `docker run` command to run the container manually.
9 changes: 9 additions & 0 deletions docker-compose.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
services:
app:
image: ghcr.io/tauri-wow-community-devs/tsm-app-data-generator:latest
pull_policy: always
restart: always
ports:
- "${SERVER_PORT:-9876}:${SERVER_PORT:-9876}"
env_file:
- .env.local
28 changes: 14 additions & 14 deletions package.json
Original file line number Diff line number Diff line change
@@ -1,11 +1,14 @@
{
"name": "tauri-api",
"version": "1.1.0",
"version": "1.2.0",
"main": "src/index.ts",
"license": "MIT",
"scripts": {
"build": "ttsc -P ./tsconfig.json",
"start": "ts-node -r tsconfig-paths/register ./src/index.ts"
"build": "tsc -P ./tsconfig.json",
"start": "ts-node ./src/index.ts"
},
"engines": {
"node": ">=20.0.0"
},
"eslintConfig": {
"extends": [
Expand All @@ -14,20 +17,17 @@
},
"devDependencies": {
"@topsoft4u/eslint-config": "1.0.30",
"@types/express": "4.17.13",
"@types/node": "17.0.9",
"@types/node-cron": "3.0.1",
"@zerollup/ts-transform-paths": "1.7.18",
"axios": "0.24.0",
"@types/express": "4.17.21",
"@types/node": "^20.0.0",
"@types/node-cron": "3.0.11",
"eslint": "8.7.0",
"ts-node": "10.4.0",
"tsconfig-paths": "3.12.0",
"ttypescript": "1.5.13",
"typescript": "4.4.4"
"typescript": "5.5.4"
},
"dependencies": {
"dotenv": "14.2.0",
"express": "4.17.2",
"node-cron": "3.0.0"
"axios": "1.7.7",
"dotenv": "16.4.5",
"express": "4.19.2",
"node-cron": "3.0.3"
}
}
20 changes: 11 additions & 9 deletions src/index.ts
Original file line number Diff line number Diff line change
@@ -1,21 +1,25 @@
import cron from "node-cron";
import {Realm} from "src/constants/realms";
import {cacheAuctionData} from "src/services/cacheAuctionData";
import {log} from "src/utils";
import {Realm} from "./constants/realms";
import {initDotEnv} from "./lib/env";
import {initServer} from "./lib/server";
import {cacheAuctionData} from "./services/cacheAuctionData";
import {log} from "./utils";

initDotEnv();
initServer();

const realms = [Realm.TAURI, Realm.EVERMOON, Realm.MISTBLADE, Realm.MISTBLADE_S2];
const realms = [
Realm.TAURI,
Realm.EVERMOON,
Realm.MISTBLADE,
Realm.MISTBLADE_S2,
];

let fetchAHInProgress = false;

// Every minute
cron.schedule("* * * * *", async () => {
if (fetchAHInProgress)
return;
if (fetchAHInProgress) return;

try {
fetchAHInProgress = true;
Expand All @@ -24,9 +28,7 @@ cron.schedule("* * * * *", async () => {
await cacheAuctionData(realm);
log(`${realm.toString()} - end`);
}
}
finally {
} finally {
fetchAHInProgress = false;
}
});

2 changes: 1 addition & 1 deletion src/lib/api.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import axios, {AxiosRequestConfig} from "axios";
import {Realm,RealmXSource,ApiSourceInfo} from "src/constants/realms";
import {ApiSourceInfo, Realm, RealmXSource} from "../constants/realms";

export const apiCall = async <T>(url: string, realm: Realm, params?: { [key: string]: any }) => {
try {
Expand Down
2 changes: 1 addition & 1 deletion src/lib/cache.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import fs from "fs";
import path from "path";
import {log} from "src/utils";
import {log} from "../utils";

const wasInit = false;

Expand Down
19 changes: 11 additions & 8 deletions src/lib/env.ts
Original file line number Diff line number Diff line change
@@ -1,24 +1,27 @@
import {config} from "dotenv";
import fs from "fs";
import path from "path";
import {config} from "dotenv";

export const initDotEnv = () => {
let envFile = "";
try {
envFile = ".env.local";
if (!fs.existsSync(path.resolve(envFile)))
envFile = ".env";
if (!fs.existsSync(path.resolve(envFile))) envFile = ".env";
} catch (err) {
envFile = ".env";
}

config({
path: envFile
path: envFile,
});

const envVariables = ["API_KEY", "SECRET_KEY"];
envVariables.forEach(env => {
if (!process.env[env])
throw new Error(`Missing .env variable: ${env}`);
const envVariables = [
"API_KEY",
"SECRET_KEY",
"STORMFORGE_API_KEY",
"STORMFORGE_SECRET_KEY",
];
envVariables.forEach((env) => {
if (!process.env[env]) throw new Error(`Missing .env variable: ${env}`);
});
};
2 changes: 1 addition & 1 deletion src/lib/server.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ export const initServer = () => {
app.set("etag", false);
app.use(
express.static("public", {
maxAge: 300
maxAge: 300,
})
);
app.use(express.json());
Expand Down
7 changes: 4 additions & 3 deletions src/lib/tsm/index.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
export * from "src/lib/tsm/tsm";
export * from "src/lib/tsm/math";
export * from "src/lib/tsm/types";
export * from "./math";
export * from "./tsm";
export * from "./types";

6 changes: 3 additions & 3 deletions src/lib/tsm/tsm.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import {AuctionItem} from "src/methods/auctions/auctions-data";
import {TSMItemObject} from "src/lib/tsm/types";
import {calculateMarketValue} from "src/lib/tsm/math";
import {AuctionItem} from "../../methods/auctions/auctions-data";
import {calculateMarketValue} from "./math";
import type {TSMItemObject} from "./types";

export const parseAHInfo = (items: AuctionItem[]): TSMItemObject => {
items = items.filter(item => item.buyout > 0);
Expand Down
2 changes: 1 addition & 1 deletion src/lib/tsm/types.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import {Realm} from "src/constants/realms";
import {Realm} from "../../constants/realms";

export type TSMRealmInfo = {
alliance: TSMItemObject;
Expand Down
4 changes: 2 additions & 2 deletions src/methods/auctions/auctions-data.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import {apiCall} from "src/lib/api";
import {Realm} from "src/constants/realms";
import {Realm} from "../../constants/realms";
import {apiCall} from "../../lib/api";

export const fetchAuctionsData = (realm: Realm = Realm.TAURI) => apiCall<AuctionsDataResult>("auctions-data", realm);

Expand Down
4 changes: 2 additions & 2 deletions src/methods/auctions/auctions-info.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import {apiCall} from "src/lib/api";
import {Realm} from "src/constants/realms";
import {Realm} from "../../constants/realms";
import {apiCall} from "../../lib/api";

export const fetchAuctionsInfo = (realm: Realm = Realm.TAURI) => apiCall<AuctionsInfoResult>("auctions-info", realm);

Expand Down
4 changes: 2 additions & 2 deletions src/methods/auctions/auctions-item-prices.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import {apiCall} from "src/lib/api";
import {Realm} from "src/constants/realms";
import {Realm} from "../../constants/realms";
import {apiCall} from "../../lib/api";
import {AuctionsDataResult} from "./auctions-data";

export const fetchAuctionsItemPrices = (item: number, realm: Realm = Realm.TAURI) => apiCall<AuctionsDataResult>("auctions-item-prices", realm, {item});
4 changes: 2 additions & 2 deletions src/routes/checkPrices.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import {NextFunction, Request, Response} from "express";
import {Realm} from "src/constants/realms";
import {fetchAuctionsItemPrices} from "../methods/auctions/auctions-item-prices";
import {Realm} from "../constants/realms";
import {AuctionItem} from "../methods/auctions/auctions-data";
import {fetchAuctionsItemPrices} from "../methods/auctions/auctions-item-prices";

type Faction = "ALLIANCE" | "HORDE" | "BOTH";
type Body = {
Expand Down
4 changes: 2 additions & 2 deletions src/routes/getTSMAppData.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import {NextFunction, Request, Response} from "express";
import {getQueryRealms} from "src/utils";
import {generateTSMAppData} from "src/services/generateTSMAppData";
import {generateTSMAppData} from "../services/generateTSMAppData";
import {getQueryRealms} from "../utils";

export const getTSMAppData = async (req: Request, res: Response, next: NextFunction) => {
const realms = getQueryRealms(req);
Expand Down
12 changes: 6 additions & 6 deletions src/services/cacheAuctionData.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import {Realm} from "src/constants/realms";
import {AuctionsInfoResult, fetchAuctionsInfo} from "src/methods/auctions/auctions-info";
import {cache} from "src/lib/cache";
import {log} from "src/utils";
import {fetchAuctionsData} from "src/methods/auctions/auctions-data";
import {parseAHInfo, TSMItemObject, TSMRealmInfo} from "src/lib/tsm";
import {log} from "console";
import {Realm} from "../constants/realms";
import {cache} from "../lib/cache";
import {TSMItemObject, TSMRealmInfo, parseAHInfo} from "../lib/tsm";
import {fetchAuctionsData} from "../methods/auctions/auctions-data";
import {AuctionsInfoResult, fetchAuctionsInfo} from "../methods/auctions/auctions-info";

export const cacheAuctionData = async (realm: Realm): Promise<TSMRealmInfo | undefined> => {
if (realm === Realm.TAURI || realm === Realm.EVERMOON) {
Expand Down
8 changes: 4 additions & 4 deletions src/services/generateTSMAppData.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import {getCachedData} from "src/services/cacheAuctionData";
import {Realm} from "src/constants/realms";
import {TSMFileData} from "src/lib/tsm";
import {log} from "src/utils";
import {log} from "console";
import {Realm} from "../constants/realms";
import type {TSMFileData} from "../lib/tsm";
import {getCachedData} from "./cacheAuctionData";

export const generateTSMAppData = async (realms: Realm[]) => {
const fileData: TSMFileData = {};
Expand Down
2 changes: 1 addition & 1 deletion src/utils.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import {Request} from "express";
import {Realm} from "src/constants/realms";
import {Realm} from "./constants/realms";

type Query = {
realms: {
Expand Down
11 changes: 0 additions & 11 deletions tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,17 +3,6 @@
"compilerOptions": {
"allowJs": false,
"allowSyntheticDefaultImports": true,
"baseUrl": ".",
"paths": {
"@/src/*": [
"src/*"
]
},
"plugins": [
{
"transform": "@zerollup/ts-transform-paths",
}
],
"declaration": true,
"esModuleInterop": true,
"forceConsistentCasingInFileNames": true,
Expand Down
Loading

0 comments on commit 7d6fea3

Please sign in to comment.