feat(products): implement professional product management experience

Products dashboard (real total/published/drafts/out-of-stock/hidden/missing-images/missing-SEO/low-quality counts, recently-edited list, recommended next action); list gains table/grid view toggle, density, saved column visibility and saved sort (persisted via LocalStorageService), plus real bulk assign-category/assign-tags/duplicate/CSV-export alongside existing publish/hide/delete; per-row and per-editor reusable ProductHealthWidget (images/SEO/price/category/description/inventory checklist + completion %); editor reorganized into General/Media/Pricing/Inventory/Categories/Attributes/SEO/Visibility/Advanced tabs, media now uses the shared MediaPickerComponent/ImageFieldComponent (primary image + reorderable gallery) instead of raw URL textareas, specifications/attributes/variants moved off pipe-delimited textareas onto the shared KeyValueEditorComponent, SEO tab explains fields in plain language with a live search-result preview, inventory relabeled in business language, toggles/badges use the shared Toggle/Badge components. Filled in the adminProducts i18n namespace (previously ~98% missing, rendering raw translation keys) across en/ru/hy.
This commit is contained in:
sdarbinyan
2026-07-18 16:34:06 +04:00
parent 5d52d81c7d
commit aeb48504c5
19 changed files with 1561 additions and 212 deletions

View File

@@ -1232,6 +1232,141 @@ export interface Translations {
adminProducts: {
emptyTitle: string;
emptyDescription: string;
emptyGuide: string;
search: string;
category: string;
allCategories: string;
visibility: string;
allVisibility: string;
visible: string;
hidden: string;
stockStatus: string;
allStock: string;
inStock: string;
lowStock: string;
outOfStock: string;
sortTitle: string;
sortPrice: string;
sortPriority: string;
sortStock: string;
sortUpdated: string;
showArchived: string;
infiniteScroll: string;
viewMode: string;
viewTable: string;
viewGrid: string;
density: string;
densityComfortable: string;
densityCompact: string;
columns: string;
column_sku: string;
column_brand: string;
column_price: string;
column_stock: string;
column_visibility: string;
column_updated: string;
create: string;
edit: string;
duplicate: string;
selectedCount: string;
bulkShow: string;
bulkHide: string;
bulkAssignCategory: string;
bulkAssignTags: string;
bulkDuplicateAction: string;
bulkExportAction: string;
bulkDelete: string;
tagsPlaceholder: string;
name: string;
brand: string;
healthColumn: string;
actions: string;
archive: string;
delete: string;
items: string;
loadMore: string;
noImage: string;
slug: string;
barcode: string;
priority: string;
shortDescription: string;
translations: string;
primaryImage: string;
primaryImageHint: string;
gallery: string;
galleryHint: string;
moveLeft: string;
moveRight: string;
videos: string;
discount: string;
currency: string;
stockQuantity: string;
stockQuantityHint: string;
availabilityStatus: string;
availabilityStatusHint: string;
availabilityNote: string;
availabilityNoteHint: string;
reservedNote: string;
relatedProducts: string;
specifications: string;
attributes: string;
addRow: string;
removeRow: string;
rowKey: string;
rowValue: string;
addVariant: string;
variantName: string;
variantsHint: string;
seoExplain: string;
searchTitle: string;
searchTitleHint: string;
searchDescription: string;
searchDescriptionHint: string;
seoMissingTitle: string;
seoMissingDescription: string;
keywords: string;
featured: string;
recommended: string;
new: string;
bestseller: string;
badges: string;
htmlDescription: string;
customer: string;
reviewsReadonly: string;
noReviews: string;
questionsReadonly: string;
noQuestions: string;
save: string;
groupGeneral: string;
groupMedia: string;
groupPricing: string;
groupInventory: string;
groupCategories: string;
groupAttributes: string;
groupSeo: string;
groupVisibility: string;
groupAdvanced: string;
healthImages: string;
healthSeo: string;
healthPrice: string;
healthCategory: string;
healthDescription: string;
healthInventory: string;
totalProducts: string;
publishedCount: string;
draftsCount: string;
outOfStockCount: string;
hiddenCount: string;
missingImagesCount: string;
missingSeoCount: string;
lowQualityCount: string;
recentlyEdited: string;
recommendedNext: string;
openAction: string;
recommendAddImages: string;
recommendAddSeo: string;
recommendRestock: string;
recommendNone: string;
};
adminUsers: {
emptyTitle: string;