update:消息提示

This commit is contained in:
lan
2023-08-15 00:16:26 +08:00
parent 3a82542118
commit 405ca31727
52 changed files with 255 additions and 61 deletions
+5
View File
@@ -0,0 +1,5 @@
from pydantic import BaseModel
class IDData(BaseModel):
id: int
+24
View File
@@ -4,7 +4,31 @@
# @Software: PyCharm
from fastapi import APIRouter
from apps.admin.pydantics import IDData
from apps.base.models import FileCodes
from core.response import APIResponse
from core.storage import file_storage
admin_api = APIRouter(
prefix='/admin',
tags=['管理'],
)
@admin_api.delete('/file/delete')
async def file_delete(data: IDData):
file_code = await FileCodes.get(id=data.id)
await file_storage.delete_file(file_code)
await file_code.delete()
return APIResponse()
@admin_api.get('/file/list')
async def file_list(page: int = 1, size: int = 10):
data = await FileCodes.all().limit(size).offset((page - 1) * size)
return APIResponse(detail={
'page': page,
'size': size,
'data': data,
'total': await FileCodes.all().count(),
})
+4 -1
View File
@@ -8,24 +8,27 @@ export {}
declare module 'vue' {
export interface GlobalComponents {
CardTools: typeof import('./src/components/CardTools.vue')['default']
ElAside: typeof import('element-plus/es')['ElAside']
ElButton: typeof import('element-plus/es')['ElButton']
ElCard: typeof import('element-plus/es')['ElCard']
ElCol: typeof import('element-plus/es')['ElCol']
ElContainer: typeof import('element-plus/es')['ElContainer']
ElDialog: typeof import('element-plus/es')['ElDialog']
ElDrawer: typeof import('element-plus/es')['ElDrawer']
ElHeader: typeof import('element-plus/es')['ElHeader']
ElIcon: typeof import('element-plus/es')['ElIcon']
ElInput: typeof import('element-plus/es')['ElInput']
ElMain: typeof import('element-plus/es')['ElMain']
ElMenu: typeof import('element-plus/es')['ElMenu']
ElMenuItem: typeof import('element-plus/es')['ElMenuItem']
ElOption: typeof import('element-plus/es')['ElOption']
ElPagination: typeof import('element-plus/es')['ElPagination']
ElProgress: typeof import('element-plus/es')['ElProgress']
ElRadio: typeof import('element-plus/es')['ElRadio']
ElRadioGroup: typeof import('element-plus/es')['ElRadioGroup']
ElRow: typeof import('element-plus/es')['ElRow']
ElSelect: typeof import('element-plus/es')['ElSelect']
ElTable: typeof import('element-plus/es')['ElTable']
ElTableColumn: typeof import('element-plus/es')['ElTableColumn']
ElTag: typeof import('element-plus/es')['ElTag']
ElUpload: typeof import('element-plus/es')['ElUpload']
FileBox: typeof import('./src/components/FileBox.vue')['default']
+1
View File
@@ -0,0 +1 @@
import"./base-f7494360.js";import{E as c}from"./el-button-93ad78d4.js";import{a as r,E as s}from"./el-col-0122cd51.js";import{an as _,m,p as u,y as f,e,w as o,x as t}from"./index-86483aed.js";const p={};function d(i,x){const n=s,a=r,l=c;return m(),u("main",null,[f("div",null,[e(a,null,{default:o(()=>[e(n,null,{default:o(()=>[t("1")]),_:1})]),_:1}),e(l,null,{default:o(()=>[t("1")]),_:1})])])}const N=_(p,[["render",d]]);export{N as default};
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
+1
View File
@@ -0,0 +1 @@
:root{--el-loading-spinner-size:42px;--el-loading-fullscreen-spinner-size:50px}.el-loading-parent--relative{position:relative!important}.el-loading-parent--hidden{overflow:hidden!important}.el-loading-mask{position:absolute;z-index:2000;background-color:var(--el-mask-color);margin:0;top:0;right:0;bottom:0;left:0;transition:opacity var(--el-transition-duration)}.el-loading-mask.is-fullscreen{position:fixed}.el-loading-mask.is-fullscreen .el-loading-spinner{margin-top:calc((0px - var(--el-loading-fullscreen-spinner-size))/ 2)}.el-loading-mask.is-fullscreen .el-loading-spinner .circular{height:var(--el-loading-fullscreen-spinner-size);width:var(--el-loading-fullscreen-spinner-size)}.el-loading-spinner{top:50%;margin-top:calc((0px - var(--el-loading-spinner-size))/ 2);width:100%;text-align:center;position:absolute}.el-loading-spinner .el-loading-text{color:var(--el-color-primary);margin:3px 0;font-size:14px}.el-loading-spinner .circular{display:inline;height:var(--el-loading-spinner-size);width:var(--el-loading-spinner-size);-webkit-animation:loading-rotate 2s linear infinite;animation:loading-rotate 2s linear infinite}.el-loading-spinner .path{-webkit-animation:loading-dash 1.5s ease-in-out infinite;animation:loading-dash 1.5s ease-in-out infinite;stroke-dasharray:90,150;stroke-dashoffset:0;stroke-width:2;stroke:var(--el-color-primary);stroke-linecap:round}.el-loading-spinner i{color:var(--el-color-primary)}.el-loading-fade-enter-from,.el-loading-fade-leave-to{opacity:0}@-webkit-keyframes loading-rotate{to{transform:rotate(360deg)}}@keyframes loading-rotate{to{transform:rotate(360deg)}}@-webkit-keyframes loading-dash{0%{stroke-dasharray:1,200;stroke-dashoffset:0}50%{stroke-dasharray:90,150;stroke-dashoffset:-40px}to{stroke-dasharray:90,150;stroke-dashoffset:-120px}}@keyframes loading-dash{0%{stroke-dasharray:1,200;stroke-dashoffset:0}50%{stroke-dasharray:90,150;stroke-dashoffset:-40px}to{stroke-dasharray:90,150;stroke-dashoffset:-120px}}.key-button{width:6rem;height:6rem;margin:.2rem;font-size:2rem;font-weight:700;text-align:center}.code-input{height:100px;font-size:30px;font-weight:700;margin:1rem 0}.code-input .el-input__wrapper{border-radius:20px!important}
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
+1
View File
@@ -0,0 +1 @@
import"./base-f7494360.js";import{E as c}from"./el-button-93ad78d4.js";import{a as r,E as s}from"./el-col-0122cd51.js";import{an as _,m,p as u,y as f,e,w as t,x as o}from"./index-86483aed.js";const i={};function p(d,x){const n=s,a=r,l=c;return m(),u("main",null,[f("div",null,[e(a,null,{default:t(()=>[e(n,null,{default:t(()=>[o("1")]),_:1})]),_:1}),e(l,null,{default:t(()=>[o("1")]),_:1})])])}const N=_(i,[["render",p]]);export{N as default};
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
+1
View File
@@ -0,0 +1 @@
import{b as g,e as _,_ as w,w as $,j as r,m as u,c as b}from"./base-f7494360.js";import{d as p,B as o,I as O,m as h,J as v,w as j,E as N,D as C,s as c,H as x,$ as E,A as S,f as k}from"./index-86483aed.js";const R=Symbol("rowContextKey"),K=["start","center","end","space-around","space-between","space-evenly"],B=["top","middle","bottom"],P=g({tag:{type:String,default:"div"},gutter:{type:Number,default:0},justify:{type:String,values:K,default:"start"},align:{type:String,values:B}}),A=p({name:"ElRow"}),D=p({...A,props:P,setup(f){const t=f,l=_("row"),a=o(()=>t.gutter);O(R,{gutter:a});const i=o(()=>{const e={};return t.gutter&&(e.marginRight=e.marginLeft=`-${t.gutter/2}px`),e}),m=o(()=>[l.b(),l.is(`justify-${t.justify}`,t.justify!=="start"),l.is(`align-${t.align}`,!!t.align)]);return(e,d)=>(h(),v(E(e.tag),{class:C(c(m)),style:x(c(i))},{default:j(()=>[N(e.$slots,"default")]),_:3},8,["class","style"]))}});var I=w(D,[["__file","/home/runner/work/element-plus/element-plus/packages/components/row/src/row.vue"]]);const M=$(I),J=g({tag:{type:String,default:"div"},span:{type:Number,default:24},offset:{type:Number,default:0},pull:{type:Number,default:0},push:{type:Number,default:0},xs:{type:r([Number,Object]),default:()=>u({})},sm:{type:r([Number,Object]),default:()=>u({})},md:{type:r([Number,Object]),default:()=>u({})},lg:{type:r([Number,Object]),default:()=>u({})},xl:{type:r([Number,Object]),default:()=>u({})}}),L=p({name:"ElCol"}),H=p({...L,props:J,setup(f){const t=f,{gutter:l}=S(R,{gutter:o(()=>0)}),a=_("col"),i=o(()=>{const e={};return l.value&&(e.paddingLeft=e.paddingRight=`${l.value/2}px`),e}),m=o(()=>{const e=[];return["span","offset","pull","push"].forEach(s=>{const n=t[s];b(n)&&(s==="span"?e.push(a.b(`${t[s]}`)):n>0&&e.push(a.b(`${s}-${t[s]}`)))}),["xs","sm","md","lg","xl"].forEach(s=>{b(t[s])?e.push(a.b(`${s}-${t[s]}`)):k(t[s])&&Object.entries(t[s]).forEach(([n,y])=>{e.push(n!=="span"?a.b(`${s}-${n}-${y}`):a.b(`${s}-${y}`))})}),l.value&&e.push(a.is("guttered")),[a.b(),e]});return(e,d)=>(h(),v(E(e.tag),{class:C(c(m)),style:x(c(i))},{default:j(()=>[N(e.$slots,"default")]),_:3},8,["class","style"]))}});var T=w(H,[["__file","/home/runner/work/element-plus/element-plus/packages/components/col/src/col.vue"]]);const Q=$(T);export{Q as E,M as a};
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
+1
View File
@@ -0,0 +1 @@
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
+1
View File
@@ -0,0 +1 @@
import{O as A,a6 as N}from"./index-86483aed.js";var o=(E=>(E[E.TEXT=1]="TEXT",E[E.CLASS=2]="CLASS",E[E.STYLE=4]="STYLE",E[E.PROPS=8]="PROPS",E[E.FULL_PROPS=16]="FULL_PROPS",E[E.HYDRATE_EVENTS=32]="HYDRATE_EVENTS",E[E.STABLE_FRAGMENT=64]="STABLE_FRAGMENT",E[E.KEYED_FRAGMENT=128]="KEYED_FRAGMENT",E[E.UNKEYED_FRAGMENT=256]="UNKEYED_FRAGMENT",E[E.NEED_PATCH=512]="NEED_PATCH",E[E.DYNAMIC_SLOTS=1024]="DYNAMIC_SLOTS",E[E.HOISTED=-1]="HOISTED",E[E.BAIL=-2]="BAIL",E))(o||{});const e=E=>{const _=A(E)?E:[E],S=[];return _.forEach(T=>{var r;A(T)?S.push(...e(T)):N(T)&&A(T.children)?S.push(...e(T.children)):(S.push(T),N(T)&&((r=T.component)!=null&&r.subTree)&&S.push(...e(T.component.subTree)))}),S};export{o as P,e as f};
+1 -1
View File
@@ -5,7 +5,7 @@
<link rel="icon" href="/logo_small.png">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>FileCodeBox</title>
<script type="module" crossorigin src="/assets/index-3a74cfec.js"></script>
<script type="module" crossorigin src="/assets/index-86483aed.js"></script>
<link rel="stylesheet" href="/assets/index-7bc26ac6.css">
</head>
<body>
-2
View File
@@ -1,8 +1,6 @@
@import './base.css';
#app {
max-width: 1280px;
margin: 0 auto;
display: flex;
flex-direction: column;
justify-content: center;
+1 -1
View File
@@ -69,7 +69,7 @@ const showTextDetailVisible = ref(false);
<div style="width: 200px;">
<div style="display: flex;justify-content: space-between">
<qrcode-vue v-if="value.name!=='文本分享'" :value="value.text" :size="100"></qrcode-vue>
<div style="width: 100px;height: 100px;flex-wrap: wrap;overflow-y:scroll ">{{value.text}}</div>
<div v-else style="width: 100px;height: 100px;flex-wrap: wrap;overflow-y:scroll ">{{value.text}}</div>
<div style="display: flex;flex-direction: column;justify-content: space-around">
<el-tag size="large" style="cursor: pointer" @click="copyText(value.code)">{{ value.code }}</el-tag>
<el-tag v-if="value.name!=='文本分享'" size="large" type="success" style="cursor: pointer" @click="openUrl(value.text);">
-1
View File
@@ -10,5 +10,4 @@ const app = createApp(App)
app.use(createPinia())
app.use(router)
app.mount('#app')
+20 -3
View File
@@ -6,17 +6,34 @@ const router = createRouter({
{
path: '/',
name: 'home',
component: () => import('@/views/HomeView.vue'),
component: () => import('@/views/Share/HomeView.vue'),
},
{
path: '/send',
name: 'send',
component: () => import('@/views/SendView.vue'),
component: () => import('@/views/Share/SendView.vue'),
},
{
path: '/admin',
name: 'admin',
component: () => import('@/views/AdminView.vue'),
component: () => import('@/views/Admin/AdminView.vue'),
children:[
{
path: '',
name: 'file',
component: () => import('@/views/Admin/FileView.vue'),
},
{
path: 'setting',
name: 'setting',
component: () => import('@/views/Admin/SettingView.vue'),
},
{
path: 'about',
name: 'about',
component: () => import('@/views/Admin/AboutView.vue'),
},
]
}
],
});
+13
View File
@@ -0,0 +1,13 @@
<template>
<main>
<div>
<el-row>
<el-col>1</el-col>
</el-row>
<el-button>1</el-button>
</div>
</main>
</template>
<script lang="ts" setup>
</script>
+34
View File
@@ -0,0 +1,34 @@
<template>
<el-container style="height: 100vh;width: 100vw;position: relative;user-select: none">
<el-header>
<el-menu mode="horizontal" router default-active="/admin">
<el-menu-item v-for="menu in menus" :index="menu.path" :key="menu.path">{{menu.name}}</el-menu-item>
</el-menu>
</el-header>
<el-main>
<router-view/>
</el-main>
</el-container>
</template>
<script setup lang="ts">
import { useDark } from '@vueuse/core';
import { ref } from "vue";
const isDark = useDark()
const menus = ref([
{
name: '文件管理',
path: '/admin',
},
{
name: '系统设置',
path: '/admin/setting',
},
{
name: '关于我们',
path: '/admin/about',
}
]);
console.log(isDark.value);
</script>
<style lang="scss" scoped>
</style>
+69
View File
@@ -0,0 +1,69 @@
<template>
<main>
<el-table stripe :data="tableData" style="width: 100%">
<el-table-column prop="code" label="取件码" />
<el-table-column prop="prefix" label="文件前缀" />
<el-table-column prop="suffix" label="后缀" />
<el-table-column prop="text" label="文本">
<template #default="scope">
<span style="width: 6rem;overflow: hidden;text-overflow: ellipsis;white-space: nowrap;">{{ scope.row.text }}</span>
</template>
</el-table-column>
<el-table-column prop="used_count" label="已用次数" />
<el-table-column prop="expired_count" label="可用次数" />
<el-table-column prop="file_path" label="文件路径" />
<el-table-column>
<template #header>
操作
</template>
<template #default="scope">
<el-button type="danger" size="small" @click="deleteFile(scope.row.id)">删除</el-button>
</template>
</el-table-column>
</el-table>
<el-pagination @size-change="updatePageSize" @current-change="updateCurrentPage" background layout="prev, pager, next" :page-size="params.size" :page-count="params.total/params.size" :total="params.total" />
</main>
</template>
<script lang="ts" setup>
import { request } from "@/utils/request";
import { ref } from "vue";
import { ElMessage } from "element-plus";
const tableData = ref([]);
const params = ref({
page: 1,
size: 10,
total: 0,
});
const updateCurrentPage = (currentPage: number) => {
params.value.page = currentPage;
refreshData();
};
const deleteFile = (id: number) => {
request({
url: '/admin/file/delete',
method: 'delete',
data: {
id,
},
}).then(() => {
ElMessage.success('删除成功');
refreshData();
});
};
const updatePageSize=(pageSize: number) => {
params.value.size = pageSize;
refreshData();
};
const refreshData=() => {
request({
url: '/admin/file/list',
method: 'get',
params: params.value,
}).then((res:any) => {
tableData.value = res.detail.data;
params.value.total = res.detail.total;
});
}
refreshData();
</script>
@@ -0,0 +1,12 @@
<template>
<main>
<div>
<el-row>
<el-col>1</el-col>
</el-row>
</div>
</main>
</template>
<script lang="ts" setup>
</script>
-14
View File
@@ -1,14 +0,0 @@
<template>
<el-container style="width: 100vw;height: 100%;position: relative">
<el-aside width="200" style="height: 100%">
<el-menu>
<el-menu-item index="1">文件管理</el-menu-item>
<el-menu-item index="4">1</el-menu-item>
</el-menu>
</el-aside>
<el-main>Main</el-main>
</el-container>
</template>
<script setup lang="ts">
</script>
Binary file not shown.
Binary file not shown.