diff --git a/src/food-market.infrastructure/Integrations/MoySklad/MoySkladImportService.cs b/src/food-market.infrastructure/Integrations/MoySklad/MoySkladImportService.cs index cb82666..2953411 100644 --- a/src/food-market.infrastructure/Integrations/MoySklad/MoySkladImportService.cs +++ b/src/food-market.infrastructure/Integrations/MoySklad/MoySkladImportService.cs @@ -39,20 +39,14 @@ public async Task ImportCounterpartiesAsync(string token, { var orgId = _tenant.OrganizationId ?? throw new InvalidOperationException("No tenant organization in context."); - // MoySklad сам НЕ имеет встроенного "Supplier/Customer" поля у контрагентов. - // Классификация обычно через теги ("Поставщик"/"Покупатель") или группы. Если их нет — - // оставляем Unspecified, не выдумываем за пользователя. + // MoySklad НЕ имеет поля "Поставщик/Покупатель" у контрагентов вообще — это + // не наша выдумка, проверено через API: counterparty entity содержит только + // group (группа доступа), tags (произвольные), state (пользовательская цепочка + // статусов), companyType (legal/individual/entrepreneur). Никакой role/kind. + // Поэтому при импорте ВСЕГДА ставим Unspecified — пользователь сам решит. + // Параметр tags оставлен ради совместимости сигнатуры, не используется. static foodmarket.Domain.Catalog.CounterpartyKind ResolveKind(IReadOnlyList? tags) - { - if (tags is null || tags.Count == 0) return foodmarket.Domain.Catalog.CounterpartyKind.Unspecified; - var lower = tags.Select(t => t.ToLowerInvariant()).ToList(); - var hasSupplier = lower.Any(t => t.Contains("постав")); - var hasCustomer = lower.Any(t => t.Contains("покуп") || t.Contains("клиент")); - if (hasSupplier && hasCustomer) return foodmarket.Domain.Catalog.CounterpartyKind.Both; - if (hasSupplier) return foodmarket.Domain.Catalog.CounterpartyKind.Supplier; - if (hasCustomer) return foodmarket.Domain.Catalog.CounterpartyKind.Customer; - return foodmarket.Domain.Catalog.CounterpartyKind.Unspecified; - } + => foodmarket.Domain.Catalog.CounterpartyKind.Unspecified; static foodmarket.Domain.Catalog.CounterpartyType ResolveType(string? companyType) => companyType switch diff --git a/src/food-market.web/src/lib/useLookups.ts b/src/food-market.web/src/lib/useLookups.ts index e978bbf..9d715f8 100644 --- a/src/food-market.web/src/lib/useLookups.ts +++ b/src/food-market.web/src/lib/useLookups.ts @@ -20,8 +20,8 @@ export const useCountries = () => useLookup('countries', '/api/catalog/ export const useCurrencies = () => useLookup('currencies', '/api/catalog/currencies') export const useStores = () => useLookup('stores', '/api/catalog/stores') export const usePriceTypes = () => useLookup('price-types', '/api/catalog/price-types') -export const useSuppliers = () => useQuery({ - queryKey: ['lookup:suppliers'], - queryFn: async () => (await api.get>('/api/catalog/counterparties?pageSize=500&kind=1')).data.items, - staleTime: 5 * 60 * 1000, -}) +// MoySklad-style: контрагент один, может быть и поставщиком, и покупателем +// в разных документах. Не фильтруем по Kind — пользователь сам выбирает. +export const useCounterparties = () => useLookup('counterparties', '/api/catalog/counterparties') +// Алиас для обратной совместимости со старым кодом форм Supply/RetailSale. +export const useSuppliers = useCounterparties diff --git a/src/food-market.web/src/pages/CounterpartiesPage.tsx b/src/food-market.web/src/pages/CounterpartiesPage.tsx index f2e2e19..dcf16ac 100644 --- a/src/food-market.web/src/pages/CounterpartiesPage.tsx +++ b/src/food-market.web/src/pages/CounterpartiesPage.tsx @@ -36,6 +36,8 @@ interface Form { } const blankForm: Form = { + // Kind по умолчанию Unspecified — MoySklad не имеет такого поля у контрагентов, + // не выдумываем за пользователя. Пусть выберет вручную если нужно. name: '', legalName: '', kind: CounterpartyKind.Unspecified, type: CounterpartyType.LegalEntity, bin: '', iin: '', taxNumber: '', countryId: '', address: '', phone: '', email: '',