mirror of
https://github.com/khairul169/github-leaderboard.git
synced 2025-04-28 15:39:31 +07:00
71 lines
1.9 KiB
TypeScript
71 lines
1.9 KiB
TypeScript
import db from "@server/db";
|
|
import github from "@server/lib/github";
|
|
import queue from "@server/lib/queue";
|
|
import { repositories, users } from "@server/models";
|
|
import { and, eq } from "drizzle-orm";
|
|
import { FetchRepoDataJobType } from "./fetch-repo-data";
|
|
|
|
export type FetchUserRepos = {
|
|
userId: number;
|
|
};
|
|
|
|
export const fetchUserRepos = async (data: FetchUserRepos) => {
|
|
const [user] = await db.select().from(users).where(eq(users.id, data.userId));
|
|
if (!user) {
|
|
throw new Error("User not found!");
|
|
}
|
|
|
|
const res = await github.getRepositories(user.username, {
|
|
sort: "stargazers",
|
|
fetchAll: true,
|
|
});
|
|
|
|
const jobList = [] as FetchRepoDataJobType[];
|
|
|
|
await db.transaction(async (tx) => {
|
|
for (const repo of res.repositories) {
|
|
const data = {
|
|
...repo,
|
|
userId: user.id,
|
|
lastUpdate: repo.lastUpdate.toISOString(),
|
|
isPending: true,
|
|
};
|
|
|
|
const [existing] = await tx
|
|
.select({ id: repositories.id })
|
|
.from(repositories)
|
|
.where(
|
|
and(
|
|
eq(repositories.userId, data.userId),
|
|
eq(repositories.name, data.name)
|
|
)
|
|
);
|
|
|
|
if (existing) {
|
|
await tx
|
|
.update(repositories)
|
|
.set(data)
|
|
.where(eq(repositories.id, existing.id));
|
|
jobList.push({ id: existing.id, uri: data.uri });
|
|
} else {
|
|
const [result] = await tx.insert(repositories).values(data).returning();
|
|
jobList.push({ id: result.id, uri: data.uri });
|
|
}
|
|
}
|
|
});
|
|
|
|
// Queue fetch repo details
|
|
queue.addBulk(jobList.map((data) => ({ name: "fetchRepoData", data })));
|
|
queue.addBulk(
|
|
jobList.map((data) => ({
|
|
name: "fetchRepoContributors",
|
|
data,
|
|
opts: {
|
|
attempts: 5,
|
|
backoff: { type: "exponential", delay: 30000 },
|
|
jobId: `contributors:${data.uri}`,
|
|
},
|
|
}))
|
|
);
|
|
};
|