Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
38 changes: 15 additions & 23 deletions .github/workflows/main.yml
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,7 @@ jobs:

- name: Read Node version from mise.toml
id: node
run:
echo "version=$(grep -E '^node\s*=' mise.toml | sed -E 's/.*"([^"]+)".*/\1/')" >>
run: echo "version=$(grep -E '^node\s*=' mise.toml | sed -E 's/.*"([^"]+)".*/\1/')" >>
"$GITHUB_OUTPUT"
Comment on lines +17 to 18

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Node-version extraction relies on double-quoted value format in mise.toml.

The sed pattern s/.*"([^"]+)".*/\1/ requires the value to be double-quoted (e.g. node = "20.x"). If mise.toml is ever updated to use single quotes or bare integers, sed returns an empty string and actions/setup-node fails silently with a confusing error. The same pattern is repeated in the build, testDeploy, and deploy jobs (Lines 83-84, 133-134, 196-197).

🛡️ More robust extraction
-        run: echo "version=$(grep -E '^node\s*=' mise.toml | sed -E 's/.*"([^"]+)".*/\1/')" >>
-          "$GITHUB_OUTPUT"
+        run: |
+          version=$(grep -E '^node\s*=' mise.toml | sed -E 's/.*["'"'"']([^"'"'"']+)["'"'"'].*/\1/')
+          echo "version=$version" >> "$GITHUB_OUTPUT"
+          if [ -z "$version" ]; then echo "::error::Could not parse node version from mise.toml"; exit 1; fi

Apply the same fix to the identical steps in build (Line 83), testDeploy (Line 133), and deploy (Line 196).

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
run: echo "version=$(grep -E '^node\s*=' mise.toml | sed -E 's/.*"([^"]+)".*/\1/')" >>
"$GITHUB_OUTPUT"
run: |
version=$(grep -E '^node\s*=' mise.toml | sed -E 's/.*["'"'"']([^"'"'"']+)["'"'"'].*/\1/')
echo "version=$version" >> "$GITHUB_OUTPUT"
if [ -z "$version" ]; then echo "::error::Could not parse node version from mise.toml"; exit 1; fi
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/main.yml around lines 17 - 18, The step that extracts node
version using the run command (the `run: echo "version=$(grep -E '^node\s*='
mise.toml | sed -E 's/.*"([^"]+)".*/\1/')" >> "$GITHUB_OUTPUT"` line) only
matches double-quoted values; change the sed/regex to accept optional
surrounding quotes (double or single) or bare values so it reliably captures
node = "20.x", node = '20.x', or node = 20, and replace the existing pattern in
that run step; then apply the identical fix to the repeated extraction steps in
the build, testDeploy, and deploy jobs so all actions/setup-node invocations
receive a robust version value.


- name: Install package manager (from package.json)
Expand All @@ -40,8 +39,7 @@ jobs:
node_modules
${{ steps.yarn-config.outputs.cacheFolder }}
.yarn/install-state.gz
key:
yarn-${{ runner.os }}-node${{ steps.node.outputs.version }}-${{
key: yarn-${{ runner.os }}-node${{ steps.node.outputs.version }}-${{
hashFiles('yarn.lock') }}
restore-keys: |
yarn-${{ runner.os }}-node${{ steps.node.outputs.version }}-
Expand All @@ -53,20 +51,20 @@ jobs:
case "$(yarn --version)" in 1.*) echo 'expected up-to-date yarn version'; exit 1 ;; esac
yarn install --immutable

- name: run linter
run: yarn lint
- name: Format
run: yarn format:check

- name: run format
run: yarn format
- name: Lint
run: yarn lint

- name: run typecheck
- name: Typecheck
run: yarn typecheck

- name: run tests
- name: Test
run: yarn coverage

- name: Upload coverage reports to Codecov
uses: codecov/codecov-action@v4.0.1
uses: codecov/codecov-action@v5
with:
token: ${{ secrets.CODECOV_TOKEN }}
slug: game-ci/versioning-backend
Expand All @@ -82,8 +80,7 @@ jobs:

- name: Read Node version from mise.toml
id: node
run:
echo "version=$(grep -E '^node\s*=' mise.toml | sed -E 's/.*"([^"]+)".*/\1/')" >>
run: echo "version=$(grep -E '^node\s*=' mise.toml | sed -E 's/.*"([^"]+)".*/\1/')" >>
"$GITHUB_OUTPUT"

- name: Install package manager (from package.json)
Expand All @@ -108,8 +105,7 @@ jobs:
node_modules
${{ steps.yarn-config.outputs.cacheFolder }}
.yarn/install-state.gz
key:
yarn-${{ runner.os }}-node${{ steps.node.outputs.version }}-${{
key: yarn-${{ runner.os }}-node${{ steps.node.outputs.version }}-${{
hashFiles('yarn.lock') }}
restore-keys: |
yarn-${{ runner.os }}-node${{ steps.node.outputs.version }}-
Expand All @@ -134,8 +130,7 @@ jobs:

- name: Read Node version from mise.toml
id: node
run:
echo "version=$(grep -E '^node\s*=' mise.toml | sed -E 's/.*"([^"]+)".*/\1/')" >>
run: echo "version=$(grep -E '^node\s*=' mise.toml | sed -E 's/.*"([^"]+)".*/\1/')" >>
"$GITHUB_OUTPUT"

- name: Install package manager (from package.json)
Expand All @@ -160,8 +155,7 @@ jobs:
node_modules
${{ steps.yarn-config.outputs.cacheFolder }}
.yarn/install-state.gz
key:
yarn-${{ runner.os }}-node${{ steps.node.outputs.version }}-${{
key: yarn-${{ runner.os }}-node${{ steps.node.outputs.version }}-${{
hashFiles('yarn.lock') }}
restore-keys: |
yarn-${{ runner.os }}-node${{ steps.node.outputs.version }}-
Expand Down Expand Up @@ -199,8 +193,7 @@ jobs:

- name: Read Node version from mise.toml
id: node
run:
echo "version=$(grep -E '^node\s*=' mise.toml | sed -E 's/.*"([^"]+)".*/\1/')" >>
run: echo "version=$(grep -E '^node\s*=' mise.toml | sed -E 's/.*"([^"]+)".*/\1/')" >>
"$GITHUB_OUTPUT"

- name: Install package manager (from package.json)
Expand All @@ -225,8 +218,7 @@ jobs:
node_modules
${{ steps.yarn-config.outputs.cacheFolder }}
.yarn/install-state.gz
key:
yarn-${{ runner.os }}-node${{ steps.node.outputs.version }}-${{
key: yarn-${{ runner.os }}-node${{ steps.node.outputs.version }}-${{
hashFiles('yarn.lock') }}
restore-keys: |
yarn-${{ runner.os }}-node${{ steps.node.outputs.version }}-
Expand Down
13 changes: 6 additions & 7 deletions .husky/pre-commit
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
#!/bin/sh
. "$(dirname -- "$0")/_/husky.sh"

# Fix from https://github.com/typicode/husky/issues/968#issuecomment-1176848345
if [ -t 2 ] ; then exec >/dev/tty 2>&1 ; fi

# Check changes that are staged for commit
#!/usr/bin/env sh
yarn lint-staged
yarn typecheck

if command -v gitleaks >/dev/null 2>&1; then
gitleaks protect --staged --no-banner --redact
fi
16 changes: 16 additions & 0 deletions .oxfmtrc.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
{
"semi": true,
"singleQuote": true,
"trailingComma": "all",
"printWidth": 100,
"proseWrap": "preserve",
"sortPackageJson": false,
"ignorePatterns": [
"**/node_modules/**",
"**/lib/**",
"**/dist/**",
"**/coverage/**",
"**/.yarn/**",
"**/.firebase/**"
]
}
42 changes: 40 additions & 2 deletions .oxlintrc.json
Original file line number Diff line number Diff line change
@@ -1,5 +1,43 @@
{
"$schema": "./node_modules/oxlint/configuration_schema.json",
"plugins": ["typescript", "vitest", "unicorn", "oxc"],
"categories": {
"correctness": "error",
"suspicious": "error",
"perf": "error"
},
"rules": {
"no-unsafe-declaration-merging": "off"
}
"vitest/require-mock-type-parameters": "off",
"vitest/valid-title": "off",
"typescript/no-explicit-any": "warn",
"typescript/ban-ts-comment": "off",
"typescript/no-namespace": "off",
"typescript/no-unsafe-declaration-merging": "off",
"typescript/no-extraneous-class": "off",
"no-bitwise": "off",
"no-await-in-loop": "off"
},
"overrides": [
{
"files": ["**/*.test.ts", "**/*.spec.ts", "**/test/**/*.ts"],
"rules": {
"typescript/no-explicit-any": "off",
"no-unused-vars": "off"
}
}
],
"env": {
"browser": false,
"node": true,
"es2024": true,
"vitest/globals": true
},
"ignorePatterns": [
"**/node_modules/**",
"**/lib/**",
"**/dist/**",
"**/coverage/**",
"**/.yarn/**",
"**/.firebase/**"
]
}
4 changes: 0 additions & 4 deletions .prettierignore

This file was deleted.

6 changes: 0 additions & 6 deletions .prettierrc.json

This file was deleted.

3 changes: 1 addition & 2 deletions .yarnrc.yml
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
nodeLinker: node-modules


# Solo project; PRs are exclusively from the maintainer. Re-enable when
# accepting third-party PRs that auto-trigger CI without manual review.
enableHardenedMode: false

npmRegistryServer: "https://registry.npmjs.org/"
npmRegistryServer: 'https://registry.npmjs.org/'
1 change: 0 additions & 1 deletion DEVELOPMENT.md
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,6 @@ This will compile the TypeScript code into JavaScript in the `lib` directory, wh
To use Firebase Admin SDK locally:

1. Download a service account key from your Firebase project settings:

- Go to [Firebase Console](https://console.firebase.google.com/)
- Select your project
- Go to Project Settings > Service accounts
Expand Down
4 changes: 2 additions & 2 deletions firebase.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,8 @@
"functions": {
"runtime": "nodejs22",
"predeploy": [
"yarn workspace functions lint",
"yarn workspace functions test run",
"yarn lint",
"yarn workspace functions run test:run",
"yarn workspace functions build"
]
},
Expand Down
11 changes: 3 additions & 8 deletions functions/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@
"name": "functions",
"scripts": {
"dev": "yarn watch",
"lint": "eslint \"src/**/*\"",
"build": "run -T tsc",
"watch": "run -T tsc --watch",
"serve": "yarn build && firebase emulators:start --only functions",
Expand All @@ -11,7 +10,8 @@
"deploy": "firebase deploy --only functions",
"logs": "firebase functions:log",
"test": "run -T vitest",
"typecheck": "run -T tsc --noEmit",
"typecheck": "run -T tsgo --noEmit",
"typecheck:tsc": "run -T tsc --noEmit",
"coverage": "run -T vitest run --coverage",
"test:run": "run -T vitest run",
"test:ui": "run -T vitest --ui"
Expand All @@ -38,12 +38,7 @@
"@types/node-fetch": "^2.6.11",
"@types/semver": "^7.5.8",
"@types/ws": "^8.5.13",
"@typescript-eslint/eslint-plugin": "^7.12.0",
"@typescript-eslint/parser": "^7.12.0",
"eslint": "^8.57.0",
"eslint-plugin-import": "^2.29.1",
"firebase-functions-test": "^3.3.0",
"jest": "^29.7.0"
"firebase-functions-test": "^3.3.0"
},
"private": true,
"packageManager": "yarn@4.14.1"
Expand Down
5 changes: 3 additions & 2 deletions functions/src/config/credential.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,9 @@ import { credential } from 'firebase-admin';

export const getCredential = (): credential.Credential => {
try {
const serviceAccount = require(process.env.GOOGLE_APPLICATION_CREDENTIALS ??
'../../service-account.json');
const serviceAccount = require(
process.env.GOOGLE_APPLICATION_CREDENTIALS ?? '../../service-account.json',
);
return credential.cert(serviceAccount);
} catch {
return credential.applicationDefault();
Expand Down
3 changes: 3 additions & 0 deletions mise.toml
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
[tools]
node = "24.12.0"
yarn = "4.14.1"
actionlint = "latest"
shellcheck = "latest"
gitleaks = "latest"
38 changes: 20 additions & 18 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,26 +7,26 @@
"functions"
],
"scripts": {
"dev": "husky install && turbo dev",
"lint": "oxlint --deny-warnings . && yarn workspace functions lint",
"format": "prettier --write .",
"typecheck": "yarn workspace functions typecheck",
"test": "vitest",
"coverage": "vitest run --coverage",
"dev": "node scripts/ensure-husky.mjs && yarn workspace functions dev",
"test": "node scripts/ensure-husky.mjs && vitest run",
"test:watch": "vitest",
"test:ui": "vitest --ui",
"test:run": "vitest run",
"prepare": "husky install || true"
"coverage": "vitest run --coverage",
"lint": "yarn oxlint --report-unused-disable-directives",
"format": "oxfmt --write",
"format:check": "oxfmt --check",
"typecheck": "yarn workspace functions typecheck",
"setup:hooks": "node scripts/ensure-husky.mjs",
"prepare": "husky"
},
"lint-staged": {
"*.@(sh|bash|zsh|fish)": [
"shellcheck",
"git update-index --chmod=+x"
],
"*.@(json|jsonc|json5|md|mdx|yaml|yml)": "prettier --write",
"*.@(ts|tsx|mts|js|jsx|mjs|cjs)": [
"oxlint --fix",
"prettier --write"
]
"oxlint --fix --quiet",
"oxfmt --write"
],
"*.@(json|jsonc|json5|md|mdx|yaml|yml|css|scss|sass|html|toml)": "oxfmt --write",
".github/workflows/*.@(yml|yaml)": "actionlint"
},
"repository": {
"type": "git",
Expand All @@ -48,16 +48,18 @@
"dependencies": {
"@google-cloud/firestore": "^7.8.0",
"firebase-tools": "^13.10.2",
"firestore-backfire": "^2.5.3",
"prettier": "^2.8.7"
"firestore-backfire": "^2.5.3"
},
"devDependencies": {
"@typescript/native-preview": "^7.0.0-dev.20260505.1",
"@vitest/coverage-v8": "^3.2.4",
"@vitest/ui": "^3.2.4",
"eslint": "^10.3.0",
"eslint-plugin-unicorn": "^64.0.0",
"husky": "^9.1.7",
"lint-staged": "^15.4.3",
"oxfmt": "^0.48.0",
"oxlint": "^1.32.0",
"shellcheck": "^4.1.0",
"typescript": "^5.9.3",
"vitest": "^3.2.4"
},
Expand Down
Loading
Loading