feat: 添加头文件信息,添加图床工具。

This commit is contained in:
539943419 committed 2025-01-22 01:16:25 +08:00
1 parent f8fba79d55
commit fda826a272
12 files changed
+515 -13

No files matched your search

+1 -1
View File
@@ -18,7 +18,7 @@ import "/style/default.scss";
useHead({ useHead({
title: '杪 Blog', title: '杪 Blog',
meta: [ meta: [
{ name: 'description', content: '杪儿的博客' } { name: 'description', content: '杪儿的博客', lang: 'zh-CN' }
], ],
}) })
+1
View File
@@ -0,0 +1 @@
<template><svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 512 512"><rect x="128" y="128" width="336" height="336" rx="57" ry="57" fill="none" stroke="currentColor" stroke-linejoin="round" stroke-width="32"></rect><path d="M383.5 128l.5-24a56.16 56.16 0 0 0-56-56H112a64.19 64.19 0 0 0-64 64v216a56.16 56.16 0 0 0 56 56h24" fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="32"></path></svg></template>
+1
View File
@@ -0,0 +1 @@
<template><svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 512 512"><path d="M320 367.79h76c55 0 100-29.21 100-83.6s-53-81.47-96-83.6c-8.89-85.06-71-136.8-144-136.8c-69 0-113.44 45.79-128 91.2c-60 5.7-112 43.88-112 106.4s54 106.4 120 106.4h56" fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="32"></path><path fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="32" d="M320 255.79l-64-64l-64 64"></path><path fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="32" d="M256 448.21V207.79"></path></svg></template>
+2
View File
@@ -24,6 +24,7 @@
"node-fetch": "^3.3.2", "node-fetch": "^3.3.2",
"nuxt": "^3.15.1", "nuxt": "^3.15.1",
"pinia": "^2.3.0", "pinia": "^2.3.0",
"qrcode": "^1.5.4",
"unplugin-auto-import": "^19.0.0", "unplugin-auto-import": "^19.0.0",
"unplugin-vue-components": "^28.0.0", "unplugin-vue-components": "^28.0.0",
"vue": "^3.4.21", "vue": "^3.4.21",
@@ -44,6 +45,7 @@
"@types/better-sqlite3": "^7.6.12", "@types/better-sqlite3": "^7.6.12",
"@types/jsonwebtoken": "^9.0.7", "@types/jsonwebtoken": "^9.0.7",
"@types/markdown-it": "^14.1.2", "@types/markdown-it": "^14.1.2",
"@types/qrcode": "^1.5.5",
"element-plus": "^2.9.3", "element-plus": "^2.9.3",
"sass": "^1.83.1", "sass": "^1.83.1",
"vite-plugin-mkcert": "^1.17.6" "vite-plugin-mkcert": "^1.17.6"
+15 -1
View File
@@ -91,8 +91,12 @@ const PageContent = reactive<PageContent[]>([
}, },
{ {
name: 'MiaoBlog', name: 'MiaoBlog',
description: '施工中,不过不要抱有太大期待', description: '施工中,不过最好不要抱有太大期待,毕竟还是以实现功能为目标去做的',
links: [ links: [
{
name: "gitea",
url: "https://nj.miaospring.top:3001/539943419/miaoBlog.git"
},
{ {
name: "github", name: "github",
url: "https://github.com/Zioywishing/miaoBlog" url: "https://github.com/Zioywishing/miaoBlog"
@@ -134,6 +138,16 @@ const PageContent = reactive<PageContent[]>([
} }
] ]
}, },
{
name: '喵喵图床',
description: '其实就是一个很简陋的图床,上传,下载,没了',
nuxtLinks: [
{
name: 'link',
to: `/tools/imgBed`
}
]
},
] ]
}, { }, {
subTitle: '学习资料', subTitle: '学习资料',
+196
View File
@@ -0,0 +1,196 @@
<template>
<div class="imgBed-wrapper">
<div class="imgBed-wrapper-upload">
<el-upload class="imgBed-wrapper-upload-el" :auto-upload="false" v-model="fileList"
action="/api/tools/imgBed/upload" ref="uploadRef" :headers="headers" drag :data="data"
@success="handleSuccess">
<template #trigger>
<div class="imgBed-upload">
<upload class="imgBed-upload-icon"></upload>
<el-text style="margin: 0;">拖拽 图片 至此<br />或单击此处选择文件</el-text>
</div>
</template>
</el-upload>
<el-row>
<el-col :span="17">
<el-input v-model="expire" placeholder="有效期(小时)" style="width: 100%;">
<template #prepend>过期时间(小时)</template>
</el-input>
</el-col>
<el-col :span="7" class="flex-end">
<el-button type="primary" @click="handleUpload">
点击上传图片
</el-button>
</el-col>
</el-row>
<el-table :data="tableData" style="width: 100%">
<el-table-column show-overflow-tooltip prop="name" label="文件名" />
<el-table-column prop="expire" label="过期时间" width="180" />
<el-table-column fixed="right" prop="share" label="操作" width="180">
<template #default="scoped">
<el-button link type="primary" size="small" @click="handleDownload(scoped.row)">
下载
</el-button>
<el-button link type="primary" size="small" @click="handleShare(scoped.row)">分享</el-button>
</template>
</el-table-column>
</el-table>
</div>
<el-dialog v-model="showShareDialog" title="分享链接">
<div style="display: flex; flex-direction: column; align-items: center; justify-content: center;">
<img :src="shareDialogData.img" alt="shareQRCodeBase64" />
<div style="max-width: 80%;">
<span>{{ shareDialogData.url }}</span>
<span>
<copy style="width: 15px; margin-left: 4px; transform: translateY(3px); cursor: pointer;" @click="handleCopyUrl(shareDialogData.url)"></copy>
</span>
</div>
</div>
</el-dialog>
</div>
</template>
<script setup lang="ts">
import type { UploadInstance } from 'element-plus';
import upload from '~/components/icons/upload.vue';
import copy from '~/components/icons/copy.vue';
// @ts-ignore
import QRCode from 'qrcode'
const fileList = ref([])
const headers = reactive({
Authorization: ``
})
const uploadRef = ref<UploadInstance>()
const tableData = reactive<{
name: string;
expire: string;
hash: string;
}[]>([])
const showShareDialog = ref(false)
const shareDialogData = ref({
img: '',
url: '',
})
const expire = ref(1)
const data = computed(() => {
return {
expire: expire.value * 3600 * 1000
}
})
const handleUpload = () => {
uploadRef.value!.submit()
}
const handleSuccess = (res: {
code: number;
fileName: string;
expire: number;
hash: string;
fileSize: number;
}) => {
if (res.code === 200) {
const data = {
name: res.fileName,
expire: formatDate(new Date(Number(res.expire)), 'yyyy-MM-dd HH:mm:ss'),
expireDate: Number(res.expire),
hash: res.hash,
}
tableData.push(data)
}
}
const handleDownload = (row: {
name: string;
hash: string;
}) => {
const url = `/api/tools/imgBed/download/${row.hash}`
const a = document.createElement('a')
a.download = row.name
a.href = url
a.click()
}
const handleShare = async (row: {
name: string;
hash: string;
}) => {
const url = `${location.origin}/api/tools/imgBed/download/${row.hash}`
const data = await QRCode.toDataURL(url)
shareDialogData.value = {
img: data,
url: url,
}
showShareDialog.value = true
}
const handleCopyUrl = async (url: string) => {
await navigator.clipboard.writeText(url)
ElMessage.success('复制成功')
}
onMounted(() => {
const record = localStorage.getItem('miaoTool-imgBed-uploadRecord')
if (record) {
let _record = JSON.parse(record)
// console.log({ _record, record })
_record = _record.filter((item: { expireDate: number }) => {
return item.expireDate && item.expireDate > Date.now()
})
tableData.push(..._record)
}
watchEffect(() => {
localStorage.setItem('miaoTool-imgBed-uploadRecord', JSON.stringify(tableData))
})
})
</script>
<style lang="scss" scoped>
.imgBed-wrapper {
// box-sizing: border-box;
position: relative;
margin: 0 20px;
padding: 20px 0 0 0;
width: 100%;
// height: calc(100vh - 60px);
// max-height: calc(100vh - 60px);
max-width: 800px;
display: flex;
flex-direction: column;
align-items: center;
&-upload {
width: 95%;
&-el {
margin-bottom: 30px;
}
}
.imgBed-upload {
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
margin: 5px;
&-icon {
display: block;
width: 45px;
color: #595959;
}
}
}
.flex-end {
display: flex;
justify-content: flex-end;
}
</style>
+158
View File
@@ -50,6 +50,9 @@ importers:
pinia: pinia:
specifier: ^2.3.0 specifier: ^2.3.0
version: 2.3.0(typescript@5.7.3)(vue@3.5.13(typescript@5.7.3)) version: 2.3.0(typescript@5.7.3)(vue@3.5.13(typescript@5.7.3))
qrcode:
specifier: ^1.5.4
version: 1.5.4
unplugin-auto-import: unplugin-auto-import:
specifier: ^19.0.0 specifier: ^19.0.0
version: 19.0.0(@nuxt/kit@3.15.1(magicast@0.3.5)(rollup@4.30.1))(@vueuse/core@9.13.0(vue@3.5.13(typescript@5.7.3)))(rollup@4.30.1) version: 19.0.0(@nuxt/kit@3.15.1(magicast@0.3.5)(rollup@4.30.1))(@vueuse/core@9.13.0(vue@3.5.13(typescript@5.7.3)))(rollup@4.30.1)
@@ -105,6 +108,9 @@ importers:
'@types/markdown-it': '@types/markdown-it':
specifier: ^14.1.2 specifier: ^14.1.2
version: 14.1.2 version: 14.1.2
'@types/qrcode':
specifier: ^1.5.5
version: 1.5.5
element-plus: element-plus:
specifier: ^2.9.3 specifier: ^2.9.3
version: 2.9.3(vue@3.5.13(typescript@5.7.3)) version: 2.9.3(vue@3.5.13(typescript@5.7.3))
@@ -1172,6 +1178,9 @@ packages:
'@types/parse-path@7.0.3': '@types/parse-path@7.0.3':
resolution: {integrity: sha512-LriObC2+KYZD3FzCrgWGv/qufdUy4eXrxcLgQMfYXgPbLIecKIsVBaQgUPmxSSLcjmYbDTQbMgr6qr6l/eb7Bg==} resolution: {integrity: sha512-LriObC2+KYZD3FzCrgWGv/qufdUy4eXrxcLgQMfYXgPbLIecKIsVBaQgUPmxSSLcjmYbDTQbMgr6qr6l/eb7Bg==}
'@types/qrcode@1.5.5':
resolution: {integrity: sha512-CdfBi/e3Qk+3Z/fXYShipBT13OJ2fDO2Q2w5CIP5anLTLIndQG9z6P1cnm+8zCWSpm5dnxMFd/uREtb0EXuQzg==}
'@types/resolve@1.20.2': '@types/resolve@1.20.2':
resolution: {integrity: sha512-60BCwRFOZCQhDncwQdxxeOEEkbc5dIMccYLwbxsS4TUNeVECQ/pBJ0j09mrHOl/JJvpRPGwO9SvE4nR2Nb/a4Q==} resolution: {integrity: sha512-60BCwRFOZCQhDncwQdxxeOEEkbc5dIMccYLwbxsS4TUNeVECQ/pBJ0j09mrHOl/JJvpRPGwO9SvE4nR2Nb/a4Q==}
@@ -1466,6 +1475,10 @@ packages:
resolution: {integrity: sha512-b6Ilus+c3RrdDk+JhLKUAQfzzgLEPy6wcXqS7f/xe1EETvsDP6GORG7SFuOs6cID5YkqchW/LXZbX5bc8j7ZcQ==} resolution: {integrity: sha512-b6Ilus+c3RrdDk+JhLKUAQfzzgLEPy6wcXqS7f/xe1EETvsDP6GORG7SFuOs6cID5YkqchW/LXZbX5bc8j7ZcQ==}
engines: {node: '>=8'} engines: {node: '>=8'}
camelcase@5.3.1:
resolution: {integrity: sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==}
engines: {node: '>=6'}
caniuse-api@3.0.0: caniuse-api@3.0.0:
resolution: {integrity: sha512-bsTwuIg/BZZK/vreVTYYbSWoe2F+71P7K5QGEX+pT250DZbfU1MQ5prOKpPR+LL6uWKK3KMwMCAS74QB3Um1uw==} resolution: {integrity: sha512-bsTwuIg/BZZK/vreVTYYbSWoe2F+71P7K5QGEX+pT250DZbfU1MQ5prOKpPR+LL6uWKK3KMwMCAS74QB3Um1uw==}
@@ -1505,6 +1518,9 @@ packages:
resolution: {integrity: sha512-5mOlNS0mhX0707P2I0aZ2V/cmHUEO/fL7VFLqszkhUsxt7RwnmrInf/eEQKlf5GzvYeHIjT+Ov1HRfNmymlG0w==} resolution: {integrity: sha512-5mOlNS0mhX0707P2I0aZ2V/cmHUEO/fL7VFLqszkhUsxt7RwnmrInf/eEQKlf5GzvYeHIjT+Ov1HRfNmymlG0w==}
engines: {node: '>=18'} engines: {node: '>=18'}
cliui@6.0.0:
resolution: {integrity: sha512-t6wbgtoCXvAzst7QgXxJYqPt0usEfbgQdftEPbLL/cvv6HPE5VgvqCuAIDR0NgU52ds6rFwqrgakNLrHEjCbrQ==}
cliui@8.0.1: cliui@8.0.1:
resolution: {integrity: sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==} resolution: {integrity: sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==}
engines: {node: '>=12'} engines: {node: '>=12'}
@@ -1699,6 +1715,10 @@ packages:
supports-color: supports-color:
optional: true optional: true
decamelize@1.2.0:
resolution: {integrity: sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA==}
engines: {node: '>=0.10.0'}
decompress-response@6.0.0: decompress-response@6.0.0:
resolution: {integrity: sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==} resolution: {integrity: sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==}
engines: {node: '>=10'} engines: {node: '>=10'}
@@ -1768,6 +1788,9 @@ packages:
resolution: {integrity: sha512-PJWHUb1RFevKCwaFA9RlG5tCd+FO5iRh9A8HEtkmBH2Li03iJriB6m6JIN4rGz3K3JLawI7/veA1xzRKP6ISBw==} resolution: {integrity: sha512-PJWHUb1RFevKCwaFA9RlG5tCd+FO5iRh9A8HEtkmBH2Li03iJriB6m6JIN4rGz3K3JLawI7/veA1xzRKP6ISBw==}
engines: {node: '>=0.3.1'} engines: {node: '>=0.3.1'}
dijkstrajs@1.0.3:
resolution: {integrity: sha512-qiSlmBq9+BCdCA/L46dw8Uy93mloxsPSbwnm5yrKn2vMPiy8KyAskTF6zuV/j5BMsmOGZDPs7KjU+mjb670kfA==}
dom-serializer@2.0.0: dom-serializer@2.0.0:
resolution: {integrity: sha512-wIkAryiqt/nV5EQKqQpo3SToSOV9J0DnbJqwK7Wv/Trc92zIAYZ4FlMu+JPFW1DfGFt81ZTCGgDEabffXeLyJg==} resolution: {integrity: sha512-wIkAryiqt/nV5EQKqQpo3SToSOV9J0DnbJqwK7Wv/Trc92zIAYZ4FlMu+JPFW1DfGFt81ZTCGgDEabffXeLyJg==}
@@ -1932,6 +1955,10 @@ packages:
resolution: {integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==} resolution: {integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==}
engines: {node: '>=8'} engines: {node: '>=8'}
find-up@4.1.0:
resolution: {integrity: sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==}
engines: {node: '>=8'}
flatted@3.3.2: flatted@3.3.2:
resolution: {integrity: sha512-AiwGJM8YcNOaobumgtng+6NHuOqC3A7MixFeDafM3X9cIUM+xUXoS5Vfgf+OihAYe20fxqNM9yPBXJzRtZ/4eA==} resolution: {integrity: sha512-AiwGJM8YcNOaobumgtng+6NHuOqC3A7MixFeDafM3X9cIUM+xUXoS5Vfgf+OihAYe20fxqNM9yPBXJzRtZ/4eA==}
@@ -2310,6 +2337,10 @@ packages:
resolution: {integrity: sha512-9rrA30MRRP3gBD3HTGnC6cDFpaE1kVDWxWgqWJUN0RvDNAo+Nz/9GxB+nHOH0ifbVFy0hSA1V6vFDvnx54lTEQ==} resolution: {integrity: sha512-9rrA30MRRP3gBD3HTGnC6cDFpaE1kVDWxWgqWJUN0RvDNAo+Nz/9GxB+nHOH0ifbVFy0hSA1V6vFDvnx54lTEQ==}
engines: {node: '>=14'} engines: {node: '>=14'}
locate-path@5.0.0:
resolution: {integrity: sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==}
engines: {node: '>=8'}
lodash-es@4.17.21: lodash-es@4.17.21:
resolution: {integrity: sha512-mKnC+QJ9pWVzv+C4/U3rRsHapFfHvQFoFB92e52xeyGMcX6/OlIl78je1u8vePzYZSkkogMPJ2yjxxsb89cxyw==} resolution: {integrity: sha512-mKnC+QJ9pWVzv+C4/U3rRsHapFfHvQFoFB92e52xeyGMcX6/OlIl78je1u8vePzYZSkkogMPJ2yjxxsb89cxyw==}
@@ -2647,6 +2678,18 @@ packages:
peerDependencies: peerDependencies:
typescript: ^5.x typescript: ^5.x
p-limit@2.3.0:
resolution: {integrity: sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==}
engines: {node: '>=6'}
p-locate@4.1.0:
resolution: {integrity: sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==}
engines: {node: '>=8'}
p-try@2.2.0:
resolution: {integrity: sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==}
engines: {node: '>=6'}
package-json-from-dist@1.0.1: package-json-from-dist@1.0.1:
resolution: {integrity: sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw==} resolution: {integrity: sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw==}
@@ -2675,6 +2718,10 @@ packages:
resolution: {integrity: sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==} resolution: {integrity: sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==}
engines: {node: '>= 0.8'} engines: {node: '>= 0.8'}
path-exists@4.0.0:
resolution: {integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==}
engines: {node: '>=8'}
path-is-absolute@1.0.1: path-is-absolute@1.0.1:
resolution: {integrity: sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==} resolution: {integrity: sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==}
engines: {node: '>=0.10.0'} engines: {node: '>=0.10.0'}
@@ -2734,6 +2781,10 @@ packages:
resolution: {integrity: sha512-Nc3IT5yHzflTfbjgqWcCPpo7DaKy4FnpB0l/zCAW0Tc7jxAiuqSxHasntB3D7887LSrA93kDJ9IXovxJYxyLCA==} resolution: {integrity: sha512-Nc3IT5yHzflTfbjgqWcCPpo7DaKy4FnpB0l/zCAW0Tc7jxAiuqSxHasntB3D7887LSrA93kDJ9IXovxJYxyLCA==}
engines: {node: '>=4'} engines: {node: '>=4'}
pngjs@5.0.0:
resolution: {integrity: sha512-40QW5YalBNfQo5yRYmiw7Yz6TKKVr3h6970B2YE+3fQpsWcrbj1PzJgxeJ19DRQjhMbKPIuMY8rFaXc8moolVw==}
engines: {node: '>=10.13.0'}
postcss-calc@10.1.0: postcss-calc@10.1.0:
resolution: {integrity: sha512-uQ/LDGsf3mgsSUEXmAt3VsCSHR3aKqtEIkmB+4PhzYwRYOW5MZs/GhCCFpsOtJJkP6EC6uGipbrnaTjqaJZcJw==} resolution: {integrity: sha512-uQ/LDGsf3mgsSUEXmAt3VsCSHR3aKqtEIkmB+4PhzYwRYOW5MZs/GhCCFpsOtJJkP6EC6uGipbrnaTjqaJZcJw==}
engines: {node: ^18.12 || ^20.9 || >=22.0} engines: {node: ^18.12 || ^20.9 || >=22.0}
@@ -2944,6 +2995,11 @@ packages:
resolution: {integrity: sha512-uxFIHU0YlHYhDQtV4R9J6a52SLx28BCjT+4ieh7IGbgwVJWO+km431c4yRlREUAsAmt/uMjQUyQHNEPf0M39CA==} resolution: {integrity: sha512-uxFIHU0YlHYhDQtV4R9J6a52SLx28BCjT+4ieh7IGbgwVJWO+km431c4yRlREUAsAmt/uMjQUyQHNEPf0M39CA==}
engines: {node: '>=6'} engines: {node: '>=6'}
qrcode@1.5.4:
resolution: {integrity: sha512-1ca71Zgiu6ORjHqFBDpnSMTR2ReToX4l1Au1VFLyVeBTFavzQnv5JxMFr3ukHVKpSrSA2MCk0lNJSykjUfz7Zg==}
engines: {node: '>=10.13.0'}
hasBin: true
queue-microtask@1.2.3: queue-microtask@1.2.3:
resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==} resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==}
@@ -3005,6 +3061,9 @@ packages:
resolution: {integrity: sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==} resolution: {integrity: sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==}
engines: {node: '>=0.10.0'} engines: {node: '>=0.10.0'}
require-main-filename@2.0.0:
resolution: {integrity: sha512-NKN5kMDylKuldxYLSUfrbo5Tuzh4hd+2E8NPPX02mZtn1VuREQToYe/ZdlJy+J3uCpfaiGF05e7B8W0iXbQHmg==}
resolve-from@5.0.0: resolve-from@5.0.0:
resolution: {integrity: sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==} resolution: {integrity: sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==}
engines: {node: '>=8'} engines: {node: '>=8'}
@@ -3087,6 +3146,9 @@ packages:
resolution: {integrity: sha512-VqpjJZKadQB/PEbEwvFdO43Ax5dFBZ2UECszz8bQ7pi7wt//PWe1P6MN7eCnjsatYtBT6EuiClbjSWP2WrIoTw==} resolution: {integrity: sha512-VqpjJZKadQB/PEbEwvFdO43Ax5dFBZ2UECszz8bQ7pi7wt//PWe1P6MN7eCnjsatYtBT6EuiClbjSWP2WrIoTw==}
engines: {node: '>= 0.8.0'} engines: {node: '>= 0.8.0'}
set-blocking@2.0.0:
resolution: {integrity: sha512-KiKBS8AnWGEyLzofFfmvKwpdPzqiy16LvQfK3yv/fVH7Bj13/wl3JSR1J+rfgRE9q7xUJK4qvgS8raSOeLUehw==}
setprototypeof@1.2.0: setprototypeof@1.2.0:
resolution: {integrity: sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==} resolution: {integrity: sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==}
@@ -3682,6 +3744,9 @@ packages:
whatwg-url@5.0.0: whatwg-url@5.0.0:
resolution: {integrity: sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==} resolution: {integrity: sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==}
which-module@2.0.1:
resolution: {integrity: sha512-iBdZ57RDvnOR9AGBhML2vFZf7h8vmBjhoaZqODJBFWHVtKkDmKuHai3cx5PgVMrX5YDNp27AofYbAwctSS+vhQ==}
which@2.0.2: which@2.0.2:
resolution: {integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==} resolution: {integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==}
engines: {node: '>= 8'} engines: {node: '>= 8'}
@@ -3692,6 +3757,10 @@ packages:
engines: {node: ^14.17.0 || ^16.13.0 || >=18.0.0} engines: {node: ^14.17.0 || ^16.13.0 || >=18.0.0}
hasBin: true hasBin: true
wrap-ansi@6.2.0:
resolution: {integrity: sha512-r6lPcBGxZXlIcymEu7InxDMhdW0KDxpLgoFLcguasxCaJ/SOIZwINatK9KY/tf+ZrlywOKU0UDj3ATXUBfxJXA==}
engines: {node: '>=8'}
wrap-ansi@7.0.0: wrap-ansi@7.0.0:
resolution: {integrity: sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==} resolution: {integrity: sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==}
engines: {node: '>=10'} engines: {node: '>=10'}
@@ -3715,6 +3784,9 @@ packages:
utf-8-validate: utf-8-validate:
optional: true optional: true
y18n@4.0.3:
resolution: {integrity: sha512-JKhqTOwSrqNA1NY5lSztJ1GrBiUodLMmIZuLiDaMRJ+itFd+ABVE8XBjOvIWL+rSqNDC74LCSFmlb/U4UZ4hJQ==}
y18n@5.0.8: y18n@5.0.8:
resolution: {integrity: sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==} resolution: {integrity: sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==}
engines: {node: '>=10'} engines: {node: '>=10'}
@@ -3737,10 +3809,18 @@ packages:
engines: {node: '>= 14'} engines: {node: '>= 14'}
hasBin: true hasBin: true
yargs-parser@18.1.3:
resolution: {integrity: sha512-o50j0JeToy/4K6OZcaQmW6lyXXKhq7csREXcDwk2omFPJEwUNOVtJKvmDr9EI1fAJZUyZcRF7kxGBWmRXudrCQ==}
engines: {node: '>=6'}
yargs-parser@21.1.1: yargs-parser@21.1.1:
resolution: {integrity: sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==} resolution: {integrity: sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==}
engines: {node: '>=12'} engines: {node: '>=12'}
yargs@15.4.1:
resolution: {integrity: sha512-aePbxDmcYW++PaqBsJ+HYUFwCdv4LVvdnhBy78E57PIor8/OVvhMrADFFEDh8DHDFRv/O9i3lPhsENjO7QX0+A==}
engines: {node: '>=8'}
yargs@17.7.2: yargs@17.7.2:
resolution: {integrity: sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==} resolution: {integrity: sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==}
engines: {node: '>=12'} engines: {node: '>=12'}
@@ -4939,6 +5019,10 @@ snapshots:
'@types/parse-path@7.0.3': {} '@types/parse-path@7.0.3': {}
'@types/qrcode@1.5.5':
dependencies:
'@types/node': 22.10.5
'@types/resolve@1.20.2': {} '@types/resolve@1.20.2': {}
'@types/web-bluetooth@0.0.16': {} '@types/web-bluetooth@0.0.16': {}
@@ -5335,6 +5419,8 @@ snapshots:
cac@6.7.14: {} cac@6.7.14: {}
camelcase@5.3.1: {}
caniuse-api@3.0.0: caniuse-api@3.0.0:
dependencies: dependencies:
browserslist: 4.24.4 browserslist: 4.24.4
@@ -5383,6 +5469,12 @@ snapshots:
is-wsl: 3.1.0 is-wsl: 3.1.0
is64bit: 2.0.0 is64bit: 2.0.0
cliui@6.0.0:
dependencies:
string-width: 4.2.3
strip-ansi: 6.0.1
wrap-ansi: 6.2.0
cliui@8.0.1: cliui@8.0.1:
dependencies: dependencies:
string-width: 4.2.3 string-width: 4.2.3
@@ -5566,6 +5658,8 @@ snapshots:
optionalDependencies: optionalDependencies:
supports-color: 9.4.0 supports-color: 9.4.0
decamelize@1.2.0: {}
decompress-response@6.0.0: decompress-response@6.0.0:
dependencies: dependencies:
mimic-response: 3.1.0 mimic-response: 3.1.0
@@ -5607,6 +5701,8 @@ snapshots:
diff@7.0.0: {} diff@7.0.0: {}
dijkstrajs@1.0.3: {}
dom-serializer@2.0.0: dom-serializer@2.0.0:
dependencies: dependencies:
domelementtype: 2.3.0 domelementtype: 2.3.0
@@ -5827,6 +5923,11 @@ snapshots:
dependencies: dependencies:
to-regex-range: 5.0.1 to-regex-range: 5.0.1
find-up@4.1.0:
dependencies:
locate-path: 5.0.0
path-exists: 4.0.0
flatted@3.3.2: {} flatted@3.3.2: {}
follow-redirects@1.15.9(debug@4.4.0): follow-redirects@1.15.9(debug@4.4.0):
@@ -6213,6 +6314,10 @@ snapshots:
mlly: 1.7.4 mlly: 1.7.4
pkg-types: 1.3.0 pkg-types: 1.3.0
locate-path@5.0.0:
dependencies:
p-locate: 4.1.0
lodash-es@4.17.21: {} lodash-es@4.17.21: {}
lodash-unified@1.0.3(@types/lodash-es@4.17.12)(lodash-es@4.17.21)(lodash@4.17.21): lodash-unified@1.0.3(@types/lodash-es@4.17.12)(lodash-es@4.17.21)(lodash@4.17.21):
@@ -6703,6 +6808,16 @@ snapshots:
transitivePeerDependencies: transitivePeerDependencies:
- encoding - encoding
p-limit@2.3.0:
dependencies:
p-try: 2.2.0
p-locate@4.1.0:
dependencies:
p-limit: 2.3.0
p-try@2.2.0: {}
package-json-from-dist@1.0.1: {} package-json-from-dist@1.0.1: {}
package-manager-detector@0.2.8: {} package-manager-detector@0.2.8: {}
@@ -6731,6 +6846,8 @@ snapshots:
parseurl@1.3.3: {} parseurl@1.3.3: {}
path-exists@4.0.0: {}
path-is-absolute@1.0.1: {} path-is-absolute@1.0.1: {}
path-key@3.1.1: {} path-key@3.1.1: {}
@@ -6776,6 +6893,8 @@ snapshots:
pluralize@8.0.0: {} pluralize@8.0.0: {}
pngjs@5.0.0: {}
postcss-calc@10.1.0(postcss@8.4.49): postcss-calc@10.1.0(postcss@8.4.49):
dependencies: dependencies:
postcss: 8.4.49 postcss: 8.4.49
@@ -6980,6 +7099,12 @@ snapshots:
punycode.js@2.3.1: {} punycode.js@2.3.1: {}
qrcode@1.5.4:
dependencies:
dijkstrajs: 1.0.3
pngjs: 5.0.0
yargs: 15.4.1
queue-microtask@1.2.3: {} queue-microtask@1.2.3: {}
queue-tick@1.0.1: {} queue-tick@1.0.1: {}
@@ -7048,6 +7173,8 @@ snapshots:
require-from-string@2.0.2: {} require-from-string@2.0.2: {}
require-main-filename@2.0.0: {}
resolve-from@5.0.0: {} resolve-from@5.0.0: {}
resolve@1.22.10: resolve@1.22.10:
@@ -7157,6 +7284,8 @@ snapshots:
transitivePeerDependencies: transitivePeerDependencies:
- supports-color - supports-color
set-blocking@2.0.0: {}
setprototypeof@1.2.0: {} setprototypeof@1.2.0: {}
shebang-command@2.0.0: shebang-command@2.0.0:
@@ -7732,6 +7861,8 @@ snapshots:
tr46: 0.0.3 tr46: 0.0.3
webidl-conversions: 3.0.1 webidl-conversions: 3.0.1
which-module@2.0.1: {}
which@2.0.2: which@2.0.2:
dependencies: dependencies:
isexe: 2.0.0 isexe: 2.0.0
@@ -7740,6 +7871,12 @@ snapshots:
dependencies: dependencies:
isexe: 2.0.0 isexe: 2.0.0
wrap-ansi@6.2.0:
dependencies:
ansi-styles: 4.3.0
string-width: 4.2.3
strip-ansi: 6.0.1
wrap-ansi@7.0.0: wrap-ansi@7.0.0:
dependencies: dependencies:
ansi-styles: 4.3.0 ansi-styles: 4.3.0
@@ -7756,6 +7893,8 @@ snapshots:
ws@8.18.0: {} ws@8.18.0: {}
y18n@4.0.3: {}
y18n@5.0.8: {} y18n@5.0.8: {}
yallist@3.1.1: {} yallist@3.1.1: {}
@@ -7768,8 +7907,27 @@ snapshots:
yaml@2.7.0: {} yaml@2.7.0: {}
yargs-parser@18.1.3:
dependencies:
camelcase: 5.3.1
decamelize: 1.2.0
yargs-parser@21.1.1: {} yargs-parser@21.1.1: {}
yargs@15.4.1:
dependencies:
cliui: 6.0.0
decamelize: 1.2.0
find-up: 4.1.0
get-caller-file: 2.0.5
require-directory: 2.1.1
require-main-filename: 2.0.0
set-blocking: 2.0.0
string-width: 4.2.3
which-module: 2.0.1
y18n: 4.0.3
yargs-parser: 18.1.3
yargs@17.7.2: yargs@17.7.2:
dependencies: dependencies:
cliui: 8.0.1 cliui: 8.0.1
-1
View File
@@ -1,5 +1,4 @@
// @ts-ignore // @ts-ignore
import testData from "~/public/testData/test.md"
import DB from 'better-sqlite3'; import DB from 'better-sqlite3';
import { postItem } from "~/types/post"; import { postItem } from "~/types/post";
@@ -0,0 +1,39 @@
// @ts-ignore
import DB from 'better-sqlite3';
import { defineEventHandler, getRouterParam } from 'h3';
import fs from 'fs';
import { sendStream } from 'h3';
export default defineEventHandler(async (event) => {
try {
const hash = getRouterParam(event, 'hash');
if (!hash) {
return { code: 400, msg: 'Invalid hash parameter' };
}
const db = new DB('./userData/db/imgBed.db');
// 从数据库中查询文件信息
const fileInfo = db.prepare(`
SELECT name, expire FROM imgBed WHERE hash =?
`).get(hash) as { name: string, expire: number };
db.close();
if (!fileInfo) {
return { code: 404, msg: 'File not found' };
}
const fileName = fileInfo.name;
const filePath = `./userData/imgBed/${hash}`;
// 检查文件是否存在
if (!fs.existsSync(filePath)) {
return { code: 404, msg: 'File not found on disk' };
}
const fileStream = fs.createReadStream(filePath);
setResponseHeader(event, 'Content-Disposition', `attachment; filename="${fileName}"`);
// 发送文件流
return sendStream(event, fileStream);
} catch (error) {
console.error(error);
return { code: 500, msg: 'Internal Server Error' };
}
});
+39
View File
@@ -0,0 +1,39 @@
// @ts-ignore
import DB from 'better-sqlite3';
import { defineEventHandler, readBody } from 'h3';
import crypto from 'crypto';
import fs from 'fs';
export default defineEventHandler(async (event) => {
try {
const data = await readFormData(event)
const file = data.get('file') as File
const expire = data.get('expire') as string
console.log({
file: file.name,
expire,
})
const fileBuffer = Buffer.from(await file.arrayBuffer());
// 计算文件的 MD5 哈希值
const hash = crypto.createHash('md5').update(fileBuffer).digest('hex');
const fileName = file.name;
const filePath = `./userData/imgBed/${hash}`;
// 将文件写入磁盘
await fs.promises.writeFile(filePath, fileBuffer);
// 获取文件大小
const fileSize = fileBuffer.length;
const db = new DB('./userData/db/imgBed.db');
// 插入数据到数据库
db.prepare(`
INSERT INTO imgBed (name, hash, size, expire)
VALUES (?,?,?,?)
`).run([fileName, hash, fileSize, expire]);
db.close();
return { code: 200, hash, fileName, fileSize, expire: Number(expire) + Date.now() };
} catch (error) {
console.error(error);
return { code: 500, msg: 'Internal Server Error' };
}
});
-3
View File
@@ -7,12 +7,10 @@ const pathNeedAuth = serverConfig.auth.api
export default defineEventHandler(async (event) => { export default defineEventHandler(async (event) => {
const path = getRequestURL(event).pathname const path = getRequestURL(event).pathname
// console.log(path)
if (pathNeedAuth.has(path)) { if (pathNeedAuth.has(path)) {
const key = getKey() const key = getKey()
// @ts-ignore // @ts-ignore
const authHeader = event.headers.get('authorization'); const authHeader = event.headers.get('authorization');
// console.log(authHeader)
if (!authHeader || !authHeader.startsWith('Bearer ')) { if (!authHeader || !authHeader.startsWith('Bearer ')) {
throw createError({ statusCode: 401, statusMessage: 'Unauthorized' }) throw createError({ statusCode: 401, statusMessage: 'Unauthorized' })
} }
@@ -20,7 +18,6 @@ export default defineEventHandler(async (event) => {
try { try {
const decoded = jwt.verify(token, key) as { userId: number, password: string, username: string, exp: number } const decoded = jwt.verify(token, key) as { userId: number, password: string, username: string, exp: number }
if (decoded.exp > Date.now()) { if (decoded.exp > Date.now()) {
// console.log('token expired')
throw createError({ statusCode: 401, statusMessage: 'Token invalid or expired', data: { err: 'token expired', token } }) throw createError({ statusCode: 401, statusMessage: 'Token invalid or expired', data: { err: 'token expired', token } })
} }
// console.log(decoded) // console.log(decoded)
+63 -7
View File
@@ -1,5 +1,6 @@
import mkfileIfNotExist from "./mkfileIfNotExist" import mkfileIfNotExist from "./mkfileIfNotExist"
import db from 'better-sqlite3' import DB from 'better-sqlite3'
import fs from 'fs'
let checked = false let checked = false
@@ -14,6 +15,7 @@ function checkUserData() {
const dirList = [ const dirList = [
'./userData/', './userData/',
'./userData/db/', './userData/db/',
'./userData/imgBed/',
] ]
dirList.forEach(mkdirIfNotExist) dirList.forEach(mkdirIfNotExist)
@@ -24,9 +26,14 @@ function checkUserData() {
} }
function createDB() { function createDB() {
const userDB = new db('./userData/db/user.db'); createUserDB();
const postsDB = new db('./userData/db/posts.db'); createPostsDB();
createImgBedDB();
}
const createUserDB = () => {
const userDB = new DB('./userData/db/user.db');
userDB.exec(` userDB.exec(`
CREATE TABLE IF NOT EXISTS user ( CREATE TABLE IF NOT EXISTS user (
id INTEGER PRIMARY KEY AUTOINCREMENT, id INTEGER PRIMARY KEY AUTOINCREMENT,
@@ -36,7 +43,11 @@ function createDB() {
lastLoginTime INTEGER NOT NULL lastLoginTime INTEGER NOT NULL
); );
`); `);
userDB.close();
}
const createPostsDB = () => {
const postsDB = new DB('./userData/db/posts.db');
postsDB.exec(` postsDB.exec(`
CREATE TABLE IF NOT EXISTS posts ( CREATE TABLE IF NOT EXISTS posts (
id INTEGER PRIMARY KEY AUTOINCREMENT, id INTEGER PRIMARY KEY AUTOINCREMENT,
@@ -49,14 +60,12 @@ function createDB() {
FOREIGN KEY(tag_id) REFERENCES tags(id) FOREIGN KEY(tag_id) REFERENCES tags(id)
); );
`); `);
postsDB.exec(` postsDB.exec(`
CREATE TABLE IF NOT EXISTS postContent ( CREATE TABLE IF NOT EXISTS postContent (
id INTEGER PRIMARY KEY AUTOINCREMENT, id INTEGER PRIMARY KEY AUTOINCREMENT,
content TEXT NOT NULL content TEXT NOT NULL
); );
`); `);
postsDB.exec(` postsDB.exec(`
CREATE TABLE IF NOT EXISTS tags ( CREATE TABLE IF NOT EXISTS tags (
id INTEGER PRIMARY KEY AUTOINCREMENT, id INTEGER PRIMARY KEY AUTOINCREMENT,
@@ -77,9 +86,56 @@ function createDB() {
tag15 TEXT tag15 TEXT
); );
`); `);
postsDB.close(); postsDB.close();
userDB.close();
} }
const createImgBedDB = () => {
const imgBedDB = new DB('./userData/db/imgBed.db');
imgBedDB.exec(`
CREATE TABLE IF NOT EXISTS imgBed (
id INTEGER PRIMARY KEY AUTOINCREMENT,
name TEXT NOT NULL,
hash TEXT NOT NULL,
size INTEGER NOT NULL,
expire INTEGER NOT NULL
);
`);
imgBedDB.close();
setInterval(cleanExpiredFiles_imgBed, 1000 * 30 * 60 );
// cleanExpiredFiles_imgBed()
}
const cleanExpiredFiles_imgBed = async () => {
try {
const db = new DB('./userData/db/imgBed.db');
const currentTime = Date.now();
// 从数据库中查询过期文件的哈希
const expiredFiles = db.prepare(`
SELECT hash FROM imgBed WHERE expire <?
`).all(currentTime) as {
hash: string;
}[];
db.close();
for (const file of expiredFiles) {
const hash = file.hash;
const filePath = useRuntimeConfig().public.userDataPath + `/imgBed/${hash}`;
// 检查文件是否存在
if (fs.existsSync(filePath)) {
// 删除文件
fs.unlinkSync(filePath);
}
}
// 从数据库中删除过期文件的记录
const db2 = new DB('./userData/db/imgBed.db');
db2.prepare(`
DELETE FROM imgBed WHERE expire <?
`).run(currentTime);
db2.close();
} catch (error) {
console.error('Error cleaning expired files:', error);
}
};
export default checkUserData export default checkUserData