diff --git a/client/package-lock.json b/client/package-lock.json
index 3efb283..ac1555d 100644
--- a/client/package-lock.json
+++ b/client/package-lock.json
@@ -119,7 +119,6 @@
"version": "7.29.7",
"dev": true,
"license": "MIT",
- "peer": true,
"dependencies": {
"@babel/code-frame": "^7.29.7",
"@babel/generator": "^7.29.7",
@@ -419,7 +418,6 @@
}
],
"license": "MIT",
- "peer": true,
"engines": {
"node": ">=18"
},
@@ -441,7 +439,6 @@
}
],
"license": "MIT",
- "peer": true,
"engines": {
"node": ">=18"
}
@@ -499,7 +496,6 @@
"node_modules/@dicebear/core": {
"version": "9.4.2",
"license": "MIT",
- "peer": true,
"dependencies": {
"@types/json-schema": "^7.0.15"
},
@@ -617,6 +613,29 @@
"@dicebear/core": "^9.0.0"
}
},
+ "node_modules/@emnapi/core": {
+ "version": "1.10.0",
+ "resolved": "https://registry.npmjs.org/@emnapi/core/-/core-1.10.0.tgz",
+ "integrity": "sha512-yq6OkJ4p82CAfPl0u9mQebQHKPJkY7WrIuk205cTYnYe+k2Z8YBh11FrbRG/H6ihirqcacOgl2BIO8oyMQLeXw==",
+ "dev": true,
+ "license": "MIT",
+ "optional": true,
+ "dependencies": {
+ "@emnapi/wasi-threads": "1.2.1",
+ "tslib": "^2.4.0"
+ }
+ },
+ "node_modules/@emnapi/runtime": {
+ "version": "1.10.0",
+ "resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.10.0.tgz",
+ "integrity": "sha512-ewvYlk86xUoGI0zQRNq/mC+16R1QeDlKQy21Ki3oSYXNgLb45GV1P6A0M+/s6nyCuNDqe5VpaY84BzXGwVbwFA==",
+ "dev": true,
+ "license": "MIT",
+ "optional": true,
+ "dependencies": {
+ "tslib": "^2.4.0"
+ }
+ },
"node_modules/@emnapi/wasi-threads": {
"version": "1.2.1",
"resolved": "https://registry.npmjs.org/@emnapi/wasi-threads/-/wasi-threads-1.2.1.tgz",
@@ -674,7 +693,6 @@
"node_modules/@emotion/react": {
"version": "11.14.0",
"license": "MIT",
- "peer": true,
"dependencies": {
"@babel/runtime": "^7.18.3",
"@emotion/babel-plugin": "^11.13.5",
@@ -712,7 +730,6 @@
"node_modules/@emotion/styled": {
"version": "11.14.1",
"license": "MIT",
- "peer": true,
"dependencies": {
"@babel/runtime": "^7.18.3",
"@emotion/babel-plugin": "^11.13.5",
@@ -1333,6 +1350,17 @@
"@floating-ui/utils": "^0.2.11"
}
},
+ "node_modules/@floating-ui/dom": {
+ "version": "1.7.6",
+ "resolved": "https://registry.npmjs.org/@floating-ui/dom/-/dom-1.7.6.tgz",
+ "integrity": "sha512-9gZSAI5XM36880PPMm//9dfiEngYoC6Am2izES1FF406YFsjvyBMmeJ2g4SAju3xWwtuynNRFL2s9hgxpLI5SQ==",
+ "license": "MIT",
+ "optional": true,
+ "dependencies": {
+ "@floating-ui/core": "^1.7.5",
+ "@floating-ui/utils": "^0.2.11"
+ }
+ },
"node_modules/@floating-ui/utils": {
"version": "0.2.11",
"license": "MIT",
@@ -1551,7 +1579,6 @@
"resolved": "https://registry.npmjs.org/@mui/material/-/material-9.0.1.tgz",
"integrity": "sha512-voyCpeUxcSWLN7KPZuq0pGCIt726T9K6kiVM3XUcywZDAlZSarLHaUxJVQpospbjjOzN53hwyjo8s6KoWl6utw==",
"license": "MIT",
- "peer": true,
"dependencies": {
"@babel/runtime": "^7.29.2",
"@mui/core-downloads-tracker": "^9.0.1",
@@ -2440,6 +2467,7 @@
"integrity": "sha512-b0P0sZPKtyu8HkeRAfCq0IfURZK+SuwMjY1UXGBU27wpAiTwQAIlq56IbIO+ytk/JjS1fMR14ee5WBBfKi5J6A==",
"dev": true,
"license": "Apache-2.0",
+ "peer": true,
"dependencies": {
"dequal": "^2.0.3"
}
@@ -2520,7 +2548,6 @@
"node_modules/@tiptap/core": {
"version": "3.23.6",
"license": "MIT",
- "peer": true,
"funding": {
"type": "github",
"url": "https://github.com/sponsors/ueberdosis"
@@ -2711,7 +2738,6 @@
"node_modules/@tiptap/extension-list": {
"version": "3.23.6",
"license": "MIT",
- "peer": true,
"funding": {
"type": "github",
"url": "https://github.com/sponsors/ueberdosis"
@@ -2812,7 +2838,6 @@
"node_modules/@tiptap/extensions": {
"version": "3.23.6",
"license": "MIT",
- "peer": true,
"funding": {
"type": "github",
"url": "https://github.com/sponsors/ueberdosis"
@@ -2825,7 +2850,6 @@
"node_modules/@tiptap/pm": {
"version": "3.23.6",
"license": "MIT",
- "peer": true,
"dependencies": {
"prosemirror-changeset": "^2.3.0",
"prosemirror-commands": "^1.6.2",
@@ -2918,7 +2942,8 @@
"node_modules/@types/aria-query": {
"version": "5.0.4",
"dev": true,
- "license": "MIT"
+ "license": "MIT",
+ "peer": true
},
"node_modules/@types/chai": {
"version": "5.2.3",
@@ -2951,7 +2976,6 @@
"version": "24.12.4",
"dev": true,
"license": "MIT",
- "peer": true,
"dependencies": {
"undici-types": "~7.16.0"
}
@@ -2967,7 +2991,6 @@
"node_modules/@types/react": {
"version": "19.2.15",
"license": "MIT",
- "peer": true,
"dependencies": {
"csstype": "^3.2.2"
}
@@ -2975,7 +2998,6 @@
"node_modules/@types/react-dom": {
"version": "19.2.3",
"license": "MIT",
- "peer": true,
"peerDependencies": {
"@types/react": "^19.2.0"
}
@@ -3002,7 +3024,6 @@
"version": "8.59.4",
"dev": true,
"license": "MIT",
- "peer": true,
"dependencies": {
"@typescript-eslint/scope-manager": "8.59.4",
"@typescript-eslint/types": "8.59.4",
@@ -3171,7 +3192,6 @@
"version": "8.59.4",
"dev": true,
"license": "MIT",
- "peer": true,
"dependencies": {
"@eslint-community/eslint-utils": "^4.9.1",
"@typescript-eslint/scope-manager": "8.59.4",
@@ -3684,7 +3704,6 @@
"version": "8.16.0",
"dev": true,
"license": "MIT",
- "peer": true,
"bin": {
"acorn": "bin/acorn"
},
@@ -3729,6 +3748,7 @@
"version": "5.0.1",
"dev": true,
"license": "MIT",
+ "peer": true,
"engines": {
"node": ">=8"
}
@@ -4839,6 +4859,7 @@
"version": "2.0.3",
"dev": true,
"license": "MIT",
+ "peer": true,
"engines": {
"node": ">=6"
}
@@ -4865,7 +4886,8 @@
"node_modules/dom-accessibility-api": {
"version": "0.5.16",
"dev": true,
- "license": "MIT"
+ "license": "MIT",
+ "peer": true
},
"node_modules/dom-helpers": {
"version": "5.2.1",
@@ -4904,7 +4926,6 @@
}
],
"license": "MIT",
- "peer": true,
"engines": {
"node": ">=11.0.0"
}
@@ -5130,7 +5151,6 @@
"dev": true,
"hasInstallScript": true,
"license": "MIT",
- "peer": true,
"bin": {
"esbuild": "bin/esbuild"
},
@@ -5190,7 +5210,6 @@
"integrity": "sha512-XoMjdBOwe/esVgEvLmNsD3IRHkm7fbKIUGvrleloJXUZgDHig2IPWNniv+GwjyJXzuNqVjlr5+4yVUZjycJwfQ==",
"dev": true,
"license": "MIT",
- "peer": true,
"dependencies": {
"@eslint-community/eslint-utils": "^4.8.0",
"@eslint-community/regexpp": "^4.12.1",
@@ -5249,7 +5268,6 @@
"version": "10.1.8",
"dev": true,
"license": "MIT",
- "peer": true,
"bin": {
"eslint-config-prettier": "bin/cli.js"
},
@@ -5381,7 +5399,6 @@
"version": "4.16.2",
"dev": true,
"license": "MIT",
- "peer": true,
"dependencies": {
"@package-json/types": "^0.0.12",
"@typescript-eslint/types": "^8.56.0",
@@ -7167,6 +7184,7 @@
"version": "1.5.0",
"dev": true,
"license": "MIT",
+ "peer": true,
"bin": {
"lz-string": "bin/bin.js"
}
@@ -7182,7 +7200,6 @@
"node_modules/maplibre-gl": {
"version": "5.24.0",
"license": "BSD-3-Clause",
- "peer": true,
"dependencies": {
"@mapbox/jsonlint-lines-primitives": "^2.0.2",
"@mapbox/point-geometry": "^1.1.0",
@@ -7740,7 +7757,6 @@
"version": "3.8.3",
"dev": true,
"license": "MIT",
- "peer": true,
"bin": {
"prettier": "bin/prettier.cjs"
},
@@ -7766,6 +7782,7 @@
"version": "27.5.1",
"dev": true,
"license": "MIT",
+ "peer": true,
"dependencies": {
"ansi-regex": "^5.0.1",
"ansi-styles": "^5.0.0",
@@ -7779,6 +7796,7 @@
"version": "5.2.0",
"dev": true,
"license": "MIT",
+ "peer": true,
"engines": {
"node": ">=10"
},
@@ -7789,7 +7807,8 @@
"node_modules/pretty-format/node_modules/react-is": {
"version": "17.0.2",
"dev": true,
- "license": "MIT"
+ "license": "MIT",
+ "peer": true
},
"node_modules/prop-types": {
"version": "15.8.1",
@@ -7935,7 +7954,6 @@
"node_modules/react": {
"version": "19.2.6",
"license": "MIT",
- "peer": true,
"engines": {
"node": ">=0.10.0"
}
@@ -7943,7 +7961,6 @@
"node_modules/react-dom": {
"version": "19.2.6",
"license": "MIT",
- "peer": true,
"dependencies": {
"scheduler": "^0.27.0"
},
@@ -9127,7 +9144,6 @@
"version": "4.0.4",
"dev": true,
"license": "MIT",
- "peer": true,
"engines": {
"node": ">=12"
},
@@ -9318,7 +9334,6 @@
"integrity": "sha512-y2TvuxSZPDyQakkFRPZHKFm+KKVqIisdg9/CZwm9ftvKXLP8NRWj38/ODjNbr43SsoXqNuAisEf1GdCxqWcdBw==",
"dev": true,
"license": "Apache-2.0",
- "peer": true,
"bin": {
"tsc": "bin/tsc",
"tsserver": "bin/tsserver"
@@ -9530,7 +9545,6 @@
"version": "8.0.14",
"dev": true,
"license": "MIT",
- "peer": true,
"dependencies": {
"lightningcss": "^1.32.0",
"picomatch": "^4.0.4",
@@ -9644,7 +9658,6 @@
"version": "4.0.4",
"dev": true,
"license": "MIT",
- "peer": true,
"engines": {
"node": ">=12"
},
@@ -9884,7 +9897,6 @@
"version": "4.0.4",
"dev": true,
"license": "MIT",
- "peer": true,
"engines": {
"node": ">=12"
},
@@ -9896,7 +9908,6 @@
"version": "7.3.3",
"dev": true,
"license": "MIT",
- "peer": true,
"dependencies": {
"esbuild": "^0.27.0",
"fdir": "^6.5.0",
@@ -10198,7 +10209,6 @@
"integrity": "sha512-ytENFjIJFl2UwYglde2jchW2Hwm4GJFLDiSXWdTrJQBIN9Fcyp7n4DhxJEiWNAJMV1/BqWfW/kkg71UDcHJyTQ==",
"dev": true,
"license": "MIT",
- "peer": true,
"funding": {
"url": "https://github.com/sponsors/colinhacks"
}
diff --git a/client/src/features/product-form/ui/GalleryImagePicker.tsx b/client/src/features/product-form/ui/GalleryImagePicker.tsx
index 572a089..9fee2fe 100644
--- a/client/src/features/product-form/ui/GalleryImagePicker.tsx
+++ b/client/src/features/product-form/ui/GalleryImagePicker.tsx
@@ -59,7 +59,7 @@ export function GalleryImagePicker({
return (
+ >
+ )
+}
+
+export function AdminSliderPage() {
+ const sliderQuery = useQuery({
+ queryKey: ['admin', 'catalog-slider'],
+ queryFn: fetchAdminCatalogSlider,
+ })
+
+ const galleryQuery = useQuery({
+ queryKey: ['admin', 'gallery'],
+ queryFn: fetchAdminGallery,
+ })
+
+ const galleryItems: GalleryImageItem[] = galleryQuery.data?.items ?? []
+
+ const initialSlides = useMemo(() => {
+ if (!sliderQuery.isSuccess) return []
+ return sliderQuery.data.slides.map((s) => ({
+ galleryImageId: s.galleryImageId,
+ caption: s.caption,
+ textColor: s.textColor || '#ffffff',
+ }))
+ }, [sliderQuery.isSuccess, sliderQuery.data?.slides])
+
+ if (sliderQuery.isLoading || galleryQuery.isLoading) {
+ return Загрузка…
+ }
+
+ if (sliderQuery.isError) {
+ return Не удалось загрузить слайдер.
+ }
+
+ return (
+
+
+ Слайдер
+
+
+ Изображения для карусели на главной странице. Сначала загрузите фото в Галерею и обработайте их (Resize), затем
+ добавьте в слайдер. Порядок строк = порядок показа.
+
+
+
)
}
diff --git a/client/src/pages/auth/ui/AuthPage.tsx b/client/src/pages/auth/ui/AuthPage.tsx
index 73d2221..d7b679a 100644
--- a/client/src/pages/auth/ui/AuthPage.tsx
+++ b/client/src/pages/auth/ui/AuthPage.tsx
@@ -13,12 +13,24 @@ import { AuthForgotForm } from '@/features/auth-forgot'
import { OAuthButtons } from '@/features/auth-oauth'
import { AuthPasswordForm } from '@/features/auth-password'
import { $user } from '@/shared/model/auth'
-import { useThemeController } from '@/app/providers/theme-controller'
+import type { ColorScheme } from '@/shared/model/theme'
import { BearLogo } from '@/shared/ui/BearLogo'
+function readStoredScheme(): ColorScheme {
+ try {
+ const raw = localStorage.getItem('craftshop_theme')
+ if (!raw) return 'craft'
+ const parsed = JSON.parse(raw)
+ const scheme = parsed?.scheme
+ return scheme === 'forest' || scheme === 'ocean' || scheme === 'berry' ? scheme : 'craft'
+ } catch {
+ return 'craft'
+ }
+}
+
export function AuthPage() {
const theme = useTheme()
- const { scheme } = useThemeController()
+ const scheme = readStoredScheme()
const [message, setMessage] = useState(null)
const [oauthError, setOauthError] = useState(null)
const [tab, setTab] = useState(0)
@@ -40,7 +52,7 @@ export function AuthPage() {
setSearchParams({}, { replace: true })
}, 0)
return () => clearTimeout(timeoutId)
- }, [])
+ }, [searchParams, setSearchParams])
if (showForgot) {
return (