mirror of
https://github.com/hydralauncher/hydra.git
synced 2025-03-09 15:40:26 +00:00
Merge pull request #596 from hydralauncher/feature/integrate-hydra-api
feat: create HydraApi
This commit is contained in:
commit
8fad9b05e6
7 changed files with 122 additions and 4 deletions
|
@ -1,4 +1,3 @@
|
|||
MAIN_VITE_STEAMGRIDDB_API_KEY=YOUR_API_KEY
|
||||
MAIN_VITE_ONLINEFIX_USERNAME=YOUR_USERNAME
|
||||
MAIN_VITE_ONLINEFIX_PASSWORD=YOUR_PASSWORD
|
||||
MAIN_VITE_API_URL=API_URL
|
||||
|
||||
|
|
|
@ -11,6 +11,7 @@ import type { BetterSqlite3ConnectionOptions } from "typeorm/driver/better-sqlit
|
|||
|
||||
import { databasePath } from "./constants";
|
||||
import migrations from "./migrations";
|
||||
import { UserAuth } from "./entity/user-auth";
|
||||
|
||||
export const createDataSource = (
|
||||
options: Partial<BetterSqlite3ConnectionOptions>
|
||||
|
@ -24,6 +25,7 @@ export const createDataSource = (
|
|||
GameShopCache,
|
||||
DownloadSource,
|
||||
DownloadQueue,
|
||||
UserAuth,
|
||||
],
|
||||
synchronize: true,
|
||||
database: databasePath,
|
||||
|
|
28
src/main/entity/user-auth.ts
Normal file
28
src/main/entity/user-auth.ts
Normal file
|
@ -0,0 +1,28 @@
|
|||
import {
|
||||
Entity,
|
||||
PrimaryGeneratedColumn,
|
||||
Column,
|
||||
CreateDateColumn,
|
||||
UpdateDateColumn,
|
||||
} from "typeorm";
|
||||
|
||||
@Entity("user_auth")
|
||||
export class UserAuth {
|
||||
@PrimaryGeneratedColumn()
|
||||
id: number;
|
||||
|
||||
@Column("text", { default: "" })
|
||||
accessToken: string;
|
||||
|
||||
@Column("text", { default: "" })
|
||||
refreshToken: string;
|
||||
|
||||
@Column("int", { default: 0 })
|
||||
tokenExpirationTimestamp: number;
|
||||
|
||||
@CreateDateColumn()
|
||||
createdAt: Date;
|
||||
|
||||
@UpdateDateColumn()
|
||||
updatedAt: Date;
|
||||
}
|
|
@ -9,6 +9,7 @@ import { RealDebridClient } from "./services/real-debrid";
|
|||
import { fetchDownloadSourcesAndUpdate } from "./helpers";
|
||||
import { publishNewRepacksNotifications } from "./services/notifications";
|
||||
import { MoreThan } from "typeorm";
|
||||
import { HydraApi } from "./services/hydra-api";
|
||||
|
||||
startMainLoop();
|
||||
|
||||
|
@ -20,6 +21,8 @@ const loadState = async (userPreferences: UserPreferences | null) => {
|
|||
if (userPreferences?.realDebridApiToken)
|
||||
RealDebridClient.authorize(userPreferences?.realDebridApiToken);
|
||||
|
||||
HydraApi.setupApi();
|
||||
|
||||
const [nextQueueItem] = await downloadQueueRepository.find({
|
||||
order: {
|
||||
id: "DESC",
|
||||
|
|
|
@ -7,6 +7,7 @@ import {
|
|||
Repack,
|
||||
UserPreferences,
|
||||
} from "@main/entity";
|
||||
import { UserAuth } from "./entity/user-auth";
|
||||
|
||||
export const gameRepository = dataSource.getRepository(Game);
|
||||
|
||||
|
@ -21,3 +22,5 @@ export const downloadSourceRepository =
|
|||
dataSource.getRepository(DownloadSource);
|
||||
|
||||
export const downloadQueueRepository = dataSource.getRepository(DownloadQueue);
|
||||
|
||||
export const userAuthRepository = dataSource.getRepository(UserAuth);
|
||||
|
|
84
src/main/services/hydra-api.ts
Normal file
84
src/main/services/hydra-api.ts
Normal file
|
@ -0,0 +1,84 @@
|
|||
import { userAuthRepository } from "@main/repository";
|
||||
import axios, { AxiosInstance } from "axios";
|
||||
|
||||
export class HydraApi {
|
||||
private static instance: AxiosInstance;
|
||||
|
||||
private static readonly EXPIRATION_OFFSET_IN_MS = 1000 * 60 * 5;
|
||||
|
||||
private static userAuth = {
|
||||
authToken: "",
|
||||
refreshToken: "",
|
||||
expirationTimestamp: 0,
|
||||
};
|
||||
|
||||
static async setupApi() {
|
||||
this.instance = axios.create({
|
||||
baseURL: import.meta.env.MAIN_VITE_API_URL,
|
||||
});
|
||||
|
||||
const userAuth = await userAuthRepository.findOne({
|
||||
where: { id: 1 },
|
||||
});
|
||||
|
||||
this.userAuth = {
|
||||
authToken: userAuth?.accessToken ?? "",
|
||||
refreshToken: userAuth?.refreshToken ?? "",
|
||||
expirationTimestamp: userAuth?.tokenExpirationTimestamp ?? 0,
|
||||
};
|
||||
}
|
||||
|
||||
private static async revalidateAccessTokenIfExpired() {
|
||||
const now = new Date();
|
||||
if (this.userAuth.expirationTimestamp < now.getTime()) {
|
||||
const response = await this.instance.post(`/auth/refresh`, {
|
||||
refreshToken: this.userAuth.refreshToken,
|
||||
});
|
||||
|
||||
const { accessToken, expiresIn } = response.data;
|
||||
|
||||
const tokenExpirationTimestamp =
|
||||
now.getTime() + expiresIn - this.EXPIRATION_OFFSET_IN_MS;
|
||||
|
||||
this.userAuth.authToken = accessToken;
|
||||
this.userAuth.expirationTimestamp = tokenExpirationTimestamp;
|
||||
|
||||
userAuthRepository.upsert(
|
||||
{
|
||||
id: 1,
|
||||
accessToken,
|
||||
tokenExpirationTimestamp,
|
||||
},
|
||||
["id"]
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
private static getAxiosConfig() {
|
||||
return {
|
||||
headers: {
|
||||
Authorization: `Bearer ${this.userAuth.authToken}`,
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
static async get(url: string) {
|
||||
await this.revalidateAccessTokenIfExpired();
|
||||
return this.instance.get(url, this.getAxiosConfig());
|
||||
}
|
||||
|
||||
static async post(url: string, data?: any) {
|
||||
await this.revalidateAccessTokenIfExpired();
|
||||
return this.instance.post(url, data, this.getAxiosConfig());
|
||||
}
|
||||
|
||||
static async put(url, data?: any) {
|
||||
await this.revalidateAccessTokenIfExpired();
|
||||
return this.instance.put(url, data, this.getAxiosConfig());
|
||||
}
|
||||
|
||||
static async patch(url, data?: any) {
|
||||
await this.revalidateAccessTokenIfExpired();
|
||||
return this.instance.patch(url, data, this.getAxiosConfig());
|
||||
}
|
||||
}
|
3
src/main/vite-env.d.ts
vendored
3
src/main/vite-env.d.ts
vendored
|
@ -2,8 +2,7 @@
|
|||
|
||||
interface ImportMetaEnv {
|
||||
readonly MAIN_VITE_STEAMGRIDDB_API_KEY: string;
|
||||
readonly MAIN_VITE_ONLINEFIX_USERNAME: string;
|
||||
readonly MAIN_VITE_ONLINEFIX_PASSWORD: string;
|
||||
readonly MAIN_VITE_API_URL: string;
|
||||
}
|
||||
|
||||
interface ImportMeta {
|
||||
|
|
Loading…
Add table
Reference in a new issue