mirror of
https://github.com/Zagrios/bs-manager.git
synced 2026-07-03 14:08:25 +02:00
detection of oculus beat saber installation
This commit is contained in:
@@ -1,3 +1,4 @@
|
||||
export const BS_EXECUTABLE = "Beat Saber.exe";
|
||||
export const OCULUS_BS_DIR = "hyperbolic-magnetism-beat-saber"
|
||||
export const BS_APP_ID = "620980";
|
||||
export const BS_DEPOT = "620981";
|
||||
|
||||
@@ -3,7 +3,7 @@ import { BSVersion } from 'shared/bs-version.interface';
|
||||
import { InstallationLocationService } from "./installation-location.service";
|
||||
import { SteamService } from "./steam.service";
|
||||
import { UtilsService } from "./utils.service";
|
||||
import { BS_APP_ID } from "../constants";
|
||||
import { BS_APP_ID, OCULUS_BS_DIR } from "../constants";
|
||||
import path from "path";
|
||||
import { createInterface } from "readline";
|
||||
import { createReadStream } from "fs";
|
||||
@@ -12,6 +12,8 @@ import { ConfigurationService } from "./configuration.service";
|
||||
import { rename } from "fs/promises";
|
||||
import { BsmException } from "shared/models/bsm-exception.model";
|
||||
import log from "electron-log";
|
||||
import { OculusService } from "./oculus.service";
|
||||
import { DownloadLinkType } from "shared/models/mods";
|
||||
|
||||
export class BSLocalVersionService{
|
||||
|
||||
@@ -22,6 +24,7 @@ export class BSLocalVersionService{
|
||||
private readonly installLocationService: InstallationLocationService;
|
||||
private readonly utilsService: UtilsService;
|
||||
private readonly steamService: SteamService;
|
||||
private readonly oculusService: OculusService;
|
||||
private readonly remoteVersionService: BSVersionLibService;
|
||||
private readonly configService: ConfigurationService;
|
||||
|
||||
@@ -34,6 +37,7 @@ export class BSLocalVersionService{
|
||||
this.installLocationService = InstallationLocationService.getInstance();
|
||||
this.utilsService = UtilsService.getInstance();
|
||||
this.steamService = SteamService.getInstance();
|
||||
this.oculusService = OculusService.getInstance();
|
||||
this.remoteVersionService = BSVersionLibService.getInstance();
|
||||
this.configService = ConfigurationService.getInstance();
|
||||
}
|
||||
@@ -80,6 +84,7 @@ export class BSLocalVersionService{
|
||||
|
||||
public async getVersionPath(version: BSVersion): Promise<string>{
|
||||
if(version.steam){ return this.steamService.getGameFolder(BS_APP_ID, "Beat Saber") }
|
||||
if(version.oculus){ return this.oculusService.getGameFolder(OCULUS_BS_DIR); }
|
||||
return path.join(
|
||||
this.installLocationService.versionsDirectory,
|
||||
this.getVersionFolder(version)
|
||||
@@ -87,7 +92,6 @@ export class BSLocalVersionService{
|
||||
}
|
||||
|
||||
private removeSpecialChar(seq: string): string{
|
||||
// eslint-disable-next-line no-useless-escape
|
||||
return seq.replace( /[<>:"\/\\|?*]+/g, '' );
|
||||
}
|
||||
|
||||
@@ -95,27 +99,46 @@ export class BSLocalVersionService{
|
||||
return version.name ? `${version.BSVersion}-${version.name}` : version.BSVersion;
|
||||
}
|
||||
|
||||
public getVersionType(version: BSVersion): "steam"|"universal"{
|
||||
public getVersionType(version: BSVersion): DownloadLinkType{
|
||||
if(version.steam){ return "steam"; }
|
||||
if(version.oculus){ return "oculus"; }
|
||||
return "universal"
|
||||
}
|
||||
|
||||
private async getSteamVersion(): Promise<BSVersion>{
|
||||
const steamBsFolder = await this.steamService.getGameFolder(BS_APP_ID, "Beat Saber");
|
||||
if(!steamBsFolder || !this.utilsService.pathExist(steamBsFolder)){ return null; }
|
||||
const steamBsVersion = await this.getVersionOfBSFolder(steamBsFolder);
|
||||
if(!steamBsVersion){ return null; }
|
||||
const version = await this.remoteVersionService.getVersionDetails(steamBsVersion);
|
||||
if(!version){ return null; }
|
||||
return {...version, steam: true};
|
||||
}
|
||||
|
||||
private async getOculusVersion(): Promise<BSVersion>{
|
||||
const oculusBsFolder = await this.oculusService.getGameFolder(OCULUS_BS_DIR);
|
||||
if(!oculusBsFolder){ return null; }
|
||||
const oculusBsVersion = await this.getVersionOfBSFolder(oculusBsFolder);
|
||||
if(!oculusBsVersion){ return null; }
|
||||
const version = await this.remoteVersionService.getVersionDetails(oculusBsVersion);
|
||||
if(!version){ return null; }
|
||||
return {...version, oculus: true};
|
||||
}
|
||||
|
||||
public async getInstalledVersions(): Promise<BSVersion[]>{
|
||||
|
||||
const versions: BSVersion[] = [];
|
||||
const steamBsFolder = await this.steamService.getGameFolder(BS_APP_ID, "Beat Saber");
|
||||
if(steamBsFolder && this.utilsService.pathExist(steamBsFolder)){
|
||||
const steamBsVersion = await this.getVersionOfBSFolder(steamBsFolder);
|
||||
if(steamBsVersion){
|
||||
const steamVersionDetails = this.remoteVersionService.getVersionDetails(steamBsVersion);
|
||||
versions.push(steamVersionDetails ? {...steamVersionDetails, steam: true} : {BSVersion: steamBsVersion, steam: true});
|
||||
}
|
||||
}
|
||||
const steamVersion = await this.getSteamVersion();
|
||||
if(steamVersion){ versions.push(steamVersion); }
|
||||
const oculusVersion = await this.getOculusVersion();
|
||||
if(oculusVersion){ versions.push(oculusVersion); }
|
||||
|
||||
if(!this.utilsService.pathExist(this.installLocationService.versionsDirectory)){ return versions }
|
||||
|
||||
const folderInInstallation = this.utilsService.listDirsInDir(this.installLocationService.versionsDirectory);
|
||||
folderInInstallation.forEach(f => {
|
||||
for(const f of folderInInstallation){
|
||||
log.info("try get version from folder", f);
|
||||
let version = this.remoteVersionService.getVersionDetails(f);
|
||||
let version = await this.remoteVersionService.getVersionDetails(f);
|
||||
if(version){ version = this.getCustomVersions().find(v => v.BSVersion === version.BSVersion && v.name === version.name) ?? version; }
|
||||
else { version = this.getCustomVersions().find(v => {
|
||||
const [version, ...rest] = f.split("-");
|
||||
@@ -125,7 +148,7 @@ export class BSLocalVersionService{
|
||||
})
|
||||
}
|
||||
version && versions.push(version);
|
||||
});
|
||||
};
|
||||
this.setCustomVersions(versions.filter(v => !!v.name || !!v.color));
|
||||
return versions;
|
||||
}
|
||||
|
||||
@@ -16,7 +16,7 @@ export class BSVersionLibService{
|
||||
private utilsService: UtilsService;
|
||||
private requestService: RequestService
|
||||
|
||||
private bsVersions: BSVersion[] = [];
|
||||
private bsVersions: BSVersion[];
|
||||
|
||||
private constructor(){
|
||||
this.utilsService = UtilsService.getInstance();
|
||||
@@ -44,25 +44,26 @@ export class BSVersionLibService{
|
||||
writeFileSync(localVersionsPath, JSON.stringify(versions, null, "\t"), {encoding: 'utf-8', flag: 'w'});
|
||||
};
|
||||
|
||||
private async loadBsVersions(): Promise<BSVersion[]>{
|
||||
const [localVersions, remoteVersions] = await Promise.all([
|
||||
this.getLocalVersions(), (await isOnline({timeout: 1500}) && this.getRemoteVersions())
|
||||
]);
|
||||
let resVersions = localVersions;
|
||||
if(remoteVersions && remoteVersions.length){ resVersions = remoteVersions; this.updateLocalVersions(resVersions); }
|
||||
this.bsVersions = resVersions;
|
||||
return this.bsVersions;
|
||||
private async loadBsVersions(): Promise<BSVersion[]>{
|
||||
if(this.bsVersions){ return this.bsVersions; }
|
||||
const [localVersions, remoteVersions] = await Promise.all([
|
||||
this.getLocalVersions(), (await isOnline({timeout: 1500}) && this.getRemoteVersions())
|
||||
]);
|
||||
let resVersions = localVersions;
|
||||
if(remoteVersions && remoteVersions.length){ resVersions = remoteVersions; this.updateLocalVersions(resVersions); }
|
||||
this.bsVersions = resVersions;
|
||||
return this.bsVersions;
|
||||
}
|
||||
|
||||
public async getAvailableVersions(): Promise<BSVersion[]>{
|
||||
if(this.bsVersions && this.bsVersions.length){ return this.bsVersions; }
|
||||
const bsVersions = await this.loadBsVersions();
|
||||
if(!bsVersions || !bsVersions.length){ return []; }
|
||||
return bsVersions;
|
||||
}
|
||||
|
||||
public getVersionDetails(version: string): BSVersion{
|
||||
return this.bsVersions.find(v => v.BSVersion === version);
|
||||
}
|
||||
public async getVersionDetails(version: string): Promise<BSVersion>{
|
||||
const versions = await this.getAvailableVersions();
|
||||
return versions.find(v => v.BSVersion === version);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,63 @@
|
||||
import { UtilsService } from "./utils.service";
|
||||
import regedit from 'regedit'
|
||||
import path from "path";
|
||||
|
||||
export class OculusService {
|
||||
|
||||
private static instance: OculusService;
|
||||
|
||||
private readonly utils: UtilsService;
|
||||
|
||||
private oculusPaths: string[];
|
||||
|
||||
public static getInstance(): OculusService{
|
||||
if(!OculusService.instance){ OculusService.instance = new OculusService(); }
|
||||
return OculusService.instance;
|
||||
}
|
||||
|
||||
private constructor(){
|
||||
this.utils = UtilsService.getInstance();
|
||||
}
|
||||
|
||||
public oculusRunning(): boolean{
|
||||
return this.utils.taskRunning("OculusClient.exe");
|
||||
}
|
||||
|
||||
public async getOculusLibsPath(): Promise<string[]>{
|
||||
|
||||
if(this.oculusPaths){ return this.oculusPaths; }
|
||||
|
||||
const oculusLibsRegKey = "HKCU\\SOFTWARE\\Oculus VR, LLC\\Oculus\\Libraries";
|
||||
|
||||
const libsRegData = (await regedit.promisified.list([oculusLibsRegKey]))["HKCU\\SOFTWARE\\Oculus VR, LLC\\Oculus\\Libraries"];
|
||||
|
||||
if(!libsRegData.exists || !libsRegData.keys){ return null; }
|
||||
|
||||
const libsPath = (await Promise.all(libsRegData.keys.map(async key => {
|
||||
const originalPath = (await regedit.promisified.list([`${oculusLibsRegKey}\\${key}`]))[`${oculusLibsRegKey}\\${key}`];
|
||||
if(!originalPath.exists || !libsRegData.values || !originalPath.values["OriginalPath"]){ return null; }
|
||||
|
||||
return originalPath.values["OriginalPath"].value as string;
|
||||
|
||||
}, []))).filter(path => !!path);
|
||||
|
||||
this.oculusPaths = libsPath;
|
||||
|
||||
return libsPath;
|
||||
|
||||
}
|
||||
|
||||
public async getGameFolder(gameFolder: string): Promise<string>{
|
||||
|
||||
const libsFolders = await this.getOculusLibsPath();
|
||||
const rootLibDir = "Software"
|
||||
|
||||
for(const lib of libsFolders){
|
||||
const gameFullPath = path.join(lib, rootLibDir, gameFolder);
|
||||
if(this.utils.pathExist(gameFullPath)){ return gameFullPath; }
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -6,6 +6,7 @@ export interface BSVersion {
|
||||
ReleaseDate?: string,
|
||||
year?: string,
|
||||
steam?: boolean,
|
||||
oculus?: boolean,
|
||||
name?: string,
|
||||
color?: string
|
||||
}
|
||||
Reference in New Issue
Block a user