Files
hack/tools/scripts/llm-key-hunter/results/_cache/content/andretripol_pico-pu-api-control.json
OpenCode 68a9071cf1 feat: reconcile local master with origin (exa/hot-platform hunters, leaks ledger, latest results)
Local branch had diverged from origin/master (sibling commits on the same base). Rewrote local history linearly on top of origin/master, folding in all local content: exa/hot-platform discovery hunters, leaks ledger, nightly sweep orchestrator, updated .gitignore and skill docs, plus the latest hunt output and vault state. Remote-only files (vault keys, channel scripts) were restored rather than dropped, so the resulting tree is a full union of both sides.
2026-08-07 12:53:47 +08:00

1 line
6.8 KiB
JSON

{"repo": "andretripol/pico-pu-api-control", "files": {"PicoPuApiControl.Core/BalanceClient.cs": {"0a8cc0f9bae46101722234bb2afa4c8b8d752425": {"t": 1786068388.7539876, "n": 2194, "h": "745c156d12c29c58", "c": "using System.Net.Http.Headers;\nusing System.Net.Http.Json;\nusing System.Text.Json;\nusing System.Text.Json.Serialization;\n\nnamespace PicoPuApiControl.Core;\n\npublic sealed class BalanceInfo\n{\n [JsonPropertyName(\"currency\")]\n public string? Currency { get; set; }\n\n [JsonPropertyName(\"total_balance\")]\n public string? TotalBalance { get; set; }\n\n [JsonPropertyName(\"granted_balance\")]\n public string? GrantedBalance { get; set; }\n\n [JsonPropertyName(\"topped_up_balance\")]\n public string? ToppedUpBalance { get; set; }\n}\n\npublic sealed class BalanceResponse\n{\n [JsonPropertyName(\"is_available\")]\n public bool IsAvailable { get; set; }\n\n [JsonPropertyName(\"balance_infos\")]\n public List<BalanceInfo>? BalanceInfos { get; set; }\n}\n\npublic sealed class BalanceApiException : Exception\n{\n public int StatusCode { get; }\n\n public BalanceApiException(int statusCode, string body, string providerName = \"DeepSeek\")\n : base($\"{providerName} API returned {statusCode}: {body}\")\n {\n StatusCode = statusCode;\n }\n}\n\npublic sealed class BalanceClient\n{\n private readonly HttpClient _http;\n private readonly string _baseUrl;\n\n public BalanceClient(string baseUrl = \"https://api.deepseek.com\", HttpClient? http = null)\n {\n _baseUrl = baseUrl.TrimEnd('/');\n _http = http ?? new HttpClient();\n }\n\n public async Task<BalanceResponse?> GetBalanceAsync(string apiKey, CancellationToken ct = default)\n {\n using var request = new HttpRequestMessage(HttpMethod.Get, $\"{_baseUrl}/user/balance\");\n request.Headers.Authorization = new AuthenticationHeaderValue(\"Bearer\", apiKey);\n request.Headers.Accept.Add(new MediaTypeWithQualityHeaderValue(\"application/json\"));\n\n using var response = await _http.SendAsync(request, ct).ConfigureAwait(false);\n var body = await response.Content.ReadAsStringAsync(ct).ConfigureAwait(false);\n\n if (!response.IsSuccessStatusCode)\n throw new BalanceApiException((int)response.StatusCode, body);\n\n if (string.IsNullOrWhiteSpace(body))\n return null;\n\n return JsonSerializer.Deserialize<BalanceResponse>(body);\n }\n}\n"}}, "PicoPuApiControl.Core/ProviderCatalog.cs": {"0a8cc0f9bae46101722234bb2afa4c8b8d752425": {"t": 1786068389.3814323, "n": 3991, "h": "7ffa1fcdb56e4b5d", "c": "namespace PicoPuApiControl.Core;\n\npublic static class ProviderIds\n{\n public const string DeepSeek = \"deepseek\";\n public const string OpenAi = \"openai\";\n public const string Claude = \"claude\";\n public const string Qwen = \"qwen\";\n public const string MiMo = \"mimo\";\n public const string Grok = \"grok\";\n public const string Gemini = \"gemini\";\n public const string Glm = \"glm\";\n public const string Kimi = \"kimi\";\n public const string OpenRouter = \"openrouter\";\n}\n\npublic enum BalanceMode\n{\n Automatic,\n Manual,\n}\n\npublic sealed record ProviderDefinition(\n string Id,\n string DisplayName,\n string ShortName,\n string BaseUrl,\n string BalancePath,\n string PortalUrl,\n BalanceMode BalanceMode)\n{\n public bool HasBalanceEndpoint => this.BalanceMode == PicoPuApiControl.Core.BalanceMode.Automatic;\n public bool IsManual => this.BalanceMode == PicoPuApiControl.Core.BalanceMode.Manual;\n}\n\n/// <summary>\n/// Providers with an official balance endpoint are queried automatically.\n/// Providers whose ordinary API key does not expose a public balance are\n/// available in explicit manual mode; their amounts never pretend to be\n/// provider-reported data.\n/// </summary>\npublic static class ProviderCatalog\n{\n private static readonly IReadOnlyList<ProviderDefinition> Providers =\n [\n new(\n ProviderIds.DeepSeek,\n \"DeepSeek\",\n \"DS\",\n \"https://api.deepseek.com\",\n \"/user/balance\",\n \"https://platform.deepseek.com\",\n BalanceMode.Automatic),\n new(\n ProviderIds.OpenAi,\n \"OpenAI\",\n \"AI\",\n \"\",\n \"\",\n \"https://platform.openai.com/usage\",\n BalanceMode.Manual),\n new(\n ProviderIds.Claude,\n \"Claude\",\n \"CL\",\n \"\",\n \"\",\n \"https://console.anthropic.com/settings/billing\",\n BalanceMode.Manual),\n new(\n ProviderIds.Qwen,\n \"Qwen\",\n \"QW\",\n \"\",\n \"\",\n \"https://bailian.console.aliyun.com/\",\n BalanceMode.Manual),\n new(\n ProviderIds.MiMo,\n \"MiMo\",\n \"MI\",\n \"\",\n \"\",\n \"https://platform.xiaomimimo.com/\",\n BalanceMode.Manual),\n new(\n ProviderIds.Grok,\n \"Grok\",\n \"GK\",\n \"\",\n \"\",\n \"https://console.x.ai/\",\n BalanceMode.Manual),\n new(\n ProviderIds.Gemini,\n \"Gemini\",\n \"GE\",\n \"\",\n \"\",\n \"https://aistudio.google.com/\",\n BalanceMode.Manual),\n new(\n ProviderIds.Glm,\n \"GLM\",\n \"GL\",\n \"\",\n \"\",\n \"https://open.bigmodel.cn/\",\n BalanceMode.Manual),\n new(\n ProviderIds.Kimi,\n \"Kimi\",\n \"KM\",\n \"\",\n \"\",\n \"https://platform.moonshot.cn/\",\n BalanceMode.Manual),\n new(\n ProviderIds.OpenRouter,\n \"OpenRouter\",\n \"OR\",\n \"https://openrouter.ai\",\n \"/api/v1/key\",\n \"https://openrouter.ai/credits\",\n BalanceMode.Automatic),\n ];\n\n public static IReadOnlyList<ProviderDefinition> All => Providers;\n\n public static ProviderDefinition Get(string providerId)\n => Providers.FirstOrDefault(p => string.Equals(p.Id, providerId, StringComparison.OrdinalIgnoreCase))\n ?? throw new ArgumentException($\"Unknown provider: {providerId}\", nameof(providerId));\n\n public static bool TryGet(string? providerId, out ProviderDefinition definition)\n {\n definition = Providers.FirstOrDefault(p =>\n string.Equals(p.Id, providerId, StringComparison.OrdinalIgnoreCase))!;\n return definition is not null;\n }\n}\n"}}}}