Files
hack/tools/scripts/llm-key-hunter/results/_cache/content/125w5_deepnote.json
T

1 line
7.9 KiB
JSON
Raw Blame History

This file contains invisible Unicode characters
This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
{"repo": "125w5/deepnote", "files": {"native/src/DeepNote.App/MainWindow.Settings.cs": {"f86adb1765de16a662ba7a89a436afd7ea6bcf46": {"t": 1785746218.7631025, "n": 6915, "h": "e7892938f7ea6131", "c": "using System;\nusing System.Collections.Generic;\nusing System.Collections.ObjectModel;\nusing System.Diagnostics;\nusing System.IO;\nusing System.Linq;\nusing System.Net.Http;\nusing System.Net.Http.Headers;\nusing System.Runtime.InteropServices;\nusing System.Runtime.CompilerServices;\nusing System.Runtime.InteropServices.WindowsRuntime;\nusing System.Security.Cryptography;\nusing System.Text;\nusing System.Text.Json;\nusing System.Threading;\nusing System.Threading.Tasks;\nusing DeepNote.Core;\nusing DeepNote.Pdf;\nusing DeepNote.Storage;\nusing Microsoft.UI.Xaml;\nusing Microsoft.UI.Xaml.Controls;\nusing Microsoft.UI.Xaml.Controls.Primitives;\nusing Microsoft.UI.Xaml.Input;\nusing Microsoft.UI.Xaml.Media;\nusing Microsoft.UI.Xaml.Media.Imaging;\nusing Microsoft.UI.Xaml.Shapes;\nusing WinRT.Interop;\nusing Windows.ApplicationModel.DataTransfer;\nusing Windows.Data.Pdf;\nusing Windows.Foundation;\nusing Windows.Graphics.Imaging;\nusing Windows.Media.Ocr;\nusing Windows.Storage;\nusing Windows.Storage.FileProperties;\nusing Windows.Storage.Pickers;\nusing Windows.Storage.Streams;\nusing Windows.System;\nusing Windows.UI;\n\nnamespace DeepNote.App;\n\npublic sealed partial class MainWindow\n{\n\tprivate async void TestAiConnection_Click(object sender, RoutedEventArgs e)\n\t{\n\t\tawait TestAiConnectionAsync();\n\t}\n\n\tprivate async void SaveSettings_Click(object sender, RoutedEventArgs e)\n\t{\n\t\t_persistedState.AiProvider = GetSelectedComboText(AiProviderBox, \"OpenAI Compatible\");\n\t\t_persistedState.AiBaseUrl = AiBaseUrlBox.Text;\n\t\t_persistedState.AiModel = AiModelBox.Text;\n\t\t_persistedState.AiBudget = GetSelectedComboText(AiBudgetBox, \"低消耗\");\n\t\t_persistedState.OcrEngine = GetSelectedComboText(OcrEngineBox, \"Windows OCR\");\n\t\t_persistedState.OcrLanguage = OcrLanguageBox.Text;\n\t\t_persistedState.OcrBatchSize = OcrBatchBox.Text;\n\t\t_persistedState.AutoLoadOcrCache = AutoLoadOcrCacheBox.IsChecked == true;\n\t\t_persistedState.AutoOcrCurrentPage = AutoOcrCurrentPageBox.IsChecked == true;\n\t\t_persistedState.AutoOcrDelayMs = (int.TryParse(AutoOcrDelayBox.Text, out var delay) ? Math.Clamp(delay, 0, 5000) : 300);\n\t\t_autoLoadOcrCache = _persistedState.AutoLoadOcrCache;\n\t\t_autoOcrCurrentPage = _persistedState.AutoOcrCurrentPage;\n\t\t_autoOcrDelayMs = _persistedState.AutoOcrDelayMs;\n\t\tstring protectedApiKey = ProtectApiKey(AiApiKeyBox.Password);\n\t\tawait _database.SaveSettingAsync(\"ai\", JsonSerializer.Serialize(new\n\t\t{\n\t\t\tAiProvider = _persistedState.AiProvider,\n\t\t\tAiBaseUrl = _persistedState.AiBaseUrl,\n\t\t\tAiModel = _persistedState.AiModel,\n\t\t\tAiBudget = _persistedState.AiBudget,\n\t\t\tApiKeyProtected = protectedApiKey,\n\t\t\tApiKeyStorage = (string.IsNullOrWhiteSpace(protectedApiKey) ? \"empty\" : \"dpapi-current-user\")\n\t\t}));\n\t\tawait _database.SaveSettingAsync(\"ocr\", JsonSerializer.Serialize(new\n\t\t{\n\t\t\tOcrEngine = _persistedState.OcrEngine,\n\t\t\tOcrLanguage = _persistedState.OcrLanguage,\n\t\t\tOcrBatchSize = _persistedState.OcrBatchSize,\n\t\t\tAutoLoadOcrCache = _persistedState.AutoLoadOcrCache,\n\t\t\tAutoOcrCurrentPage = _persistedState.AutoOcrCurrentPage,\n\t\t\tAutoOcrDelayMs = _persistedState.AutoOcrDelayMs,\n\t\t\tCacheEnabled = true,\n\t\t\tMaxConcurrency = 1\n\t\t}));\n\t\tStatusText.Text = \"设置已保存到 SQLite,API Key 已使用 DPAPI 当前用户范围加密。\";\n\t\tawait SaveCurrentStateAsync();\n\t}\n\n\tprivate void ClearApiKey_Click(object sender, RoutedEventArgs e)\n\t{\n\t\tAiApiKeyBox.Password = string.Empty;\n\t\tStatusText.Text = \"API Key 已清空。\";\n\t}\n\n\tprivate void RecordShortcut_Click(object sender, RoutedEventArgs e)\n\t{\n\t\tStatusText.Text = \"快捷键重录入口已就绪。下一步会捕获按键并写入快捷键设置。\";\n\t}\n\n\tprivate void AiProviderBox_SelectionChanged(object sender, SelectionChangedEventArgs e)\n\t{\n\t\tswitch ((!(AiProviderBox.SelectedItem is ComboBoxItem { Content: var content })) ? \"\" : content?.ToString())\n\t\t{\n\t\tcase \"DeepSeek\":\n\t\t\tAiBaseUrlBox.Text = \"https://api.deepseek.com/v1\";\n\t\t\tAiModelBox.Text = \"deepseek-chat\";\n\t\t\tbreak;\n\t\tcase \"Moonshot\":\n\t\t\tAiBaseUrlBox.Text = \"https://api.moonshot.cn/v1\";\n\t\t\tAiModelBox.Text = \"moonshot-v1-8k\";\n\t\t\tbreak;\n\t\tcase \"通义千问\":\n\t\t\tAiBaseUrlBox.Text = \"https://dashscope.aliyuncs.com/compatible-mode/v1\";\n\t\t\tAiModelBox.Text = \"qwen-plus\";\n\t\t\tbreak;\n\t\tcase \"Ollama 本地\":\n\t\t\tAiBaseUrlBox.Text = \"http://localhost:11434/v1\";\n\t\t\tAiModelBox.Text = \"llama3.1\";\n\t\t\tbreak;\n\t\tcase \"OpenAI\":\n\t\t\tAiBaseUrlBox.Text = \"https://api.openai.com/v1\";\n\t\t\tAiModelBox.Text = \"gpt-4.1-mini\";\n\t\t\tbreak;\n\t\t}\n\t}\n\n\tprivate async Task TestAiConnectionAsync()\n\t{\n\t\tstring baseUrl = AiBaseUrlBox.Text.Trim().TrimEnd('/');\n\t\tif (string.IsNullOrWhiteSpace(baseUrl))\n\t\t{\n\t\t\tStatusText.Text = \"AI 测试失败:Base URL 不能为空。\";\n\t\t\treturn;\n\t\t}\n\t\tStatusText.Text = \"正在测试 AI 连接:\" + GetSelectedComboText(AiProviderBox, \"OpenAI Compatible\") + \" · \" + baseUrl;\n\t\ttry\n\t\t{\n\t\t\tusing HttpClient client = new HttpClient\n\t\t\t{\n\t\t\t\tTimeout = TimeSpan.FromSeconds(10L)\n\t\t\t};\n\t\t\tif (!string.IsNullOrWhiteSpace(AiApiKeyBox.Password))\n\t\t\t{\n\t\t\t\tclient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue(\"Bearer\", AiApiKeyBox.Password);\n\t\t\t}\n\t\t\tusing HttpResponseMessage response = await client.GetAsync(baseUrl + \"/models\");\n\t\t\tawait _database.SaveSettingAsync(\"ai.lastTest\", JsonSerializer.Serialize(new\n\t\t\t{\n\t\t\t\tBaseUrl = baseUrl,\n\t\t\t\tStatusCode = (int)response.StatusCode,\n\t\t\t\tIsSuccessStatusCode = response.IsSuccessStatusCode,\n\t\t\t\tTestedAt = DateTimeOffset.UtcNow\n\t\t\t}));\n\t\t\tStatusText.Text = (response.IsSuccessStatusCode ? \"AI 连接测试成功:/models 可访问。\" : $\"AI 连接测试失败:HTTP {response.StatusCode} {response.ReasonPhrase}\");\n\t\t}\n\t\tcatch (Exception ex)\n\t\t{\n\t\t\tawait _database.SaveSettingAsync(\"ai.lastTest\", JsonSerializer.Serialize(new\n\t\t\t{\n\t\t\t\tBaseUrl = baseUrl,\n\t\t\t\tIsSuccessStatusCode = false,\n\t\t\t\tError = ex.Message,\n\t\t\t\tTestedAt = DateTimeOffset.UtcNow\n\t\t\t}));\n\t\t\tStatusText.Text = \"AI 连接测试失败:\" + ex.Message;\n\t\t}\n\t}\n\n\tprivate static string GetSelectedComboText(ComboBox comboBox, string fallback)\n\t{\n\t\treturn (!(comboBox.SelectedItem is ComboBoxItem { Content: var content })) ? (comboBox.SelectionBoxItem?.ToString() ?? fallback) : (content?.ToString() ?? fallback);\n\t}\n\n\tprivate static string ProtectApiKey(string apiKey)\n\t{\n\t\tif (string.IsNullOrWhiteSpace(apiKey))\n\t\t{\n\t\t\treturn \"\";\n\t\t}\n\t\tbyte[] bytes = Encoding.UTF8.GetBytes(apiKey);\n\t\tbyte[] inArray = ProtectedData.Protect(bytes, null, DataProtectionScope.CurrentUser);\n\t\treturn Convert.ToBase64String(inArray);\n\t}\n\n\tprivate void OpenPluginFolder_Click(object sender, RoutedEventArgs e)\n\t{\n\t\tStatusText.Text = \"插件目录入口已就绪。\";\n\t}\n\n\tprivate void PluginDocs_Click(object sender, RoutedEventArgs e)\n\t{\n\t\tStatusText.Text = \"插件开发文档入口已就绪。\";\n\t}\n\n\tprivate async void SettingsButton_Click(object sender, RoutedEventArgs e)\n\t{\n\t\tawait _commands.ExecuteAsync(\"workspace.settings\");\n\t}\n\n\tprivate Task ShowSettingsAsync()\n\t{\n\t\tStatusText.Text = \"设置页入口已打开:常规、阅读器、AI、OCR、插件、快捷键、存储、诊断将逐步接入真实页面。\";\n\t\t_activeRightTab = \"ai\";\n\t\tApplyRightTabVisuals();\n\t\treturn CreateAiDraftAsync(\"AI 设置入口\", \"AI 设置将支持:OpenAI、DeepSeek、Moonshot、通义、Ollama、自定义 OpenAI Compatible;API Key 会加密保存。\");\n\t}\n}\n\n"}}}}