Initial commit: migrated from GitHub
This commit is contained in:
20
Dockerfile
Normal file
20
Dockerfile
Normal file
@@ -0,0 +1,20 @@
|
|||||||
|
# Use Node LTS image
|
||||||
|
FROM node:18-alpine
|
||||||
|
|
||||||
|
# Set working directory
|
||||||
|
WORKDIR /app
|
||||||
|
|
||||||
|
# Copy dependency files
|
||||||
|
COPY package*.json ./
|
||||||
|
|
||||||
|
# Install dependencies
|
||||||
|
RUN npm install
|
||||||
|
|
||||||
|
# Copy the rest of the app
|
||||||
|
COPY . .
|
||||||
|
|
||||||
|
# Expose development port
|
||||||
|
EXPOSE 3000
|
||||||
|
|
||||||
|
# Start the dev server
|
||||||
|
CMD ["npm", "run", "dev"]
|
||||||
14
docker-compose.yml
Normal file
14
docker-compose.yml
Normal file
@@ -0,0 +1,14 @@
|
|||||||
|
version: '3.8'
|
||||||
|
|
||||||
|
services:
|
||||||
|
chesskit:
|
||||||
|
build: .
|
||||||
|
ports:
|
||||||
|
- "3100:3000"
|
||||||
|
volumes:
|
||||||
|
- .:/app
|
||||||
|
- /app/node_modules # Prevent overwriting node_modules
|
||||||
|
environment:
|
||||||
|
- NODE_ENV=development
|
||||||
|
stdin_open: true
|
||||||
|
tty: true
|
||||||
@@ -4,25 +4,34 @@ import { Stockfish16 } from "./stockfish16";
|
|||||||
import { Stockfish16_1 } from "./stockfish16_1";
|
import { Stockfish16_1 } from "./stockfish16_1";
|
||||||
import { Stockfish17 } from "./stockfish17";
|
import { Stockfish17 } from "./stockfish17";
|
||||||
|
|
||||||
export const isWasmSupported = () =>
|
export const isWasmSupported = (): boolean =>
|
||||||
typeof WebAssembly === "object" &&
|
typeof WebAssembly === "object" &&
|
||||||
WebAssembly.validate(
|
WebAssembly.validate(
|
||||||
Uint8Array.of(0x0, 0x61, 0x73, 0x6d, 0x01, 0x00, 0x00, 0x00)
|
Uint8Array.of(0x0, 0x61, 0x73, 0x6d, 0x01, 0x00, 0x00, 0x00)
|
||||||
);
|
);
|
||||||
|
|
||||||
export const isMultiThreadSupported = () => {
|
export const isIosDevice = (): boolean => {
|
||||||
|
if (typeof navigator !== "undefined") {
|
||||||
|
return /iPhone|iPad|iPod/i.test(navigator.userAgent);
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
};
|
||||||
|
|
||||||
|
export const isMobileDevice = (): boolean => {
|
||||||
|
if (typeof navigator !== "undefined") {
|
||||||
|
return isIosDevice() || /Android|Opera Mini/i.test(navigator.userAgent);
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
};
|
||||||
|
|
||||||
|
export const isMultiThreadSupported = (): boolean => {
|
||||||
try {
|
try {
|
||||||
return SharedArrayBuffer !== undefined && !isIosDevice();
|
return typeof SharedArrayBuffer !== "undefined" && !isIosDevice();
|
||||||
} catch {
|
} catch {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
export const isIosDevice = () => /iPhone|iPad|iPod/i.test(navigator.userAgent);
|
|
||||||
|
|
||||||
export const isMobileDevice = () =>
|
|
||||||
isIosDevice() || /Android|Opera Mini/i.test(navigator.userAgent);
|
|
||||||
|
|
||||||
export const isEngineSupported = (name: EngineName): boolean => {
|
export const isEngineSupported = (name: EngineName): boolean => {
|
||||||
switch (name) {
|
switch (name) {
|
||||||
case EngineName.Stockfish17:
|
case EngineName.Stockfish17:
|
||||||
@@ -36,5 +45,7 @@ export const isEngineSupported = (name: EngineName): boolean => {
|
|||||||
return Stockfish16.isSupported();
|
return Stockfish16.isSupported();
|
||||||
case EngineName.Stockfish11:
|
case EngineName.Stockfish11:
|
||||||
return Stockfish11.isSupported();
|
return Stockfish11.isSupported();
|
||||||
|
default:
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -45,16 +45,21 @@ export const sendCommandsToWorker = (
|
|||||||
};
|
};
|
||||||
|
|
||||||
export const getRecommendedWorkersNb = (): number => {
|
export const getRecommendedWorkersNb = (): number => {
|
||||||
const maxWorkersNbFromThreads = Math.max(
|
let maxWorkersNbFromThreads = 4;
|
||||||
1,
|
let maxWorkersNbFromMemory = 4;
|
||||||
Math.round(navigator.hardwareConcurrency - 4),
|
|
||||||
Math.floor((navigator.hardwareConcurrency * 2) / 3)
|
|
||||||
);
|
|
||||||
|
|
||||||
const maxWorkersNbFromMemory =
|
if (typeof navigator !== "undefined") {
|
||||||
"deviceMemory" in navigator && typeof navigator.deviceMemory === "number"
|
maxWorkersNbFromThreads = Math.max(
|
||||||
? Math.max(1, Math.round(navigator.deviceMemory))
|
1,
|
||||||
: 4;
|
Math.round(navigator.hardwareConcurrency - 4),
|
||||||
|
Math.floor((navigator.hardwareConcurrency * 2) / 3)
|
||||||
|
);
|
||||||
|
|
||||||
|
maxWorkersNbFromMemory =
|
||||||
|
"deviceMemory" in navigator && typeof navigator.deviceMemory === "number"
|
||||||
|
? Math.max(1, Math.round(navigator.deviceMemory))
|
||||||
|
: 4;
|
||||||
|
}
|
||||||
|
|
||||||
const maxWorkersNbFromDevice = isIosDevice() ? 2 : isMobileDevice() ? 4 : 8;
|
const maxWorkersNbFromDevice = isIosDevice() ? 2 : isMobileDevice() ? 4 : 8;
|
||||||
|
|
||||||
|
|||||||
@@ -1,11 +1,12 @@
|
|||||||
import { DEFAULT_ENGINE } from "@/constants";
|
import { DEFAULT_ENGINE } from "@/constants";
|
||||||
import { getRecommendedWorkersNb } from "@/lib/engine/worker";
|
import { getRecommendedWorkersNb } from "@/lib/engine/worker"; // ✅ Already includes navigator guards
|
||||||
import { EngineName } from "@/types/enums";
|
import { EngineName } from "@/types/enums";
|
||||||
import { CurrentPosition, GameEval, SavedEvals } from "@/types/eval";
|
import { CurrentPosition, GameEval, SavedEvals } from "@/types/eval";
|
||||||
import { Chess } from "chess.js";
|
import { Chess } from "chess.js";
|
||||||
import { atom } from "jotai";
|
import { atom } from "jotai";
|
||||||
import { atomWithStorage } from "jotai/utils";
|
import { atomWithStorage } from "jotai/utils";
|
||||||
|
|
||||||
|
// ✅ Core atoms for game state and UI
|
||||||
export const gameEvalAtom = atom<GameEval | undefined>(undefined);
|
export const gameEvalAtom = atom<GameEval | undefined>(undefined);
|
||||||
export const gameAtom = atom(new Chess());
|
export const gameAtom = atom(new Chess());
|
||||||
export const boardAtom = atom(new Chess());
|
export const boardAtom = atom(new Chess());
|
||||||
@@ -15,13 +16,16 @@ export const boardOrientationAtom = atom(true);
|
|||||||
export const showBestMoveArrowAtom = atom(true);
|
export const showBestMoveArrowAtom = atom(true);
|
||||||
export const showPlayerMoveIconAtom = atom(true);
|
export const showPlayerMoveIconAtom = atom(true);
|
||||||
|
|
||||||
|
// ✅ Engine config atoms
|
||||||
export const engineNameAtom = atom<EngineName>(DEFAULT_ENGINE);
|
export const engineNameAtom = atom<EngineName>(DEFAULT_ENGINE);
|
||||||
export const engineDepthAtom = atom(14);
|
export const engineDepthAtom = atom(14);
|
||||||
export const engineMultiPvAtom = atom(3);
|
export const engineMultiPvAtom = atom(3);
|
||||||
|
|
||||||
|
// ✅ This line is now safe thanks to navigator guards in the function
|
||||||
export const engineWorkersNbAtom = atomWithStorage(
|
export const engineWorkersNbAtom = atomWithStorage(
|
||||||
"engineWorkersNb",
|
"engineWorkersNb",
|
||||||
getRecommendedWorkersNb()
|
getRecommendedWorkersNb()
|
||||||
);
|
);
|
||||||
export const evaluationProgressAtom = atom(0);
|
|
||||||
|
|
||||||
|
export const evaluationProgressAtom = atom(0);
|
||||||
export const savedEvalsAtom = atom<SavedEvals>({});
|
export const savedEvalsAtom = atom<SavedEvals>({});
|
||||||
|
|||||||
Reference in New Issue
Block a user