Apply second code review fixes: robustness and correctness
- AiAssistantService: 90s HTTP timeout; RefineWithCorrections uses 29.99 example price and explicit "Never return 0" instruction; treat returned 0 as missing and keep original price instead - EbayAuthService: shared static HttpClient for all auth/token calls; SemaphoreSlim double-checked locking on GetAppTokenAsync to prevent concurrent token fetches - EbayPriceResearchService: 15s timeout; require ≥5 samples before suggesting; trim top/bottom 10% outliers; BEST_MATCH sort avoids spam/broken listing bias - PhotoAnalysisView: spinner-show inside try (Issue 1); decimal→double casts use Math.Round to avoid 19.99→19.989... drift (Issue 6); Dispatcher.CheckAccess guard for off-thread callers (Issue 7); save toast always restarts instead of silently dropping rapid saves, eliminating any stuck-flag path (Issue 8) Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -16,7 +16,7 @@ public class AiAssistantService
|
||||
{
|
||||
private readonly string _apiKey;
|
||||
private readonly string _model;
|
||||
private static readonly HttpClient _http = new();
|
||||
private static readonly HttpClient _http = new() { Timeout = TimeSpan.FromSeconds(90) };
|
||||
|
||||
private const string ApiUrl = "https://openrouter.ai/api/v1/chat/completions";
|
||||
|
||||
@@ -142,20 +142,25 @@ public class AiAssistantService
|
||||
public async Task<(string Title, string Description, decimal Price, string PriceReasoning)>
|
||||
RefineWithCorrectionsAsync(string title, string description, decimal price, string corrections)
|
||||
{
|
||||
var priceContext = price > 0
|
||||
? $"Current price: £{price:F2}\n\n"
|
||||
: "";
|
||||
|
||||
var prompt =
|
||||
"You are an expert eBay UK seller. I have a listing with incorrect details that need fixing.\n\n" +
|
||||
$"Current title: {title}\n" +
|
||||
$"Current description:\n{description}\n\n" +
|
||||
$"Current price: £{price:F2}\n\n" +
|
||||
priceContext +
|
||||
$"CORRECTIONS FROM SELLER: {corrections}\n\n" +
|
||||
"Rewrite the listing incorporating these corrections. " +
|
||||
"Return ONLY valid JSON — no markdown, no explanation:\n" +
|
||||
"{\n" +
|
||||
" \"title\": \"corrected eBay UK title, max 80 chars, keyword-rich\",\n" +
|
||||
" \"description\": \"corrected full plain-text eBay UK description\",\n" +
|
||||
" \"price_suggested\": 0.00,\n" +
|
||||
" \"price_suggested\": 29.99,\n" +
|
||||
" \"price_reasoning\": \"one sentence why this price\"\n" +
|
||||
"}";
|
||||
"}\n\n" +
|
||||
"price_suggested MUST be a realistic GBP amount greater than 0. Never return 0.";
|
||||
|
||||
var json = await CallAsync(prompt);
|
||||
|
||||
@@ -169,10 +174,11 @@ public class AiAssistantService
|
||||
obj = JObject.Parse(m.Success ? m.Groups[1].Value : json.Trim());
|
||||
}
|
||||
|
||||
var parsedPrice = obj["price_suggested"]?.Value<decimal>() ?? 0;
|
||||
return (
|
||||
obj["title"]?.ToString() ?? title,
|
||||
obj["description"]?.ToString() ?? description,
|
||||
obj["price_suggested"]?.Value<decimal>() ?? price,
|
||||
obj["title"]?.ToString() ?? title,
|
||||
obj["description"]?.ToString() ?? description,
|
||||
parsedPrice > 0 ? parsedPrice : price, // treat 0 as "not provided", keep original
|
||||
obj["price_reasoning"]?.ToString() ?? ""
|
||||
);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user