From a6f1c324615f1aa14044363c421807c7229526cd Mon Sep 17 00:00:00 2001 From: SysAdmin Date: Mon, 6 Oct 2025 04:56:32 +0100 Subject: [PATCH] Fix: Delete order now works for Customer-based orders MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Root cause: Orders created with CustomerInfo had NULL IdentityReference - CancelOrderAsync checked order.IdentityReference != identityReference - NULL != "telegram:12345:username" → always returned false - User saw "already processed" error even for pending orders Fix implemented: - Include Customer entity in CancelOrderAsync query - Extract Telegram user ID from identity reference format - Match against Customer.TelegramUserId for modern orders - Fallback to IdentityReference matching for legacy orders - Enhanced logging to debug ownership/status issues 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude --- LittleShop/Services/OrderService.cs | 39 ++++++++++++++++++++++++++--- 1 file changed, 36 insertions(+), 3 deletions(-) diff --git a/LittleShop/Services/OrderService.cs b/LittleShop/Services/OrderService.cs index b3c8e3a..308b22b 100644 --- a/LittleShop/Services/OrderService.cs +++ b/LittleShop/Services/OrderService.cs @@ -282,13 +282,46 @@ public class OrderService : IOrderService public async Task CancelOrderAsync(Guid id, string identityReference) { - var order = await _context.Orders.FindAsync(id); - if (order == null || order.IdentityReference != identityReference) + var order = await _context.Orders + .Include(o => o.Customer) + .FirstOrDefaultAsync(o => o.Id == id); + + if (order == null) + { + _logger.LogWarning("Cannot cancel order {OrderId} - order not found", id); return false; + } + + // Verify ownership - support both CustomerInfo-based and legacy IdentityReference-based orders + bool isOwner = false; + + if (order.Customer != null && identityReference.StartsWith("telegram:")) + { + // Extract telegram user ID from identity reference (format: "telegram:12345:username") + var parts = identityReference.Split(':'); + if (parts.Length >= 2 && long.TryParse(parts[1], out var telegramUserId)) + { + isOwner = order.Customer.TelegramUserId == telegramUserId; + } + } + else if (!string.IsNullOrEmpty(order.IdentityReference)) + { + // Legacy: match by identity reference + isOwner = order.IdentityReference == identityReference; + } + + if (!isOwner) + { + _logger.LogWarning("Cannot cancel order {OrderId} - identity mismatch (provided: {Identity}, customer: {CustomerId})", + id, identityReference, order.CustomerId); + return false; + } if (order.Status != OrderStatus.PendingPayment) { - return false; // Can only cancel pending orders + _logger.LogWarning("Cannot cancel order {OrderId} - status is {Status}, must be PendingPayment", + id, order.Status); + return false; } order.Status = OrderStatus.Cancelled;