core-maugli 1.2.10 → 1.2.11
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +4 -3
- package/public/blackbox-1200.webp +0 -0
- package/public/blackbox-400.webp +0 -0
- package/public/blackbox-800.webp +0 -0
- package/public/img/default/autor_default-1200.webp +0 -0
- package/public/img/default/autor_default-400.webp +0 -0
- package/public/img/default/autor_default-800.webp +0 -0
- package/public/img/default/blog_default-1200.webp +0 -0
- package/public/img/default/blog_default-400.webp +0 -0
- package/public/img/default/blog_default-800.webp +0 -0
- package/public/img/default/default-1200.webp +0 -0
- package/public/img/default/default-400.webp +0 -0
- package/public/img/default/default-800.webp +0 -0
- package/public/img/default/previews/autor_default-1200.webp +0 -0
- package/public/img/default/previews/autor_default-400.webp +0 -0
- package/public/img/default/previews/autor_default-800.webp +0 -0
- package/public/img/default/previews/blog_default-1200.webp +0 -0
- package/public/img/default/previews/blog_default-400.webp +0 -0
- package/public/img/default/previews/blog_default-800.webp +0 -0
- package/public/img/default/previews/default-1200.webp +0 -0
- package/public/img/default/previews/default-400.webp +0 -0
- package/public/img/default/previews/default-800.webp +0 -0
- package/public/img/default/previews/product_default-1200.webp +0 -0
- package/public/img/default/previews/product_default-400.webp +0 -0
- package/public/img/default/previews/product_default-800.webp +0 -0
- package/public/img/default/previews/project_default-1200.webp +0 -0
- package/public/img/default/previews/project_default-400.webp +0 -0
- package/public/img/default/previews/project_default-800.webp +0 -0
- package/public/img/default/previews/rubric_default-1200.webp +0 -0
- package/public/img/default/previews/rubric_default-400.webp +0 -0
- package/public/img/default/previews/rubric_default-800.webp +0 -0
- package/public/img/default/previews/test-1200.webp +0 -0
- package/public/img/default/previews/test-400.webp +0 -0
- package/public/img/default/previews/test-800.webp +0 -0
- package/public/img/default/previews/test2-1200.webp +0 -0
- package/public/img/default/previews/test2-400.webp +0 -0
- package/public/img/default/previews/test2-800.webp +0 -0
- package/public/img/default/product_default-1200.webp +0 -0
- package/public/img/default/product_default-400.webp +0 -0
- package/public/img/default/product_default-800.webp +0 -0
- package/public/img/default/project_default-1200.webp +0 -0
- package/public/img/default/project_default-400.webp +0 -0
- package/public/img/default/project_default-800.webp +0 -0
- package/public/img/default/rubric_default-1200.webp +0 -0
- package/public/img/default/rubric_default-400.webp +0 -0
- package/public/img/default/rubric_default-800.webp +0 -0
- package/public/img/default/rubric_default.webp +0 -0
- package/public/img/default/test-1200.webp +0 -0
- package/public/img/default/test-400.webp +0 -0
- package/public/img/default/test-800.webp +0 -0
- package/public/img/default/test2-1200.webp +0 -0
- package/public/img/default/test2-400.webp +0 -0
- package/public/img/default/test2-800.webp +0 -0
- package/public/img/examples/authors/anna-1200.webp +0 -0
- package/public/img/examples/authors/anna-400.webp +0 -0
- package/public/img/examples/authors/anna-800.webp +0 -0
- package/public/img/examples/authors/carlos-1200.webp +0 -0
- package/public/img/examples/authors/carlos-400.webp +0 -0
- package/public/img/examples/authors/carlos-800.webp +0 -0
- package/public/img/examples/authors/daria-1200.webp +0 -0
- package/public/img/examples/authors/daria-400.webp +0 -0
- package/public/img/examples/authors/daria-800.webp +0 -0
- package/public/img/examples/authors/dmitry-1200.webp +0 -0
- package/public/img/examples/authors/dmitry-400.webp +0 -0
- package/public/img/examples/authors/dmitry-800.webp +0 -0
- package/public/img/examples/authors/igor-1200.webp +0 -0
- package/public/img/examples/authors/igor-400.webp +0 -0
- package/public/img/examples/authors/igor-800.webp +0 -0
- package/public/img/examples/authors/john-1200.webp +0 -0
- package/public/img/examples/authors/john-400.webp +0 -0
- package/public/img/examples/authors/john-800.webp +0 -0
- package/public/img/examples/blog/post-1-avtomatizaciya-marketinga-kak-ii-osvobozhdaet-predprinimatelei-ot-cifrovogo-rabstva-1200.webp +0 -0
- package/public/img/examples/blog/post-1-avtomatizaciya-marketinga-kak-ii-osvobozhdaet-predprinimatelei-ot-cifrovogo-rabstva-400.webp +0 -0
- package/public/img/examples/blog/post-1-avtomatizaciya-marketinga-kak-ii-osvobozhdaet-predprinimatelei-ot-cifrovogo-rabstva-800.webp +0 -0
- package/public/img/examples/blog/post-2-avtomatizaciya-kontenta-kak-neiroseti-ubivayut-perfekcionizm-v-biznese-1200.webp +0 -0
- package/public/img/examples/blog/post-2-avtomatizaciya-kontenta-kak-neiroseti-ubivayut-perfekcionizm-v-biznese-400.webp +0 -0
- package/public/img/examples/blog/post-2-avtomatizaciya-kontenta-kak-neiroseti-ubivayut-perfekcionizm-v-biznese-800.webp +0 -0
- package/public/img/examples/blog/post-3-laik-ne-valyuta-kak-avtomatizaciya-marketinga-spasaet-ot-lozhnyh-metrik-1200.webp +0 -0
- package/public/img/examples/blog/post-3-laik-ne-valyuta-kak-avtomatizaciya-marketinga-spasaet-ot-lozhnyh-metrik-400.webp +0 -0
- package/public/img/examples/blog/post-3-laik-ne-valyuta-kak-avtomatizaciya-marketinga-spasaet-ot-lozhnyh-metrik-800.webp +0 -0
- package/public/img/examples/blog/post-5-5-fatalnyh-oshibok-marketinga-kotorye-ubivayut-startapy-na-starte-1200.webp +0 -0
- package/public/img/examples/blog/post-5-5-fatalnyh-oshibok-marketinga-kotorye-ubivayut-startapy-na-starte-400.webp +0 -0
- package/public/img/examples/blog/post-5-5-fatalnyh-oshibok-marketinga-kotorye-ubivayut-startapy-na-starte-800.webp +0 -0
- package/public/img/examples/blog/post-6-5-strategii-kontent-marketinga-dlya-startapov-avtomatizaciya-i-revolyuciya-1200.webp +0 -0
- package/public/img/examples/blog/post-6-5-strategii-kontent-marketinga-dlya-startapov-avtomatizaciya-i-revolyuciya-400.webp +0 -0
- package/public/img/examples/blog/post-6-5-strategii-kontent-marketinga-dlya-startapov-avtomatizaciya-i-revolyuciya-800.webp +0 -0
- package/public/img/examples/blog/post-7-viralnyi-kontent-ne-udacha-a-strategiya-avtomatizaciya-marketinga-1200.webp +0 -0
- package/public/img/examples/blog/post-7-viralnyi-kontent-ne-udacha-a-strategiya-avtomatizaciya-marketinga-400.webp +0 -0
- package/public/img/examples/blog/post-7-viralnyi-kontent-ne-udacha-a-strategiya-avtomatizaciya-marketinga-800.webp +0 -0
- package/public/img/examples/blog/post-agent-experience-mcp-biznes-v-epohu-ii-agentov-1200.webp +0 -0
- package/public/img/examples/blog/post-agent-experience-mcp-biznes-v-epohu-ii-agentov-400.webp +0 -0
- package/public/img/examples/blog/post-agent-experience-mcp-biznes-v-epohu-ii-agentov-800.webp +0 -0
- package/public/img/examples/blog/post_11-1200.webp +0 -0
- package/public/img/examples/blog/post_11-400.webp +0 -0
- package/public/img/examples/blog/post_11-800.webp +0 -0
- package/public/img/examples/blog/post_12-1200.webp +0 -0
- package/public/img/examples/blog/post_12-400.webp +0 -0
- package/public/img/examples/blog/post_12-800.webp +0 -0
- package/public/img/examples/blog/post_1_jsonld_guide-1200.webp +0 -0
- package/public/img/examples/blog/post_1_jsonld_guide-400.webp +0 -0
- package/public/img/examples/blog/post_1_jsonld_guide-800.webp +0 -0
- package/public/img/examples/blog/previews/post-1-avtomatizaciya-marketinga-kak-ii-osvobozhdaet-predprinimatelei-ot-cifrovogo-rabstva-1200.webp +0 -0
- package/public/img/examples/blog/previews/post-1-avtomatizaciya-marketinga-kak-ii-osvobozhdaet-predprinimatelei-ot-cifrovogo-rabstva-400.webp +0 -0
- package/public/img/examples/blog/previews/post-1-avtomatizaciya-marketinga-kak-ii-osvobozhdaet-predprinimatelei-ot-cifrovogo-rabstva-800.webp +0 -0
- package/public/img/examples/blog/previews/post-2-avtomatizaciya-kontenta-kak-neiroseti-ubivayut-perfekcionizm-v-biznese-1200.webp +0 -0
- package/public/img/examples/blog/previews/post-2-avtomatizaciya-kontenta-kak-neiroseti-ubivayut-perfekcionizm-v-biznese-400.webp +0 -0
- package/public/img/examples/blog/previews/post-2-avtomatizaciya-kontenta-kak-neiroseti-ubivayut-perfekcionizm-v-biznese-800.webp +0 -0
- package/public/img/examples/blog/previews/post-3-laik-ne-valyuta-kak-avtomatizaciya-marketinga-spasaet-ot-lozhnyh-metrik-1200.webp +0 -0
- package/public/img/examples/blog/previews/post-3-laik-ne-valyuta-kak-avtomatizaciya-marketinga-spasaet-ot-lozhnyh-metrik-400.webp +0 -0
- package/public/img/examples/blog/previews/post-3-laik-ne-valyuta-kak-avtomatizaciya-marketinga-spasaet-ot-lozhnyh-metrik-800.webp +0 -0
- package/public/img/examples/blog/previews/post-5-5-fatalnyh-oshibok-marketinga-kotorye-ubivayut-startapy-na-starte-1200.webp +0 -0
- package/public/img/examples/blog/previews/post-5-5-fatalnyh-oshibok-marketinga-kotorye-ubivayut-startapy-na-starte-400.webp +0 -0
- package/public/img/examples/blog/previews/post-5-5-fatalnyh-oshibok-marketinga-kotorye-ubivayut-startapy-na-starte-800.webp +0 -0
- package/public/img/examples/blog/previews/post-6-5-strategii-kontent-marketinga-dlya-startapov-avtomatizaciya-i-revolyuciya-1200.webp +0 -0
- package/public/img/examples/blog/previews/post-6-5-strategii-kontent-marketinga-dlya-startapov-avtomatizaciya-i-revolyuciya-400.webp +0 -0
- package/public/img/examples/blog/previews/post-6-5-strategii-kontent-marketinga-dlya-startapov-avtomatizaciya-i-revolyuciya-800.webp +0 -0
- package/public/img/examples/blog/previews/post-7-viralnyi-kontent-ne-udacha-a-strategiya-avtomatizaciya-marketinga-1200.webp +0 -0
- package/public/img/examples/blog/previews/post-7-viralnyi-kontent-ne-udacha-a-strategiya-avtomatizaciya-marketinga-400.webp +0 -0
- package/public/img/examples/blog/previews/post-7-viralnyi-kontent-ne-udacha-a-strategiya-avtomatizaciya-marketinga-800.webp +0 -0
- package/public/img/examples/blog/previews/post-agent-experience-mcp-biznes-v-epohu-ii-agentov-1200.webp +0 -0
- package/public/img/examples/blog/previews/post-agent-experience-mcp-biznes-v-epohu-ii-agentov-400.webp +0 -0
- package/public/img/examples/blog/previews/post-agent-experience-mcp-biznes-v-epohu-ii-agentov-800.webp +0 -0
- package/public/img/examples/blog/previews/post_11-1200.webp +0 -0
- package/public/img/examples/blog/previews/post_11-400.webp +0 -0
- package/public/img/examples/blog/previews/post_11-800.webp +0 -0
- package/public/img/examples/blog/previews/post_12-1200.webp +0 -0
- package/public/img/examples/blog/previews/post_12-400.webp +0 -0
- package/public/img/examples/blog/previews/post_12-800.webp +0 -0
- package/public/img/examples/blog/previews/post_1_jsonld_guide-1200.webp +0 -0
- package/public/img/examples/blog/previews/post_1_jsonld_guide-400.webp +0 -0
- package/public/img/examples/blog/previews/post_1_jsonld_guide-800.webp +0 -0
- package/public/img/examples/blog/previews/test-post-1200.webp +0 -0
- package/public/img/examples/blog/previews/test-post-400.webp +0 -0
- package/public/img/examples/blog/previews/test-post-800.webp +0 -0
- package/public/img/examples/blog/test-post-1200.webp +0 -0
- package/public/img/examples/blog/test-post-400.webp +0 -0
- package/public/img/examples/blog/test-post-800.webp +0 -0
- package/public/img/examples/products/previews/product_1-1200.webp +0 -0
- package/public/img/examples/products/previews/product_1-400.webp +0 -0
- package/public/img/examples/products/previews/product_1-800.webp +0 -0
- package/public/img/examples/products/previews/product_2-1200.webp +0 -0
- package/public/img/examples/products/previews/product_2-400.webp +0 -0
- package/public/img/examples/products/previews/product_2-800.webp +0 -0
- package/public/img/examples/products/product_1-1200.webp +0 -0
- package/public/img/examples/products/product_1-400.webp +0 -0
- package/public/img/examples/products/product_1-800.webp +0 -0
- package/public/img/examples/products/product_2-1200.webp +0 -0
- package/public/img/examples/products/product_2-400.webp +0 -0
- package/public/img/examples/products/product_2-800.webp +0 -0
- package/public/img/examples/projects/previews/project_1-1200.webp +0 -0
- package/public/img/examples/projects/previews/project_1-400.webp +0 -0
- package/public/img/examples/projects/previews/project_1-800.webp +0 -0
- package/public/img/examples/projects/previews/project_2-1200.webp +0 -0
- package/public/img/examples/projects/previews/project_2-400.webp +0 -0
- package/public/img/examples/projects/previews/project_2-800.webp +0 -0
- package/public/img/examples/projects/project_1-1200.webp +0 -0
- package/public/img/examples/projects/project_1-400.webp +0 -0
- package/public/img/examples/projects/project_1-800.webp +0 -0
- package/public/img/examples/projects/project_2-1200.webp +0 -0
- package/public/img/examples/projects/project_2-400.webp +0 -0
- package/public/img/examples/projects/project_2-800.webp +0 -0
- package/public/img/page-images/blog_default-1200.webp +0 -0
- package/public/img/page-images/blog_default-400.webp +0 -0
- package/public/img/page-images/blog_default-800.webp +0 -0
- package/scripts/generate-previews.js +22 -14
- package/src/components/RubricCard.astro +78 -5
- package/src/content/tags/ai-business.mdx +1 -3
- package/src/content/tags/automation.mdx +1 -3
- package/src/content/tags/content-strategy.mdx +1 -3
package/package.json
CHANGED
@@ -2,7 +2,7 @@
|
|
2
2
|
"name": "core-maugli",
|
3
3
|
"description": "Astro & Tailwind CSS blog theme for Maugli.",
|
4
4
|
"type": "module",
|
5
|
-
"version": "1.2.
|
5
|
+
"version": "1.2.11",
|
6
6
|
"license": "GPL-3.0-or-later OR Commercial",
|
7
7
|
"repository": {
|
8
8
|
"type": "git",
|
@@ -19,9 +19,10 @@
|
|
19
19
|
],
|
20
20
|
"scripts": {
|
21
21
|
"typograf": "node typograf-batch.js",
|
22
|
-
"dev": "astro dev",
|
22
|
+
"dev": "node resize-all.cjs && node scripts/generate-previews.js && astro dev",
|
23
|
+
"prestart": "node resize-all.cjs && node scripts/generate-previews.js",
|
23
24
|
"start": "astro dev",
|
24
|
-
"build": "node typograf-batch.js && node scripts/verify-assets.js && node scripts/generate-previews.js && astro build",
|
25
|
+
"build": "node resize-all.cjs && node typograf-batch.js && node scripts/verify-assets.js && node scripts/generate-previews.js && astro build",
|
25
26
|
"test": "node tests/examplesFilter.test.ts",
|
26
27
|
"astro": "astro",
|
27
28
|
"featured:add": "node scripts/featured.js add",
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
package/public/img/examples/blog/post-agent-experience-mcp-biznes-v-epohu-ii-agentov-1200.webp
ADDED
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
@@ -103,6 +103,8 @@ function extractImagePaths() {
|
|
103
103
|
const items = fs.readdirSync(defaultDir);
|
104
104
|
for (const item of items) {
|
105
105
|
if (item.match(/\.(webp|jpg|jpeg|png)$/i)) {
|
106
|
+
// Исключаем изображения авторов и рубрик
|
107
|
+
if (item.includes('autor') || item.includes('author') || item.includes('rubric')) continue;
|
106
108
|
imagePaths.add(`/img/default/${item}`);
|
107
109
|
}
|
108
110
|
}
|
@@ -141,42 +143,44 @@ function cleanupExistingPreviews() {
|
|
141
143
|
// Функция для создания превьюшки
|
142
144
|
async function createPreview(imagePath) {
|
143
145
|
const fullImagePath = path.join(rootDir, 'public', imagePath.replace(/^\//, ''));
|
144
|
-
|
146
|
+
|
145
147
|
if (!fs.existsSync(fullImagePath)) {
|
146
148
|
console.warn(`Image not found: ${fullImagePath}`);
|
147
149
|
return;
|
148
150
|
}
|
149
|
-
|
151
|
+
|
150
152
|
const dir = path.dirname(fullImagePath);
|
151
153
|
const ext = path.extname(fullImagePath);
|
152
154
|
const name = path.basename(fullImagePath, ext);
|
153
155
|
const previewPath = path.join(dir, 'previews', `${name}${ext}`);
|
154
|
-
|
156
|
+
|
155
157
|
// Определяем размер превью в зависимости от типа изображения
|
156
158
|
let previewWidth, previewHeight;
|
157
159
|
if (imagePath.includes('/img/default/') && (name.includes('rubric') || name.includes('tag'))) {
|
158
|
-
// Для изображений рубрик используем меньший размер
|
159
160
|
previewWidth = rubricPreviewWidth;
|
160
161
|
previewHeight = rubricPreviewHeight;
|
161
162
|
console.log(`Creating rubric preview (${previewWidth}x${previewHeight}): ${name}`);
|
162
163
|
} else {
|
163
|
-
// Для блог-постов и других изображений используем стандартный размер
|
164
164
|
previewWidth = blogPreviewWidth;
|
165
165
|
previewHeight = blogPreviewHeight;
|
166
166
|
console.log(`Creating blog preview (${previewWidth}x${previewHeight}): ${name}`);
|
167
167
|
}
|
168
|
-
|
168
|
+
|
169
169
|
// Создаем папку previews если её нет
|
170
170
|
const previewDir = path.dirname(previewPath);
|
171
171
|
if (!fs.existsSync(previewDir)) {
|
172
172
|
fs.mkdirSync(previewDir, { recursive: true });
|
173
173
|
}
|
174
|
-
|
174
|
+
|
175
|
+
// Если превью уже существует — пропускаем генерацию
|
176
|
+
if (fs.existsSync(previewPath)) {
|
177
|
+
// console.log(`Preview already exists: ${previewPath}`);
|
178
|
+
return;
|
179
|
+
}
|
175
180
|
try {
|
176
181
|
await sharp(fullImagePath)
|
177
182
|
.resize(previewWidth, previewHeight, { fit: 'cover' })
|
178
183
|
.toFile(previewPath);
|
179
|
-
|
180
184
|
console.log(`Preview created: ${previewPath}`);
|
181
185
|
} catch (error) {
|
182
186
|
console.error(`Error processing ${fullImagePath}:`, error.message);
|
@@ -185,18 +189,22 @@ async function createPreview(imagePath) {
|
|
185
189
|
|
186
190
|
// Основная функция
|
187
191
|
async function generatePreviews() {
|
188
|
-
|
189
|
-
|
190
|
-
|
192
|
+
// Очистка превью только если явно указано (например, через переменную)
|
193
|
+
const CLEAN_PREVIEWS = process.env.CLEAN_PREVIEWS === '1';
|
194
|
+
if (CLEAN_PREVIEWS) {
|
195
|
+
console.log('Cleaning up existing previews...');
|
196
|
+
cleanupExistingPreviews();
|
197
|
+
}
|
198
|
+
|
191
199
|
console.log('Scanning content for images...');
|
192
200
|
const imagePaths = extractImagePaths();
|
193
|
-
|
201
|
+
|
194
202
|
console.log(`Found ${imagePaths.length} images to process`);
|
195
|
-
|
203
|
+
|
196
204
|
for (const imagePath of imagePaths) {
|
197
205
|
await createPreview(imagePath);
|
198
206
|
}
|
199
|
-
|
207
|
+
|
200
208
|
console.log('Preview generation completed!');
|
201
209
|
}
|
202
210
|
|
@@ -112,14 +112,77 @@ function getPreviewImageSrc(imageSrc: string): string {
|
|
112
112
|
return absolutePreviewPath;
|
113
113
|
}
|
114
114
|
|
115
|
-
|
116
|
-
const previewImageSrc =
|
115
|
+
// Всегда используем дефолтное изображение для рубрик
|
116
|
+
const previewImageSrc = '/img/default/previews/rubric_default.webp';
|
117
|
+
|
118
|
+
// Список стоп-слов (предлоги, союзы, знаки)
|
119
|
+
const stopWords = [
|
120
|
+
'и',
|
121
|
+
'в',
|
122
|
+
'на',
|
123
|
+
'с',
|
124
|
+
'по',
|
125
|
+
'от',
|
126
|
+
'до',
|
127
|
+
'за',
|
128
|
+
'над',
|
129
|
+
'под',
|
130
|
+
'о',
|
131
|
+
'об',
|
132
|
+
'у',
|
133
|
+
'для',
|
134
|
+
'к',
|
135
|
+
'ко',
|
136
|
+
'из',
|
137
|
+
'без',
|
138
|
+
'при',
|
139
|
+
'а',
|
140
|
+
'но',
|
141
|
+
'или',
|
142
|
+
'да',
|
143
|
+
'же',
|
144
|
+
'ли',
|
145
|
+
'бы',
|
146
|
+
'не',
|
147
|
+
'то',
|
148
|
+
'же',
|
149
|
+
'the',
|
150
|
+
'of',
|
151
|
+
'to',
|
152
|
+
'in',
|
153
|
+
'on',
|
154
|
+
'at',
|
155
|
+
'by',
|
156
|
+
'for',
|
157
|
+
'with',
|
158
|
+
'from',
|
159
|
+
'as',
|
160
|
+
'an',
|
161
|
+
'or',
|
162
|
+
'but',
|
163
|
+
'&'
|
164
|
+
];
|
165
|
+
|
166
|
+
function getRubricInitials(title: string): string {
|
167
|
+
if (!title) return '';
|
168
|
+
// Удаляем лишние символы
|
169
|
+
const clean = title.replace(/[^\wа-яА-ЯёЁ\s]/gi, ' ');
|
170
|
+
const words = clean.split(/\s+/).filter(Boolean);
|
171
|
+
// Берём первые буквы каждого слова, кроме стоп-слов
|
172
|
+
const initials = words
|
173
|
+
.filter((word) => !stopWords.includes(word.toLowerCase()))
|
174
|
+
.slice(0, 2)
|
175
|
+
.map((word) => word[0]?.toUpperCase() || '')
|
176
|
+
.join('');
|
177
|
+
return initials;
|
178
|
+
}
|
179
|
+
|
180
|
+
const rubricInitials = getRubricInitials(title);
|
117
181
|
|
118
182
|
// Debug информация только в development режиме
|
119
183
|
if (import.meta.env.DEV) {
|
120
184
|
console.log('RubricCard Debug:', {
|
121
185
|
title,
|
122
|
-
originalImageSrc: imageSrc,
|
123
186
|
previewImageSrc,
|
124
187
|
defaultRubricImage: maugliConfig.defaultRubricImage
|
125
188
|
});
|
@@ -131,8 +194,18 @@ if (import.meta.env.DEV) {
|
|
131
194
|
class={`w-full h-[195px] border border-[var(--border-main)] rounded-custom card-bg hover:card-shadow hover:-translate-y-1 transition-all duration-300 p-6 flex flex-row gap-4 items-start ${className}`}
|
132
195
|
>
|
133
196
|
<!-- Левая часть: картинка и дата -->
|
134
|
-
<div class="flex flex-col items-end gap-2 w-[105px] h-[147px]">
|
135
|
-
<img src={previewImageSrc} alt={
|
197
|
+
<div class="flex flex-col items-end gap-2 w-[105px] h-[147px] relative">
|
198
|
+
<img src={previewImageSrc} alt={title} class="w-[105px] h-[107px] object-cover rounded-custom" loading="lazy" />
|
199
|
+
{
|
200
|
+
rubricInitials && (
|
201
|
+
<span style="position:absolute;left:0;top:0;width:105px;height:107px;display:flex;align-items:center;justify-content:center;pointer-events:none;z-index:2;">
|
202
|
+
<span style="position:absolute;left:0;top:0;width:105px;height:107px;background:rgba(0,0,0,0.10);border-radius:inherit;z-index:1;" />
|
203
|
+
<span style="position:relative;z-index:2;font-size:48px;font-weight:700;font-family:inherit;color:var(--brand-color);letter-spacing:2px;">
|
204
|
+
{rubricInitials}
|
205
|
+
</span>
|
206
|
+
</span>
|
207
|
+
)
|
208
|
+
}
|
136
209
|
<div class="flex flex-col items-end gap-1 w-[74px] h-[32px]">
|
137
210
|
<span class={`flex items-center gap-1 text-[12px] text-right ${isBrandDate ? 'text-[var(--brand-color)]' : 'text-[var(--text-muted)]'}`}>
|
138
211
|
<svg
|
@@ -1,9 +1,7 @@
|
|
1
1
|
---
|
2
2
|
title: AI в бизнесе
|
3
3
|
description: "Обзоры технологий (LLM, GPT, Claude и др.). Кейсы применения AI в бизнесе. Тренды в автоматизации контента."
|
4
|
-
|
5
|
-
src: '/img/default/rubric_default.webp'
|
6
|
-
alt: AI в бизнесе
|
4
|
+
|
7
5
|
isRubric: true
|
8
6
|
isFeatured: false
|
9
7
|
jsonld:
|
@@ -1,9 +1,7 @@
|
|
1
1
|
---
|
2
2
|
title: Автоматизация бизнеса
|
3
3
|
description: "Workflow и интеграции (Airtable, Supabase, автопостинг). AI-редакторы и сценарии. «Редакция без людей» — практика и инструменты."
|
4
|
-
|
5
|
-
src: '/img/default/rubric_default.webp'
|
6
|
-
alt: Автоматизация бизнеса
|
4
|
+
|
7
5
|
isRubric: true
|
8
6
|
isFeatured: false
|
9
7
|
jsonld:
|