diff --git a/packages/common/utils/platforms.ts b/packages/common/utils/platforms.ts index c0d84326..370a148c 100644 --- a/packages/common/utils/platforms.ts +++ b/packages/common/utils/platforms.ts @@ -1,25 +1,33 @@ -export function platformResolver(platform: string) { - let platformType = ''; - let platformFileType = ''; - let platformCommand = ''; +export type Platform = 'windows' | 'linux' | 'macos' | 'unknown'; + +interface IPlatform { + type: Platform; + fileType: string; + command: string; +} + +export function platformResolver(platform: string): IPlatform { + let type: Platform = 'unknown'; + let fileType = ''; + let command = ''; switch (platform) { case 'win32': - platformType = 'windows'; - platformFileType = '.exe'; - platformCommand = 'start ""'; + type = 'windows'; + fileType = '.exe'; + command = 'start ""'; break; case 'linux': - platformType = 'linux'; - platformCommand = 'xdg-open'; + type = 'linux'; + command = 'xdg-open'; break; case 'darwin': - platformType = 'macos'; - platformCommand = 'open -R'; + type = 'macos'; + command = 'open -R'; break; } - return { platformType, platformFileType, platformCommand }; + return { type, fileType, command }; } diff --git a/packages/server/router/index.ts b/packages/server/router/index.ts index 8df35662..feadfdcf 100644 --- a/packages/server/router/index.ts +++ b/packages/server/router/index.ts @@ -34,7 +34,9 @@ const pkgAssetsPath = export default function buildBaseApi(server: Server) { server.app.route('/json', 'GET', (req, res) => { - const osuInstance: any = req.instanceManager.getInstance(); + const osuInstance: any = req.instanceManager.getInstance( + req.instanceManager.focusedClient + ); if (!osuInstance) { res.statusCode = 500; wLogger.debug('/json', 'not_ready'); @@ -175,8 +177,8 @@ export default function buildBaseApi(server: Server) { `PP Counter opened: ${folderName} (${req.headers.referer})` ); - const { platformCommand } = platformResolver(process.platform); - exec(`${platformCommand} "${folderPath}"`, (err) => { + const platform = platformResolver(process.platform); + exec(`${platform.command} "${folderPath}"`, (err) => { if (err) { wLogger.error('Error opening file explorer:'); wLogger.debug(err); @@ -393,7 +395,9 @@ export default function buildBaseApi(server: Server) { try { const query: any = req.query; - const osuInstance: any = req.instanceManager.getInstance(); + const osuInstance: any = req.instanceManager.getInstance( + req.instanceManager.focusedClient + ); if (!osuInstance) { res.statusCode = 500; return sendJson(res, { error: 'not_ready' }); diff --git a/packages/server/router/scApi.ts b/packages/server/router/scApi.ts index 9ba14af6..a287afdc 100644 --- a/packages/server/router/scApi.ts +++ b/packages/server/router/scApi.ts @@ -3,7 +3,9 @@ import { beatmapFileShortcut } from '../scripts/beatmapFile'; export default function buildSCApi(app: HttpServer) { app.route('/json/sc', 'GET', (req, res) => { - const osuInstance: any = req.instanceManager.getInstance(); + const osuInstance: any = req.instanceManager.getInstance( + req.instanceManager.focusedClient + ); if (!osuInstance) { res.statusCode = 500; return sendJson(res, { error: 'not_ready' }); diff --git a/packages/server/router/v1.ts b/packages/server/router/v1.ts index 1137ca48..66d41071 100644 --- a/packages/server/router/v1.ts +++ b/packages/server/router/v1.ts @@ -8,7 +8,9 @@ export default function buildV1Api(app: HttpServer) { try { const url = req.pathname || '/'; - const osuInstance: any = req.instanceManager.getInstance(); + const osuInstance: any = req.instanceManager.getInstance( + req.instanceManager.focusedClient + ); if (!osuInstance) { res.statusCode = 500; return sendJson(res, { error: 'not_ready' }); diff --git a/packages/server/router/v2.ts b/packages/server/router/v2.ts index da000efd..940c35ec 100644 --- a/packages/server/router/v2.ts +++ b/packages/server/router/v2.ts @@ -7,7 +7,9 @@ import { directoryWalker } from '../utils/directories'; export default function buildV2Api(app: HttpServer) { app.route('/json/v2', 'GET', (req, res) => { - const osuInstance: any = req.instanceManager.getInstance(); + const osuInstance: any = req.instanceManager.getInstance( + req.instanceManager.focusedClient + ); if (!osuInstance) { res.statusCode = 500; return sendJson(res, { error: 'not_ready' }); @@ -18,7 +20,9 @@ export default function buildV2Api(app: HttpServer) { }); app.route('/json/v2/precise', 'GET', (req, res) => { - const osuInstance: any = req.instanceManager.getInstance(); + const osuInstance: any = req.instanceManager.getInstance( + req.instanceManager.focusedClient + ); if (!osuInstance) { res.statusCode = 500; return sendJson(res, { error: 'not_ready' }); @@ -38,7 +42,9 @@ export default function buildV2Api(app: HttpServer) { try { const url = req.pathname || '/'; - const osuInstance: any = req.instanceManager.getInstance(); + const osuInstance: any = req.instanceManager.getInstance( + req.instanceManager.focusedClient + ); if (!osuInstance) { res.statusCode = 500; return sendJson(res, { error: 'not_ready' }); @@ -69,7 +75,9 @@ export default function buildV2Api(app: HttpServer) { try { const url = req.pathname || '/'; - const osuInstance: any = req.instanceManager.getInstance(); + const osuInstance: any = req.instanceManager.getInstance( + req.instanceManager.focusedClient + ); if (!osuInstance) { res.statusCode = 500; return sendJson(res, { error: 'not_ready' }); diff --git a/packages/server/scripts/beatmapFile.ts b/packages/server/scripts/beatmapFile.ts index d4528ef5..21433998 100644 --- a/packages/server/scripts/beatmapFile.ts +++ b/packages/server/scripts/beatmapFile.ts @@ -14,7 +14,9 @@ export function beatmapFileShortcut( try { const url = req.pathname || '/'; - const osuInstance: any = req.instanceManager.getInstance(); + const osuInstance: any = req.instanceManager.getInstance( + req.instanceManager.focusedClient + ); if (!osuInstance) { res.statusCode = 500; return sendJson(res, { error: 'not_ready' }); diff --git a/packages/server/utils/socket.ts b/packages/server/utils/socket.ts index 161b8bab..2483ca3b 100644 --- a/packages/server/utils/socket.ts +++ b/packages/server/utils/socket.ts @@ -126,7 +126,9 @@ export class Websocket { startLoop() { this.loopInterval = setInterval(() => { try { - const osuInstance: any = this.instanceManager.getInstance(); + const osuInstance: any = this.instanceManager.getInstance( + this.instanceManager.focusedClient + ); if (!osuInstance || this.clients.size === 0) { return; // Exit the loop if conditions are not met } diff --git a/packages/tosu/src/api/utils/buildResult.ts b/packages/tosu/src/api/utils/buildResult.ts index 55dea98a..fafec9c3 100644 --- a/packages/tosu/src/api/utils/buildResult.ts +++ b/packages/tosu/src/api/utils/buildResult.ts @@ -30,7 +30,9 @@ const convertMemoryPlayerToResult = ( }); export const buildResult = (instanceManager: InstanceManager): ApiAnswer => { - const osuInstance = instanceManager.getInstance(); + const osuInstance = instanceManager.getInstance( + instanceManager.focusedClient + ); if (!osuInstance) { return { error: 'not_ready' }; } diff --git a/packages/tosu/src/api/utils/buildResultSC.ts b/packages/tosu/src/api/utils/buildResultSC.ts index 61bc2701..447183da 100644 --- a/packages/tosu/src/api/utils/buildResultSC.ts +++ b/packages/tosu/src/api/utils/buildResultSC.ts @@ -14,7 +14,9 @@ import { fixDecimals } from '@/utils/converters'; import { ApiAnswer } from '../types/sc'; export const buildResult = (instanceManager: InstanceManager): ApiAnswer => { - const osuInstance = instanceManager.getInstance(); + const osuInstance = instanceManager.getInstance( + instanceManager.focusedClient + ); if (!osuInstance) { return { error: 'not_ready' }; } diff --git a/packages/tosu/src/api/utils/buildResultV2.ts b/packages/tosu/src/api/utils/buildResultV2.ts index 37d5c767..9c29d867 100644 --- a/packages/tosu/src/api/utils/buildResultV2.ts +++ b/packages/tosu/src/api/utils/buildResultV2.ts @@ -78,7 +78,9 @@ const convertMemoryPlayerToResult = ( }; export const buildResult = (instanceManager: InstanceManager): ApiAnswer => { - const osuInstance = instanceManager.getInstance(); + const osuInstance = instanceManager.getInstance( + instanceManager.focusedClient + ); if (!osuInstance) { return { error: 'not_ready' }; } diff --git a/packages/tosu/src/api/utils/buildResultV2Precise.ts b/packages/tosu/src/api/utils/buildResultV2Precise.ts index c7f31e5f..4e70358f 100644 --- a/packages/tosu/src/api/utils/buildResultV2Precise.ts +++ b/packages/tosu/src/api/utils/buildResultV2Precise.ts @@ -48,7 +48,9 @@ const buildTourneyData = ( }; export const buildResult = (instanceManager: InstanceManager): ApiAnswer => { - const osuInstance = instanceManager.getInstance(); + const osuInstance = instanceManager.getInstance( + instanceManager.focusedClient + ); if (!osuInstance) { return { error: 'not_ready' }; } diff --git a/packages/tosu/src/index.ts b/packages/tosu/src/index.ts index d7d56e92..264fd358 100644 --- a/packages/tosu/src/index.ts +++ b/packages/tosu/src/index.ts @@ -41,4 +41,5 @@ const currentVersion = require(process.cwd() + '/_version.js'); httpServer.start(); instanceManager.runWatcher(); + instanceManager.runDetemination(); })(); diff --git a/packages/tosu/src/instances/manager.ts b/packages/tosu/src/instances/manager.ts index e69a4442..db37bba4 100644 --- a/packages/tosu/src/instances/manager.ts +++ b/packages/tosu/src/instances/manager.ts @@ -1,4 +1,10 @@ -import { argumetsParser, wLogger } from '@tosu/common'; +import { + ClientType, + Platform, + argumetsParser, + platformResolver, + wLogger +} from '@tosu/common'; import { Process } from 'tsprocess/dist/process'; import { AbstractInstance } from '@/instances'; @@ -7,6 +13,9 @@ import { LazerInstance } from './lazerInstance'; import { OsuInstance } from './osuInstance'; export class InstanceManager { + platformType: Platform; + focusedClient: ClientType; + osuInstances: { [key: number]: AbstractInstance; }; @@ -15,19 +24,33 @@ export class InstanceManager { this.osuInstances = {}; this.runWatcher = this.runWatcher.bind(this); + this.runDetemination = this.runDetemination.bind(this); } /** * Gets a regular instance if osu running in normal mode, else gets tournament manager */ - public getInstance() { + public getInstance(clientType?: ClientType) { if (Object.keys(this.osuInstances).length === 0) return; for (const key in this.osuInstances) { - if (this.osuInstances[key].isTourneyManager) { - return this.osuInstances[key]; + const instance = this.osuInstances[key]; + const ClientFilter = + typeof ClientType[clientType as any] !== 'undefined' + ? instance.client === clientType + : true; + + if (instance.isTourneyManager && ClientFilter) { + return instance; } } + + if (typeof clientType === 'number') { + const search = Object.values(this.osuInstances).find( + (r) => r.client === clientType + ); + return search; + } return Object.values(this.osuInstances)[0]; } @@ -100,4 +123,37 @@ export class InstanceManager { setTimeout(this.runWatcher, 1000); } + + runDetemination() { + if (!this.platformType) { + const platform = platformResolver(process.platform); + this.platformType = platform.type; + } + + if (this.platformType !== 'windows') return; + + const s1 = performance.now(); + const focusedPID = Process.getFocusedProcess(); + const instance = Object.values(this.osuInstances).find( + (r) => r.pid === focusedPID + ); + if (instance) this.focusedClient = instance.client; + + if (this.focusedClient === undefined) { + this.focusedClient = + this.getInstance()?.client || ClientType.stable; + } + + console.log( + 'focused', + ClientType[this.focusedClient], + Object.values(this.osuInstances).map((r) => ({ + id: r.pid, + client: r.client + })), + performance.now() - s1 + ); + + setTimeout(this.runDetemination, 100); + } } diff --git a/packages/updater/index.ts b/packages/updater/index.ts index ddab272b..0ddbfe48 100644 --- a/packages/updater/index.ts +++ b/packages/updater/index.ts @@ -19,7 +19,7 @@ const platform = platformResolver(process.platform); const fileDestination = path.join(getProgramPath(), 'update.zip'); const backupExecutablePath = path.join( getProgramPath(), - `tosu_old${platform.platformFileType}` + `tosu_old${platform.fileType}` ); const deleteNotLocked = async (filePath: string) => { @@ -41,7 +41,7 @@ export const checkUpdates = async () => { wLogger.info('Checking updates'); try { - if (platform.platformType === '') { + if (platform.type === 'unknown') { wLogger.warn( `Unsupported platform (${process.platform}). Unable to run updater` ); @@ -107,14 +107,10 @@ export const autoUpdater = async () => { } const findAsset = assets.find( - (r) => - r.name.includes(platform.platformType) && - r.name.endsWith('.zip') + (r) => r.name.includes(platform.type) && r.name.endsWith('.zip') ); if (!findAsset) { - wLogger.info( - `Files to update not found (${platform.platformType})` - ); + wLogger.info(`Files to update not found (${platform.type})`); return 'noFiles'; }