mirror of
https://github.com/hydralauncher/hydra.git
synced 2025-02-12 19:22:28 +00:00
feat: saving achievements on open launcher
This commit is contained in:
parent
8fb62af0cf
commit
500cd2a531
7 changed files with 63 additions and 58 deletions
|
@ -16,6 +16,9 @@ export class GameAchievement {
|
||||||
@JoinColumn()
|
@JoinColumn()
|
||||||
game: Game;
|
game: Game;
|
||||||
|
|
||||||
|
@Column("text", { nullable: true })
|
||||||
|
unlockedAchievements: string;
|
||||||
|
|
||||||
@Column("text", { nullable: true })
|
@Column("text", { nullable: true })
|
||||||
achievements: string;
|
achievements: string;
|
||||||
}
|
}
|
||||||
|
|
|
@ -22,7 +22,9 @@ export const getGameAchievementsToWatch = async (
|
||||||
const steamId = Number(game.objectID);
|
const steamId = Number(game.objectID);
|
||||||
|
|
||||||
const achievements = await steamGetAchivement(game);
|
const achievements = await steamGetAchivement(game);
|
||||||
|
|
||||||
console.log(achievements);
|
console.log(achievements);
|
||||||
|
|
||||||
if (!achievements || !achievements.length) return;
|
if (!achievements || !achievements.length) return;
|
||||||
|
|
||||||
const achievementFiles = steamFindGameAchievementFiles(game.objectID)[
|
const achievementFiles = steamFindGameAchievementFiles(game.objectID)[
|
||||||
|
@ -50,7 +52,7 @@ export const getGameAchievementsToWatch = async (
|
||||||
game: { id: gameId },
|
game: { id: gameId },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
achievements: JSON.stringify(checkedAchievements.all),
|
unlockedAchievements: JSON.stringify(checkedAchievements.all),
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,11 +1,7 @@
|
||||||
import { gameAchievementRepository, gameRepository } from "@main/repository";
|
import { gameAchievementRepository, gameRepository } from "@main/repository";
|
||||||
import { steamFindGameAchievementFiles } from "../steam/steam-find-game-achivement-files";
|
import { steamFindGameAchievementFiles } from "../steam/steam-find-game-achivement-files";
|
||||||
import { steamGlobalAchievementPercentages } from "../steam/steam-global-achievement-percentages";
|
|
||||||
import { steamAchievementInfo } from "../steam/steam-achievement-info";
|
|
||||||
import { steamAchievementMerge } from "../steam/steam-achievement-merge";
|
|
||||||
import { parseAchievementFile } from "../util/parseAchievementFile";
|
import { parseAchievementFile } from "../util/parseAchievementFile";
|
||||||
import { checkUnlockedAchievements } from "../util/check-unlocked-achievements";
|
import { HydraApi } from "@main/services";
|
||||||
import { CheckedAchievements } from "../types";
|
|
||||||
|
|
||||||
export const saveAllLocalSteamAchivements = async () => {
|
export const saveAllLocalSteamAchivements = async () => {
|
||||||
const gameAchievementFiles = steamFindGameAchievementFiles();
|
const gameAchievementFiles = steamFindGameAchievementFiles();
|
||||||
|
@ -19,56 +15,56 @@ export const saveAllLocalSteamAchivements = async () => {
|
||||||
|
|
||||||
if (!game) continue;
|
if (!game) continue;
|
||||||
|
|
||||||
const hasOnDb = await gameAchievementRepository.existsBy({
|
const savedGameAchievements = await gameAchievementRepository.findOneBy({
|
||||||
game: game,
|
game: game,
|
||||||
});
|
});
|
||||||
|
|
||||||
if (hasOnDb) continue;
|
if (!savedGameAchievements || !savedGameAchievements.achievements) {
|
||||||
|
HydraApi.get(
|
||||||
const achievementPercentage =
|
"/games/achievements",
|
||||||
await steamGlobalAchievementPercentages(objectId);
|
{
|
||||||
|
shop: "steam",
|
||||||
if (!achievementPercentage) {
|
objectId,
|
||||||
await gameAchievementRepository.save({
|
},
|
||||||
game,
|
{ needsAuth: false }
|
||||||
achievements: "[]",
|
)
|
||||||
});
|
.then((achievements) => {
|
||||||
continue;
|
return gameAchievementRepository.upsert(
|
||||||
|
{
|
||||||
|
game: { id: game.id },
|
||||||
|
achievements: JSON.stringify(achievements),
|
||||||
|
},
|
||||||
|
["game"]
|
||||||
|
);
|
||||||
|
})
|
||||||
|
.catch(console.log);
|
||||||
}
|
}
|
||||||
|
|
||||||
const achievementInfo = await steamAchievementInfo(objectId);
|
const unlockedAchievements: { name: string; unlockTime: number }[] = [];
|
||||||
|
|
||||||
if (!achievementInfo) continue;
|
|
||||||
|
|
||||||
const achievements = steamAchievementMerge(
|
|
||||||
achievementPercentage,
|
|
||||||
achievementInfo
|
|
||||||
);
|
|
||||||
|
|
||||||
if (!achievements) continue;
|
|
||||||
|
|
||||||
const checkedAchievements: CheckedAchievements = {
|
|
||||||
all: achievements,
|
|
||||||
new: [],
|
|
||||||
};
|
|
||||||
|
|
||||||
for (const achievementFile of gameAchievementFiles[key]) {
|
for (const achievementFile of gameAchievementFiles[key]) {
|
||||||
const localAchievementFile = await parseAchievementFile(
|
const localAchievementFile = await parseAchievementFile(
|
||||||
achievementFile.filePath
|
achievementFile.filePath
|
||||||
);
|
);
|
||||||
|
|
||||||
checkedAchievements.new.push(
|
console.log(achievementFile.filePath);
|
||||||
...checkUnlockedAchievements(
|
console.log(localAchievementFile);
|
||||||
achievementFile.type,
|
|
||||||
localAchievementFile,
|
for (const a of Object.keys(localAchievementFile)) {
|
||||||
achievements
|
// TODO: use checkUnlockedAchievements after refactoring it to be generic
|
||||||
).new
|
unlockedAchievements.push({
|
||||||
);
|
name: a,
|
||||||
|
unlockTime: localAchievementFile[a].UnlockTime,
|
||||||
|
});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
await gameAchievementRepository.save({
|
await gameAchievementRepository.upsert(
|
||||||
game,
|
{
|
||||||
achievements: JSON.stringify(checkedAchievements.all),
|
game: { id: game.id },
|
||||||
});
|
unlockedAchievements: JSON.stringify(unlockedAchievements),
|
||||||
|
},
|
||||||
|
["game"]
|
||||||
|
);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -1,21 +1,21 @@
|
||||||
import path from "node:path";
|
import path from "node:path";
|
||||||
import { existsSync, readdirSync } from "node:fs";
|
import fs from "node:fs";
|
||||||
import { Cracker, GameAchievementFiles } from "../types";
|
import { Cracker, GameAchievementFiles } from "../types";
|
||||||
import { app } from "electron";
|
import { app } from "electron";
|
||||||
|
|
||||||
const addGame = (
|
const addGame = (
|
||||||
achievementFiles: GameAchievementFiles,
|
achievementFiles: GameAchievementFiles,
|
||||||
gamePath: string,
|
achievementPath: string,
|
||||||
objectId: string,
|
objectId: string,
|
||||||
fileLocation: string[],
|
fileLocation: string[],
|
||||||
type: Cracker
|
type: Cracker
|
||||||
) => {
|
) => {
|
||||||
const filePath = path.join(gamePath, objectId, ...fileLocation);
|
const filePath = path.join(achievementPath, objectId, ...fileLocation);
|
||||||
|
|
||||||
if (existsSync(filePath)) {
|
if (fs.existsSync(filePath)) {
|
||||||
const achivementFile = {
|
const achivementFile = {
|
||||||
type,
|
type,
|
||||||
filePath: filePath,
|
filePath,
|
||||||
};
|
};
|
||||||
|
|
||||||
achievementFiles[objectId]
|
achievementFiles[objectId]
|
||||||
|
@ -33,7 +33,7 @@ export const steamFindGameAchievementFiles = (
|
||||||
|
|
||||||
const gameAchievementFiles: GameAchievementFiles = {};
|
const gameAchievementFiles: GameAchievementFiles = {};
|
||||||
|
|
||||||
const crackers: Cracker[] = [
|
const crackers = [
|
||||||
Cracker.codex,
|
Cracker.codex,
|
||||||
Cracker.goldberg,
|
Cracker.goldberg,
|
||||||
Cracker.rune,
|
Cracker.rune,
|
||||||
|
@ -55,9 +55,9 @@ export const steamFindGameAchievementFiles = (
|
||||||
fileLocation = ["achievements.ini"];
|
fileLocation = ["achievements.ini"];
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!existsSync(achievementPath)) continue;
|
if (!fs.existsSync(achievementPath)) continue;
|
||||||
|
|
||||||
const objectIds = readdirSync(achievementPath);
|
const objectIds = fs.readdirSync(achievementPath);
|
||||||
|
|
||||||
if (objectId) {
|
if (objectId) {
|
||||||
if (objectIds.includes(objectId)) {
|
if (objectIds.includes(objectId)) {
|
||||||
|
|
|
@ -25,7 +25,7 @@ const iniParse = async (filePath: string) => {
|
||||||
});
|
});
|
||||||
|
|
||||||
let objectName = "";
|
let objectName = "";
|
||||||
const object: any = {};
|
const object: Record<string, Record<string, string | number>> = {};
|
||||||
|
|
||||||
for await (const line of lines) {
|
for await (const line of lines) {
|
||||||
if (line.startsWith("###") || !line.length) continue;
|
if (line.startsWith("###") || !line.length) continue;
|
||||||
|
|
|
@ -16,6 +16,7 @@ import { publishNewRepacksNotifications } from "./services/notifications";
|
||||||
import { MoreThan } from "typeorm";
|
import { MoreThan } from "typeorm";
|
||||||
import { HydraApi } from "./services/hydra-api";
|
import { HydraApi } from "./services/hydra-api";
|
||||||
import { uploadGamesBatch } from "./services/library-sync";
|
import { uploadGamesBatch } from "./services/library-sync";
|
||||||
|
import { saveAllLocalSteamAchivements } from "./events/achievements/services/save-all-local-steam-achivements";
|
||||||
|
|
||||||
const loadState = async (userPreferences: UserPreferences | null) => {
|
const loadState = async (userPreferences: UserPreferences | null) => {
|
||||||
RepacksManager.updateRepacks();
|
RepacksManager.updateRepacks();
|
||||||
|
@ -58,6 +59,8 @@ const loadState = async (userPreferences: UserPreferences | null) => {
|
||||||
|
|
||||||
if (newRepacksCount > 0) publishNewRepacksNotifications(newRepacksCount);
|
if (newRepacksCount > 0) publishNewRepacksNotifications(newRepacksCount);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
saveAllLocalSteamAchivements();
|
||||||
};
|
};
|
||||||
|
|
||||||
userPreferencesRepository
|
userPreferencesRepository
|
||||||
|
|
|
@ -3,16 +3,17 @@ import type { Knex } from "knex";
|
||||||
|
|
||||||
export const CreateGameAchievement: HydraMigration = {
|
export const CreateGameAchievement: HydraMigration = {
|
||||||
name: "CreateGameAchievement",
|
name: "CreateGameAchievement",
|
||||||
up: async (knex: Knex) => {
|
up: (knex: Knex) => {
|
||||||
await knex.schema.createTable("game_achievement", (table) => {
|
return knex.schema.createTable("game_achievement", (table) => {
|
||||||
table.increments("id").primary();
|
table.increments("id").primary();
|
||||||
table.integer("gameId").notNullable();
|
table.integer("gameId").notNullable().unique();
|
||||||
table.text("achievements");
|
table.text("achievements");
|
||||||
|
table.text("unlockedAchievements");
|
||||||
table.foreign("gameId").references("game.id").onDelete("CASCADE");
|
table.foreign("gameId").references("game.id").onDelete("CASCADE");
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
down: async (knex: Knex) => {
|
down: (knex: Knex) => {
|
||||||
await knex.schema.dropTable("game_achievement");
|
return knex.schema.dropTable("game_achievement");
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
Loading…
Reference in a new issue