From 7c6f0432c8fd42e61748a1d4a3ed3405633011b9 Mon Sep 17 00:00:00 2001 From: bbedward Date: Thu, 11 Dec 2025 12:00:47 -0500 Subject: [PATCH] clipboard: add copyEntry (by id) handler --- core/cmd/dms/commands_clipboard.go | 45 ++++++++++++++----- core/internal/server/clipboard/handlers.go | 23 ++++++++++ .../Clipboard/ClipboardHistoryModal.qml | 17 +------ 3 files changed, 60 insertions(+), 25 deletions(-) diff --git a/core/cmd/dms/commands_clipboard.go b/core/cmd/dms/commands_clipboard.go index c965fe27..0092ab78 100644 --- a/core/cmd/dms/commands_clipboard.go +++ b/core/cmd/dms/commands_clipboard.go @@ -71,11 +71,13 @@ var clipHistoryCmd = &cobra.Command{ var clipGetCmd = &cobra.Command{ Use: "get ", Short: "Get clipboard entry by ID", - Long: "Get full clipboard entry data by ID (requires server)", + Long: "Get full clipboard entry data by ID (requires server). Use --copy to copy it to clipboard.", Args: cobra.ExactArgs(1), Run: runClipGet, } +var clipGetCopy bool + var clipDeleteCmd = &cobra.Command{ Use: "delete ", Short: "Delete clipboard entry", @@ -153,6 +155,7 @@ func init() { clipWatchCmd.Flags().BoolVar(&clipJSONOutput, "json", false, "Output as JSON") clipHistoryCmd.Flags().BoolVar(&clipJSONOutput, "json", false, "Output as JSON") clipGetCmd.Flags().BoolVar(&clipJSONOutput, "json", false, "Output as JSON") + clipGetCmd.Flags().BoolVarP(&clipGetCopy, "copy", "c", false, "Copy entry to clipboard") clipSearchCmd.Flags().IntVarP(&clipSearchLimit, "limit", "l", 50, "Max results") clipSearchCmd.Flags().IntVarP(&clipSearchOffset, "offset", "o", 0, "Result offset") @@ -349,6 +352,28 @@ func runClipGet(cmd *cobra.Command, args []string) { log.Fatalf("Invalid ID: %v", err) } + if clipGetCopy { + req := map[string]any{ + "id": 1, + "method": "clipboard.copyEntry", + "params": map[string]any{ + "id": id, + }, + } + + resp, err := sendServerRequest(req) + if err != nil { + log.Fatalf("Failed to copy clipboard entry: %v", err) + } + + if resp.Error != "" { + log.Fatalf("Error: %s", resp.Error) + } + + fmt.Printf("Copied entry %d to clipboard\n", id) + return + } + req := map[string]any{ "id": 1, "method": "clipboard.getEntry", @@ -375,17 +400,17 @@ func runClipGet(cmd *cobra.Command, args []string) { log.Fatal("Invalid response format") } - if clipJSONOutput { - output, _ := json.MarshalIndent(entry, "", " ") - fmt.Println(string(output)) - return - } - - if data, ok := entry["data"].(string); ok { - fmt.Print(data) - } else { + switch { + case clipJSONOutput: output, _ := json.MarshalIndent(entry, "", " ") fmt.Println(string(output)) + default: + if data, ok := entry["data"].(string); ok { + fmt.Print(data) + } else { + output, _ := json.MarshalIndent(entry, "", " ") + fmt.Println(string(output)) + } } } diff --git a/core/internal/server/clipboard/handlers.go b/core/internal/server/clipboard/handlers.go index 4a7f4f6c..4f37f89e 100644 --- a/core/internal/server/clipboard/handlers.go +++ b/core/internal/server/clipboard/handlers.go @@ -23,6 +23,8 @@ func HandleRequest(conn net.Conn, req models.Request, m *Manager) { handleClearHistory(conn, req, m) case "clipboard.copy": handleCopy(conn, req, m) + case "clipboard.copyEntry": + handleCopyEntry(conn, req, m) case "clipboard.paste": handlePaste(conn, req, m) case "clipboard.subscribe": @@ -103,6 +105,27 @@ func handleCopy(conn net.Conn, req models.Request, m *Manager) { models.Respond(conn, req.ID, models.SuccessResult{Success: true, Message: "copied to clipboard"}) } +func handleCopyEntry(conn net.Conn, req models.Request, m *Manager) { + id, err := params.Int(req.Params, "id") + if err != nil { + models.RespondError(conn, req.ID, err.Error()) + return + } + + entry, err := m.GetEntry(uint64(id)) + if err != nil { + models.RespondError(conn, req.ID, err.Error()) + return + } + + if err := m.SetClipboard(entry.Data, entry.MimeType); err != nil { + models.RespondError(conn, req.ID, err.Error()) + return + } + + models.Respond(conn, req.ID, models.SuccessResult{Success: true, Message: "copied to clipboard"}) +} + func handlePaste(conn net.Conn, req models.Request, m *Manager) { text, err := m.PasteText() if err != nil { diff --git a/quickshell/Modals/Clipboard/ClipboardHistoryModal.qml b/quickshell/Modals/Clipboard/ClipboardHistoryModal.qml index d8becf7a..1cc4a92f 100644 --- a/quickshell/Modals/Clipboard/ClipboardHistoryModal.qml +++ b/quickshell/Modals/Clipboard/ClipboardHistoryModal.qml @@ -95,27 +95,14 @@ DankModal { } function copyEntry(entry) { - DMSService.sendRequest("clipboard.getEntry", { + DMSService.sendRequest("clipboard.copyEntry", { "id": entry.id }, function (response) { if (response.error) { ToastService.showError(I18n.tr("Failed to copy entry")); return; } - const fullEntry = response.result; - if (fullEntry.isImage) { - ToastService.showInfo(I18n.tr("Image copied to clipboard")); - } else { - DMSService.sendRequest("clipboard.copy", { - "text": fullEntry.data - }, function (copyResponse) { - if (copyResponse.error) { - ToastService.showError(I18n.tr("Failed to copy")); - return; - } - ToastService.showInfo(I18n.tr("Copied to clipboard")); - }); - } + ToastService.showInfo(entry.isImage ? I18n.tr("Image copied to clipboard") : I18n.tr("Copied to clipboard")); hide(); }); }