diff --git a/components.d.ts b/components.d.ts index 6fd7eb0..7d40eed 100644 --- a/components.d.ts +++ b/components.d.ts @@ -15,13 +15,16 @@ declare module 'vue' { MiaoLazyDiv: typeof import('./src/components/miaoLazyDiv.vue')['default'] MiaoMask: typeof import('./src/components/miaoMask.vue')['default'] MiaoPopupInput: typeof import('./src/components/miaoPopupInput.vue')['default'] + NAlert: typeof import('naive-ui')['NAlert'] NButton: typeof import('naive-ui')['NButton'] NCard: typeof import('naive-ui')['NCard'] + NCheckbox: typeof import('naive-ui')['NCheckbox'] NEllipsis: typeof import('naive-ui')['NEllipsis'] NEmpty: typeof import('naive-ui')['NEmpty'] NGrid: typeof import('naive-ui')['NGrid'] NGridItem: typeof import('naive-ui')['NGridItem'] NIcon: typeof import('naive-ui')['NIcon'] + NInput: typeof import('naive-ui')['NInput'] NQrCode: typeof import('naive-ui')['NQrCode'] NScrollbar: typeof import('naive-ui')['NScrollbar'] NSpace: typeof import('naive-ui')['NSpace'] diff --git a/src-server/api/mapHandler.go b/src-server/api/mapHandler.go new file mode 100644 index 0000000..830b188 --- /dev/null +++ b/src-server/api/mapHandler.go @@ -0,0 +1,142 @@ +package api + +import ( + "crypto/md5" + "encoding/hex" + "io/ioutil" + "net/http" + "os" + "path/filepath" + + "github.com/gin-gonic/gin" +) + +// 内存存储 +var memoryStorage = make(map[string][]byte) + +// MapSetHandler 处理 /map/set/*key 请求 +func MapSetHandler(c *gin.Context) { + key := c.Param("key") + if key == "" || key == "/" { + c.JSON(http.StatusBadRequest, gin.H{"message": "failed", "error": "Key is required"}) + return + } + key = key[1:] // 移除开头的"/" + + // 获取disk参数 + diskParam := c.DefaultQuery("disk", "0") + + // 读取请求体数据 + data, err := ioutil.ReadAll(c.Request.Body) + if err != nil { + c.JSON(http.StatusBadRequest, gin.H{"message": "failed", "error": "Failed to read request body"}) + return + } + + if diskParam == "1" { + // 保存到文件系统 + cachePath := filepath.Join(staticPath, ".miaodir_cache") + + // 确保缓存目录存在 + if err := os.MkdirAll(cachePath, os.ModePerm); err != nil { + c.JSON(http.StatusInternalServerError, gin.H{"message": "failed", "error": "Failed to create cache directory"}) + return + } + + // 生成文件名 + hasher := md5.New() + hasher.Write([]byte(key)) + filename := hex.EncodeToString(hasher.Sum(nil)) + + // 写入文件 + filePath := filepath.Join(cachePath, filename) + if err := ioutil.WriteFile(filePath, data, 0644); err != nil { + c.JSON(http.StatusInternalServerError, gin.H{"message": "failed", "error": "Failed to write file"}) + return + } + } else { + // 保存到内存 + memoryStorage[key] = data + } + + c.JSON(http.StatusOK, gin.H{"message": "success"}) +} + +// MapGetHandler 处理 /map/get/*key 请求 +func MapGetHandler(c *gin.Context) { + key := c.Param("key") + if key == "" || key == "/" { + c.JSON(http.StatusBadRequest, gin.H{"message": "failed", "error": "Key is required"}) + return + } + key = key[1:] // 移除开头的"/" + + // 获取disk参数 + diskParam := c.DefaultQuery("disk", "0") + + var data []byte + var err error + + if diskParam == "1" { + // 从文件系统获取 + cachePath := filepath.Join(staticPath, ".miaodir_cache") + + // 生成文件名 + hasher := md5.New() + hasher.Write([]byte(key)) + filename := hex.EncodeToString(hasher.Sum(nil)) + + // 读取文件 + filePath := filepath.Join(cachePath, filename) + data, err = ioutil.ReadFile(filePath) + if err != nil { + c.JSON(http.StatusNotFound, gin.H{"message": "failed", "error": "Key not found"}) + return + } + } else { + // 从内存获取 + var exists bool + data, exists = memoryStorage[key] + if !exists { + c.JSON(http.StatusNotFound, gin.H{"message": "failed", "error": "Key not found"}) + return + } + } + + c.Data(http.StatusOK, "application/octet-stream", data) +} + +// MapDeleteHandler 处理 /map/delete/*key 请求 +func MapDeleteHandler(c *gin.Context) { + key := c.Param("key") + if key == "" || key == "/" { + c.JSON(http.StatusBadRequest, gin.H{"message": "failed", "error": "Key is required"}) + return + } + key = key[1:] // 移除开头的"/" + + // 获取disk参数 + diskParam := c.DefaultQuery("disk", "0") + + if diskParam == "1" { + // 从文件系统删除 + cachePath := filepath.Join(staticPath, ".miaodir_cache") + + // 生成文件名 + hasher := md5.New() + hasher.Write([]byte(key)) + filename := hex.EncodeToString(hasher.Sum(nil)) + + // 删除文件 + filePath := filepath.Join(cachePath, filename) + if err := os.Remove(filePath); err != nil && !os.IsNotExist(err) { + c.JSON(http.StatusInternalServerError, gin.H{"message": "failed", "error": "Failed to delete file"}) + return + } + } else { + // 从内存删除 + delete(memoryStorage, key) + } + + c.JSON(http.StatusOK, gin.H{"message": "success"}) +} diff --git a/src-server/main.go b/src-server/main.go index 4d54de0..c7d9023 100644 --- a/src-server/main.go +++ b/src-server/main.go @@ -42,6 +42,11 @@ func main() { // 添加获取所有可用地址的API router.GET("/addresses", api.AddressesHandler(port)) + // 添加map相关API + router.POST("/map/set/*key", api.MapSetHandler) + router.GET("/map/get/*key", api.MapGetHandler) + router.POST("/map/delete/*key", api.MapDeleteHandler) + // Redirect from '/' to '/web/' router.GET("/", func(c *gin.Context) { c.Redirect(http.StatusMovedPermanently, "/web/") diff --git a/src/class/PluginCenter.ts b/src/class/PluginCenter.ts index 1efbcda..43e3432 100644 --- a/src/class/PluginCenter.ts +++ b/src/class/PluginCenter.ts @@ -173,12 +173,12 @@ export default class PluginCenter { } } - usePlugin( - key: string, - VDirectories?: VirtualDirectory[], - VFiles?: VirtualFile[], - ...args: any[] - ): void + // usePlugin( + // key: string, + // VDirectories?: VirtualDirectory[], + // VFiles?: VirtualFile[], + // ...args: any[] + // ): void usePlugin( key: string, VDirectories?: VirtualDirectory[], diff --git a/src/hooks/init/initPlugin.ts b/src/hooks/init/initPlugin.ts index f409c4b..3f4a291 100644 --- a/src/hooks/init/initPlugin.ts +++ b/src/hooks/init/initPlugin.ts @@ -9,18 +9,22 @@ const initPlugin = async (globalAlertTip: alertTipType) => { }) const pluginCenter = usePluginCenter() for (let pluginConfig of Object.values(modulesFiles)) { - const _config = pluginConfig as { - default: registerComponentOption | Plugin - type: PluginExportType - key?: string - } - const { type, key = `${Math.random()}` } = _config - if (type === PluginExportType.component) { - pluginCenter.registerComponent( - _config.default as registerComponentOption - ) - } else if (type === PluginExportType.default) { - pluginCenter.register(key as string, _config.default as Plugin) + try { + const _config = pluginConfig as { + default: registerComponentOption | Plugin + type: PluginExportType + key?: string + } + const { type, key = `${Math.random()}` } = _config + if (type === PluginExportType.component) { + pluginCenter.registerComponent( + _config.default as registerComponentOption + ) + } else if (type === PluginExportType.default) { + pluginCenter.register(key as string, _config.default as Plugin) + } + } catch (error) { + console.error(`插件 ${pluginConfig} 初始化失败`, error) } } } diff --git a/src/plugins/miaoKVMap/KVMapPlugin.vue b/src/plugins/miaoKVMap/KVMapPlugin.vue new file mode 100644 index 0000000..2fc8473 --- /dev/null +++ b/src/plugins/miaoKVMap/KVMapPlugin.vue @@ -0,0 +1,211 @@ + + + + + \ No newline at end of file diff --git a/src/plugins/miaoKVMap/export.ts b/src/plugins/miaoKVMap/export.ts new file mode 100644 index 0000000..e61f533 --- /dev/null +++ b/src/plugins/miaoKVMap/export.ts @@ -0,0 +1,18 @@ +import { registerComponentOption } from '@/class/PluginCenter' +import { PluginExportType } from '@/types/type' +import { CopyOutline } from '@vicons/ionicons5' + +const pluginConfig: registerComponentOption = { + key: 'miaoKVMap', + name: '键值存储', + icon: CopyOutline, + getComponent: async () => (await import('./KVMapPlugin.vue')).default, + filter: (_, __) => _.length === 0 && __.length === 0, + disable: false, + single: true, + priority: 0 +} + +export default pluginConfig + +export const type = PluginExportType.component \ No newline at end of file diff --git a/src/plugins/miaoKVMap/export_mainMenu.ts b/src/plugins/miaoKVMap/export_mainMenu.ts new file mode 100644 index 0000000..93aff3d --- /dev/null +++ b/src/plugins/miaoKVMap/export_mainMenu.ts @@ -0,0 +1,25 @@ +import { Plugin, PluginGroup } from '@/class/PluginCenter' +import { PluginExportType } from '@/types/type' +import { shallowRef } from 'vue' +import { CopyOutline } from '@vicons/ionicons5' + +const pluginConfig: Plugin = { + name: '键值存储', + icon: shallowRef(CopyOutline), + filter: (_, __, views) => { + return views.find('miaoKVMap').length === 0 + }, + disable: false, + group: [PluginGroup.mainMenu], + func(_, __, hooks) { + const { getPluginCenter } = hooks + const PluginCenter = getPluginCenter() + PluginCenter.usePlugin('miaoKVMap', [], []) + }, + priority: 0 +} + +export default pluginConfig + +export const type = PluginExportType.default +// export const key = 'miaoClipboard_mainMenu' \ No newline at end of file diff --git a/vite.config.ts b/vite.config.ts index ce3fdea..575527f 100644 --- a/vite.config.ts +++ b/vite.config.ts @@ -40,7 +40,7 @@ export default defineConfig({ }, server: { proxy: { - '^/(get|upload|delete|query|rename|cut|copy|mkdir|addresses)': { + '^/(get|upload|delete|query|rename|cut|copy|mkdir|addresses|map)': { target: 'http://127.0.0.1:17705', changeOrigin: true, rewrite: (path) => path