Files
2025-11-13 05:05:53 +08:00

114 lines
3.4 KiB
TypeScript

import { auth } from '@/lib/auth'
export async function getFileContent(path: string) {
const owner = process.env.GITHUB_OWNER!
const repo = process.env.GITHUB_REPO!
const branch = process.env.GITHUB_BRANCH || 'main'
try {
const session = await auth()
const token = session?.user?.accessToken
const apiUrl = `https://api.github.com/repos/${owner}/${repo}/contents/${path}?ref=${branch}`
const response = await fetch(apiUrl, {
headers: {
Accept: 'application/vnd.github.v3.raw',
Authorization: token ? `token ${token}` : '',
'User-Agent': 'NavSphere',
},
})
if (response.status === 404) {
console.log(`File not found: ${path}, returning default data`)
if (path.includes('navigation.json')) {
return { navigationItems: [] }
}
return {}
}
if (!response.ok) {
throw new Error(`GitHub API error: ${response.statusText}`)
}
const data = await response.json()
return data
} catch (error) {
console.error('Error fetching file:', error)
if (path.includes('navigation.json')) {
return { navigationItems: [] }
}
return {}
}
}
export async function commitFile(
path: string,
content: string,
message: string,
token: string,
retryCount = 3
) {
const owner = process.env.GITHUB_OWNER!
const repo = process.env.GITHUB_REPO!
const branch = process.env.GITHUB_BRANCH || 'main'
const delay = (ms: number) => new Promise(resolve => setTimeout(resolve, ms))
for (let attempt = 1; attempt <= retryCount; attempt++) {
try {
// 1. 获取当前文件信息(如果存在)
const currentFileUrl = `https://api.github.com/repos/${owner}/${repo}/contents/${path}?ref=${branch}`
const currentFileResponse = await fetch(currentFileUrl, {
headers: {
Authorization: `token ${token}`,
Accept: 'application/vnd.github.v3+json',
'User-Agent': 'NavSphere',
},
cache: 'no-store', // 禁用缓存,确保获取最新的文件信息
})
let sha = undefined
if (currentFileResponse.ok) {
const currentFile = await currentFileResponse.json()
sha = currentFile.sha
}
// 2. 创建或更新文件
const updateUrl = `https://api.github.com/repos/${owner}/${repo}/contents/${path}`
const response = await fetch(updateUrl, {
method: 'PUT',
headers: {
Authorization: `token ${token}`,
Accept: 'application/vnd.github.v3+json',
'Content-Type': 'application/json',
'User-Agent': 'NavSphere',
},
body: JSON.stringify({
message,
content: Buffer.from(content).toString('base64'),
sha,
branch,
}),
})
if (!response.ok) {
const error = await response.json()
if (attempt < retryCount && error.message?.includes('sha')) {
console.log(`Attempt ${attempt} failed, retrying after delay...`)
await delay(1000 * attempt) // 指数退避
continue
}
throw new Error(`Failed to commit file: ${error.message}`)
}
return await response.json()
} catch (error) {
if (attempt === retryCount) {
console.error('Error in commitFile:', error)
throw error
}
console.log(`Attempt ${attempt} failed, retrying...`)
await delay(1000 * attempt)
}
}
}