optimising and making it better

This commit is contained in:
sdarbinyan
2026-02-26 21:54:21 +04:00
parent 7a00a8f1e3
commit 10b4974719
58 changed files with 318 additions and 1804 deletions

View File

@@ -146,7 +146,8 @@
}, },
"sourceMap": false, "sourceMap": false,
"namedChunks": false, "namedChunks": false,
"extractLicenses": true "extractLicenses": true,
"serviceWorker": "ngsw-config.json"
} }
}, },
"defaultConfiguration": "production" "defaultConfiguration": "production"

View File

@@ -8,7 +8,6 @@
"resources": { "resources": {
"files": [ "files": [
"/favicon.ico", "/favicon.ico",
"/index.csr.html",
"/index.html", "/index.html",
"/manifest.webmanifest", "/manifest.webmanifest",
"/*.css", "/*.css",
@@ -48,7 +47,7 @@
"https://**/*.webp" "https://**/*.webp"
], ],
"cacheConfig": { "cacheConfig": {
"maxSize": 50, "maxSize": 200,
"maxAge": "7d", "maxAge": "7d",
"strategy": "performance" "strategy": "performance"
} }

View File

@@ -16,9 +16,10 @@ export const appConfig: ApplicationConfig = {
), ),
provideHttpClient( provideHttpClient(
withInterceptors([cacheInterceptor]) withInterceptors([cacheInterceptor])
), provideServiceWorker('ngsw-worker.js', { ),
provideServiceWorker('ngsw-worker.js', {
enabled: !isDevMode(), enabled: !isDevMode(),
registrationStrategy: 'registerWhenStable:30000' registrationStrategy: 'registerWhenStable:30000'
}) })
] ]
} };

View File

@@ -43,7 +43,8 @@ export class App implements OnInit {
takeUntilDestroyed(this.destroyRef) takeUntilDestroyed(this.destroyRef)
) )
.subscribe((event) => { .subscribe((event) => {
const url = (event as NavigationEnd).urlAfterRedirects || (event as NavigationEnd).url; const navEnd = event as NavigationEnd;
const url = navEnd.urlAfterRedirects || navEnd.url;
this.isHomePage.set(url === '/' || url === '/home' || url === ''); this.isHomePage.set(url === '/' || url === '/home' || url === '');
}); });
} }

View File

@@ -1,74 +0,0 @@
<div class="legal-page">
<div class="legal-container">
<h1>О компании ООО «ИНТ ФИН ЛОГИСТИК»</h1>
<section class="legal-section">
<h2>О нас</h2>
<p>Компания DexarMarket действительно представляет собой быстроразвивающийся маркетплейс, активно функционирующий в области торговли различными товарами и услугами. Регистрация юридического лица ООО "ИНТ ФИН ЛОГИСТИК", осуществленная согласно законодательству Армении, подчеркивает международную направленность бизнеса, поскольку компания также успешно работает на российском рынке, имея необходимые реквизиты для легальной деятельности в РФ.</p>
<p>Начало своей деятельности DEXARMARKET положил именно в Армении, однако расширение произошло стремительно. Уже летом 2025 года площадка вышла на российский рынок, показывая значительный рост популярности среди партнеров и покупателей из разных регионов мира, включая Россию, Объединённые Арабские Эмираты, Турцию, Китай, Армению, Казахстан, Кыргызстан и другие государства.</p>
<p>Основная цель компании заключается в предоставлении качественного сервиса своим партнерам и покупателям, обеспечивая комфорт и надежность сделок, расширяя ассортимент товаров и услуг, а также поддерживая высокие стандарты обслуживания клиентов.</p>
<p>Таким образом, DEXARMARKET является ярким примером успешного международного проекта, демонстрирующего успешное развитие и интеграцию на глобальном уровне.</p>
</section>
<section class="legal-section">
<h2>Наша миссия</h2>
<p>Мы стремимся создать уникальную экосистему, обеспечивающую максимальный комфорт и выгоду нашим партнёрам при размещении товаров на платформе DEXARMARKET. Мы предлагаем широкий спектр дополнительных услуг и сервисов, помогающих оптимизировать бизнес-процессы наших продавцов.</p>
<p>Для покупателей мы предоставляем удобный доступ к разнообразному ассортименту качественных товаров по привлекательным ценам непосредственно от производителей и поставщиков. Это позволяет клиентам экономить время и средства, выбирая лучшие предложения на рынке.</p>
<h3>Нашими основными приоритетами являются:</h3>
<ul>
<li>Создание прозрачной и эффективной системы взаимодействия между продавцами и покупателями.</li>
<li>Предоставление инновационных решений для повышения конкурентоспособности и увеличения продаж наших партнёров.</li>
<li>Обеспечение высокого уровня клиентского сервиса и поддержки пользователей на всех этапах сотрудничества.</li>
</ul>
<p>Мы постоянно работаем над улучшением функционала нашей платформы, внедряя новые технологии и инструменты, чтобы сделать процесс покупки и продажи ещё более удобным и выгодным для всех участников рынка.</p>
</section>
<section class="legal-section">
<h2>История компании DEXARMARKET</h2>
<p>Компания DEXARMARKET возникла благодаря усилиям команды профессионалов, объединённых общей целью и опытом в ключевых областях: информационно-коммуникационных технологиях (IT), экономике и торговой отрасли. Основатели понимали важность интеграции передовых технологических решений и глубокого понимания рыночных процессов, что позволило сформировать эффективную концепцию развития маркетплейса.</p>
<h3>Основные этапы становления:</h3>
<h4>Зарождение идеи</h4>
<p>Команда, обладающая глубокими познаниями в цифровой трансформации бизнеса и экономических процессах, объединилась вокруг амбициозной цели: создание площадки, способствующей развитию предпринимательства и коммерции на международном уровне.</p>
<h4>Разработка концепции</h4>
<p>Осознавая необходимость предоставления удобных инструментов для эффективного управления бизнесом онлайн, команда приступила к разработке оригинальной модели маркетплейса, основанной на последних достижениях в области электронной коммерции и аналитики больших данных.</p>
<h4>Запуск платформы</h4>
<p>Используя инновационные решения в информационной инфраструктуре и надёжные механизмы защиты данных, команда создала стабильную цифровую среду, привлекательную для предпринимателей и конечных потребителей.</p>
<h4>Выход на международный уровень</h4>
<p>Получив признание на национальном рынке, DEXARMARKET начал своё активное продвижение на международные рынки, постепенно охватывая разные регионы и страны, создавая условия для роста малого и среднего бизнеса, а также крупных торговых компаний.</p>
<p><strong>Сегодня DEXARMARKET продолжает развиваться, совершенствуя свои технологические возможности и предлагая пользователям всё больше преимуществ и возможностей для успешной коммерческой деятельности.</strong></p>
</section>
<section class="legal-section">
<h2>Контактная информация</h2>
<p><strong>Телефон (Россия):</strong> <a href="tel:+79264593157">+7 (926) 459-31-57</a></p>
<p><strong>Телефон (Армения):</strong> <a href="tel:+37494861816">+374 94 86 18 16</a></p>
<p><strong>Email:</strong> <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a></p>
<p><strong>Часы работы:</strong><br>Техподдержка: 24/7<br>Ответы на вопросы: 10:00 - 19:00 (МСК)</p>
</section>
<section class="legal-section">
<h2>Реквизиты организации</h2>
<p><strong>Полное наименование организации:</strong><br>ОБЩЕСТВО С ОГРАНИЧЕННОЙ ОТВЕТСТВЕННОСТЬЮ «ИНТ ФИН ЛОГИСТИК»</p>
<p><strong>Директор:</strong> Оганнисян Ашот Рафикович</p>
<p><strong>Юридический адрес:</strong><br>АРМЕНИЯ, 2301, КОТАЙКСКАЯ ОБЛАСТЬ, РАЗДАН, ХАЧАТРЯНА ул, 31, 4</p>
<p><strong>Офис в Армении:</strong><br>0033, Ереван, улица Братьев Орбели, 47</p>
<p><strong>Офис в России:</strong><br>121059, Москва, наб. Тараса Шевченко, 3к2</p>
<p><strong>Основные реквизиты:</strong><br>ИНН (РФ): 9909697628<br>ИНН (Армения): 03033502<br>КПП: 770287001<br>ОГРН: 85.110.1408711</p>
<p><strong>Банковские реквизиты:</strong><br>Банк: АО "Райффайзенбанк"<br>Расчетный счет: 40807810500000002376<br>Корр. счет: 30101810200000000700<br>БИК: 044525700</p>
<p><strong>Контактная информация:</strong><br>Телефон (Россия): +7 (926) 459-31-57<br>Телефон (Армения): +374 94 86 18 16<br>Email: info@dexarmarket.ru<br>Сайт: www.dexarmarket.ru</p>
</section>
</div>
</div>

View File

@@ -1,46 +0,0 @@
<div class="legal-page">
<div class="legal-container">
<h1>Контакты</h1>
<section class="legal-section">
<h2>Контактная информация</h2>
<p>Свяжитесь с нами по любым вопросам, связанным с работой маркетплейса, оформлением заказов или возвратом товаров.</p>
</section>
<section class="legal-section">
<h2>Реквизиты организации</h2>
<p><strong>Наименование:</strong> ООО «ИНТ ФИН ЛОГИСТИК»</p>
<p><strong>ИНН:</strong> 9909697628</p>
</section>
<section class="legal-section">
<h2>Телефоны</h2>
<p><strong>Россия:</strong> <a href="tel:+79264593157">+7 (926) 459-31-57</a></p>
<p><strong>Армения:</strong> <a href="tel:+37494861816">+374 94 86 18 16</a></p>
</section>
<section class="legal-section">
<h2>Email</h2>
<p>По всем вопросам пишите на: <a href="mailto:info@dexarmarket.ru">info&#64;dexarmarket.ru</a></p>
<p>Мы стараемся отвечать на все письма в течение 24 часов в рабочие дни.</p>
</section>
<section class="legal-section">
<h2>Часы работы</h2>
<p><strong>Техническая поддержка:</strong> Круглосуточно (24/7)</p>
<p><strong>Ответы на вопросы:</strong> Понедельник - Пятница: 10:00 - 19:00 (МСК)</p>
<p>Суббота - Воскресенье: выходной</p>
</section>
<section class="legal-section">
<h2>Адреса офисов</h2>
<p><strong>Офис в Армении:</strong> 0033, Ереван, улица Братьев Орбели, 47</p>
<p><strong>Офис в России:</strong> 121059, Москва, наб. Тараса Шевченко, 3к2</p>
</section>
<section class="legal-section">
<h2>Техническая поддержка</h2>
<p>При возникновении технических проблем с работой сайта или вопросов по оформлению заказа обращайтесь на <a href="mailto:info@dexarmarket.ru">info&#64;dexarmarket.ru</a> с подробным описанием проблемы.</p>
</section>
</div>
</div>

View File

@@ -1,60 +0,0 @@
<div class="legal-page">
<div class="legal-container">
<h1>Доставка</h1>
<section class="legal-section">
<h2>1. Способы доставки</h2>
<p>1.1. <strong>Цифровые товары:</strong> Платформа DexarMarket осуществляет доставку цифровых товаров (лицензионные ключи, электронные сертификаты, цифровой контент и т.д.) на указанную Покупателем электронную почту или в личный кабинет на платформе незамедлительно после подтверждения оплаты.</p>
<p>1.2. <strong>Материальные товары:</strong> Продавец самостоятельно осуществляет доставку материальных Товаров с привлечением транспортных компаний и почтовых операторов, включая, но не ограничиваясь: <strong>АО «СДЭК»</strong>, <strong>ФГУП «Почта России»</strong>, <strong>Boxberry</strong>, <strong>DPD</strong>, <strong>Яндекс.Доставка</strong> и иных перевозчиков по согласованию с Покупателем.</p>
<p>1.3. Способы доставки материальных товаров, доступные для конкретного Заказа, определяются Продавцом на момент оформления Заказа и могут включать:</p>
<ul>
<li>курьерскую доставку (АО «СДЭК», DPD, Яндекс.Доставка, иные курьерские службы);</li>
<li>доставку в пункт выдачи (Boxberry, СДЭК, Почта России);</li>
<li>почтовую отправку (ФГУП «Почта России»);</li>
<li>самовывоз (если применимо для данного Товара).</li>
</ul>
<p>1.4. Выбор конкретного способа доставки осуществляется Покупателем в процессе оформления Заказа в пределах доступных вариантов, предложенных Продавцом.</p>
</section>
<section class="legal-section">
<h2>2. Стоимость доставки</h2>
<p>2.1. <strong>Цифровые товары:</strong> Доставка цифровых товаров осуществляется бесплатно.</p>
<p>2.2. <strong>Материальные товары:</strong> Стоимость доставки материальных товаров определяется Продавцом в зависимости от выбранного способа доставки, веса и габаритов отправления, адреса доставки и действующих тарифов перевозчика на момент оформления Заказа.</p>
<p>2.3. Итоговая стоимость доставки материальных товаров отображается Покупателю до подтверждения Заказа и включается в общую сумму к оплате.</p>
<p>2.4. В случае проведения акций и специальных предложений доставка может быть осуществлена бесплатно при выполнении условий, указанных в описании акции.</p>
</section>
<section class="legal-section">
<h2>3. Сроки доставки</h2>
<p>3.1. <strong>Цифровые товары:</strong> Доставка цифровых товаров производится мгновенно (в течение нескольких минут) после подтверждения оплаты. В отдельных случаях срок может составлять до 24 часов.</p>
<p>3.2. <strong>Материальные товары:</strong> Ориентировочные сроки доставки материальных товаров по территории Российской Федерации составляют от 1 (одного) до 14 (четырнадцати) рабочих дней с момента передачи отправления перевозчику Продавцом.</p>
<p>3.3. Указанные сроки являются приблизительными и могут изменяться в зависимости от региона доставки, работы перевозчика, погодных условий, выходных и праздничных дней.</p>
<p>3.4. Точный срок доставки материальных товаров рассчитывается автоматически при оформлении Заказа на основании данных выбранного перевозчика и доводится до сведения Покупателя.</p>
<p>3.5. Продавец не несёт ответственности за нарушение сроков доставки, вызванное действиями или бездействием перевозчика, обстоятельствами непреодолимой силы либо иными независящими от Продавца причинами.</p>
</section>
<section class="legal-section">
<h2>4. Условия передачи и приёмки Товара</h2>
<p>4.1. Товар передаётся Покупателю или указанному им лицу перевозчиком в соответствии с условиями выбранного способа доставки.</p>
<p>4.2. Риск случайной гибели или повреждения Товара переходит к Покупателю с момента фактической передачи Товара Покупателю или уполномоченному им лицу.</p>
<p>4.3. При получении Товара Покупатель обязан:</p>
<ul>
<li>проверить целостность упаковки и соответствие наименования и количества Товара данным, указанным в сопроводительных документах;</li>
<li>в случае обнаружения повреждений упаковки, недостачи или несоответствия Товара — составить акт в присутствии представителя перевозчика;</li>
<li>при отсутствии претензий — расписаться в документах перевозчика о получении Товара в надлежащем состоянии.</li>
</ul>
<p>4.4. Отправка Товара осуществляется Продавцом после подтверждения Заказа и получения оплаты (полной или частичной) в соответствии с условиями конкретного Заказа.</p>
<p>4.5. Продавец не несёт ответственности за утрату, повреждение или задержку Товара в период транспортировки, если указанные обстоятельства вызваны действиями или бездействием перевозчика. В таких случаях Покупатель вправе предъявить претензии непосредственно перевозчику в установленном законодательством порядке, а Продавец обязуется оказать содействие в урегулировании спора в разумных пределах.</p>
</section>
<section class="legal-section">
<h2>5. Контактная информация</h2>
<p>По вопросам доставки обращайтесь:</p>
<ul>
<li><strong>Email:</strong> <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a></li>
<li><strong>Телефон (Россия):</strong> <a href="tel:+79264593157">+7 (926) 459-31-57</a></li>
<li><strong>Телефон (Армения):</strong> <a href="tel:+37494861816">+374 94 86 18 16</a></li>
</ul>
</section>
</div>
</div>

View File

@@ -1,244 +0,0 @@
<div class="legal-page">
<div class="legal-container">
<h1>Часто задаваемые вопросы (FAQ) 📌</h1>
<section class="legal-section">
<h2>Общие вопросы</h2>
<div class="faq-item">
<h3>Что такое DexarMarket?</h3>
<p>DexarMarket — это онлайн-площадка, где независимые продавцы размещают свои товары и услуги. Наша задача — обеспечить удобную и безопасную среду для совершения покупок, мы сами не производим и не продаем товары.</p>
</div>
<div class="faq-item">
<h3>Как зарегистрироваться на платформе?</h3>
<p>Зарегистрироваться легко: откройте наше приложение внутри Telegram. Ваш профиль будет создан автоматически сразу же после входа.</p>
</div>
<div class="faq-item">
<h3>Безопасно ли покупать на сайте?</h3>
<p>Абсолютно да! Все транзакции защищены современными технологиями шифрования (PCI DSS и 3D Secure). Ваши банковские данные надежно хранятся отдельно от нашей системы.</p>
</div>
</section>
<section class="legal-section">
<h2>Оформление заказа</h2>
<div class="faq-item">
<h3>Как правильно оформить покупку?</h3>
<p>
1⃣ Найдите понравившийся товар и добавьте его в корзину.<br>
2⃣ Открыв корзину, кликните «Оформить заказ».<br>
3⃣ Укажите адрес доставки и контактную информацию.<br>
4⃣ Выберите удобный способ оплаты.<br>
5⃣ Ознакомьтесь и подтвердите публичную оферту.<br>
6⃣ Завершите оплату вашего заказа.
</p>
</div>
<div class="faq-item">
<h3>Можно ли внести изменения в заказ после завершения покупки?</h3>
<p>Если продавец ещё не отправил товар, напишите нам в поддержку — мы поможем скорректировать заказ. Но после отправки товара изменение невозможно.</p>
</div>
<div class="faq-item">
<h3>Как отказаться от заказа?</h3>
<p>Свяжитесь с нами или непосредственно с продавцом через чаты заказов. Пока посылка не отправлена, отказ возможен с полным возвратом денег.</p>
</div>
</section>
<section class="legal-section">
<h2>Оплата 💳</h2>
<div class="faq-item">
<h3>Какие способы оплаты доступны?</h3>
<p>Принимаются:</p>
<ul>
<li>Банковские карты Visa, MasterCard, МИР,</li>
<li>Система быстрых платежей (СБП),</li>
<li>Электронные кошельки ЮMoney, QIWI,</li>
<li>Наличные при получении (если предусмотрено продавцом).</li>
</ul>
</div>
<div class="faq-item">
<h3>Когда спишутся средства с моей карты?</h3>
<p>Операция проходит мгновенно, но деньги временно замораживаются до момента получения вами товара. Как только вы подтверждаете получение, средства отправляются продавцу.</p>
</div>
<div class="faq-item">
<h3>Почему мой платёж мог быть отклонён?</h3>
<p>Возможные причины отказа:</p>
<ul>
<li>Недостаточно средств на счёте,</li>
<li>Превышение лимита операций по карте,</li>
<li>Карта заблокирована банком,</li>
<li>Технические сбои.</li>
</ul>
<p>Рекомендуем обратиться в банк для выяснения деталей.</p>
</div>
<div class="faq-item">
<h3>Получу ли я чек об оплате?</h3>
<p>Да, электронная квитанция придёт на указанный вами e-mail сразу после успешного платежа согласно закону № 54-ФЗ.</p>
</div>
</section>
<section class="legal-section">
<h2>Доставка 🚚</h2>
<div class="faq-item">
<h3>Через какие службы осуществляется доставка?</h3>
<p><strong>Цифровые товары:</strong> Платформа DexarMarket автоматически отправляет цифровые товары (лицензии, ключи, сертификаты) на вашу электронную почту или в личный кабинет мгновенно после оплаты.</p>
<p><strong>Материальные товары:</strong> Продавец самостоятельно работает с ведущими службами доставки:</p>
<ul>
<li>СДЭК,</li>
<li>Почта России,</li>
<li>Boxberry,</li>
<li>DPD,</li>
<li>Яндекс.Доставка.</li>
</ul>
<p>Способ доставки материальных товаров выбирается исходя из предпочтений продавца и места назначения.</p>
</div>
<div class="faq-item">
<h3>Сколько стоит доставка моего заказа?</h3>
<p><strong>Цифровые товары:</strong> Доставка бесплатная — товар придёт на email мгновенно.</p>
<p><strong>Материальные товары:</strong> Цена определяется продавцом и зависит от веса, габаритов товара, выбранного способа и региона доставки. Окончательная стоимость видна при оформлении заказа.</p>
</div>
<div class="faq-item">
<h3>Какой срок доставки моего заказа?</h3>
<p><strong>Цифровые товары:</strong> Мгновенная доставка на email (в течение нескольких минут после оплаты).</p>
<p><strong>Материальные товары</strong> (примерные сроки):</p>
<ul>
<li>СДЭК: 27 рабочих дней,</li>
<li>Почта России: 514 рабочих дней,</li>
<li>Boxberry: 25 рабочих дней,</li>
<li>DPD: 13 рабочих дня,</li>
<li>Яндекс.Доставка: в тот же день (при наличии возможности в вашем городе).</li>
</ul>
</div>
<div class="faq-item">
<h3>Как отслеживать мою посылку?</h3>
<p>Вы получите трек-код на свою электронную почту и сможете увидеть статус заказа в личном кабинете. Отслеживать посылку можно на официальном сайте выбранной курьерской службы.</p>
</div>
<div class="faq-item">
<h3>Что делать, если товар пришёл повреждённым? ⛑</h3>
<p>Осмотрите товар прямо при курьере. Если обнаружились дефекты — оформляйте акт отказа от приёмки и незамедлительно сообщайте продавцу и службе поддержки.</p>
</div>
</section>
<section class="legal-section">
<h2>Возврат и обмен ✅</h2>
<div class="faq-item">
<h3>Можно ли вернуть товар?</h3>
<p>Да, закон позволяет вернуть качественный товар в течение 7 дней после получения. Бракованные изделия возвращаются по особым правилам.</p>
</div>
<div class="faq-item">
<h3>Какие товары вернуть нельзя?</h3>
<p>Нельзя вернуть товары, перечисленные в Постановлении Правительства РФ №2463: медикаменты, косметику, бельё, активированные цифровые продукты и индивидуальные заказы. Подробности смотрите в разделе <a routerLink="/return-policy">«Политика возврата»</a>.</p>
</div>
<div class="faq-item">
<h3>Как вернуть деньги?</h3>
<p>
1. Сообщите продавцу о намерении вернуть товар.<br>
2. Верните товар в оригинальной упаковке.<br>
3. Продавец проверит состояние товара и вернёт средства таким же способом, каким была произведена покупка (до 30 дней ожидания возврата).
</p>
</div>
<div class="faq-item">
<h3>Кто оплатит обратный путь?</h3>
<p>Покупатель оплачивает обратную доставку качественного товара. Если обнаружен брак — расходы несёт продавец.</p>
</div>
</section>
<section class="legal-section">
<h2>Гарантия 🔧</h2>
<div class="faq-item">
<h3>Есть ли гарантия на товары?</h3>
<p>Большинство наших товаров имеют официальную гарантию производителя. Срок варьируется от 12 до 36 месяцев и указывается в карточке каждого продукта.</p>
</div>
<div class="faq-item">
<h3>Как воспользоваться гарантией?</h3>
<p>Сообщите продавцу о неисправности, приложив фотографии дефектов и гарантийный талон. Продавец займётся ремонтом или заменой товара.</p>
</div>
<div class="faq-item">
<h3>Что не покрыто гарантией?</h3>
<p>Механические повреждения, последствия неправильной эксплуатации, самостоятельный ремонт, влияние влаги (если нет защиты), естественный износ — всё это не является страховым случаем.</p>
</div>
</section>
<section class="legal-section">
<h2>Безопасность и конфиденциальность 🔐</h2>
<div class="faq-item">
<h3>Как вы защищаете мои личные данные?</h3>
<p>Используем современные методы шифрования SSL/TLS, не храним реквизиты карт, выполняем требования закона №152-ФЗ о защите персональной информации. Подробности — в <a routerLink="/privacy-policy">Политике конфиденциальности</a>.</p>
</div>
<div class="faq-item">
<h3>Кому предоставляются мои данные?</h3>
<p>Только вашему продавцу для обработки заказа и службам доставки. Данные не используются третьими лицами для маркетинга без вашего разрешения.</p>
</div>
<div class="faq-item">
<h3>Как удалить свой аккаунт?</h3>
<p>Напишите нам в службу поддержки запрос на удаление учётной записи. Аккаунт будет ликвидирован вместе с личной информацией в течение месяца.</p>
</div>
</section>
<section class="legal-section">
<h2>Информация для продавцов 📋</h2>
<div class="faq-item">
<h3>Как начать продавать на площадке?</h3>
<p>Чтобы присоединиться к нашим продавцам, обратитесь в службу поддержки по электронной почте <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a>.</p>
</div>
<div class="faq-item">
<h3>Какова комиссия площадки?</h3>
<p>Комиссия зависит от типа товара и объёма продаж. Узнать точные условия можно при регистрации.</p>
</div>
<div class="faq-item">
<h3>Когда поступят деньги за продажу?</h3>
<p>Продавец получает средства после подтверждения клиентом получения товара либо спустя две недели с момента доставки, если клиент не указал проблем с покупкой.</p>
</div>
</section>
<section class="legal-section">
<h2>Служба поддержки 💬</h2>
<div class="faq-item">
<h3>Как связаться с поддержкой?</h3>
<p>
✉️ <strong>Email:</strong> <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a><br>
📞 <strong>Телефон (Россия):</strong> <a href="tel:+79264593157">+7 (926) 459-31-57</a><br>
📞 <strong>Телефон (Армения):</strong> <a href="tel:+37494861816">+374 94 86 18 16</a><br>
🏢 <strong>Время работы офиса:</strong> 10:00—19:00 (МСК)<br>
❄️ <strong>Техподдержка доступна круглосуточно.</strong>
</p>
</div>
<div class="faq-item">
<h3>Сколько ждать ответа?</h3>
<p>Во время рабочего дня ответ поступает в течение двух часов. В праздники и выходные возможны задержки до суток.</p>
</div>
</section>
<section class="legal-section">
<h2>Нужна помощь?</h2>
<p>Если возникнут дополнительные вопросы, обращайтесь на <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a> — мы оперативно решим любые ваши вопросы!</p>
</section>
</div>
</div>

View File

@@ -1,158 +0,0 @@
<div class="legal-page">
<div class="legal-container">
<h1>Гарантия 🔨</h1>
<section class="legal-section">
<h2>1. Основные положения о гарантии</h2>
<p>Настоящий раздел устанавливает порядок предоставления гарантийных услуг на товары, купленные на маркетплейсе DexarMarket.</p>
<ul>
<li>Обязательства по гарантии исполняет сам Продавец товара, в строгом соответствии с российским законодательством.</li>
<li>Платформа DexarMarket выступает лишь информационным посредником и не принимает участие в исполнении гарантийных условий.</li>
<li>Гарантия действует исключительно на заводские дефекты и недостатки, возникшие не по вине покупателя.</li>
</ul>
</section>
<section class="legal-section">
<h2>2. Срок гарантии 🏷</h2>
<p>Срок гарантии устанавливается Продавцом или производителем товара и публикуется:</p>
<ul>
<li>На страницах товаров нашего сайта.</li>
<li>В гарантийном талоне, вложенном в упаковку.</li>
<li>В сопроводительной документации товара.</li>
</ul>
<p><strong>Типичные сроки гарантии по категориям товаров:</strong></p>
<ul>
<li><strong>Электроника и бытовая техника:</strong> от 12 до 24 месяцев.</li>
<li><strong>Компьютерная техника и комплектующие:</strong> от 12 до 36 месяцев.</li>
<li><strong>Одежда и обувь:</strong> от 30 дней до полугода (зависит от сезонности).</li>
<li><strong>Мебель:</strong> от 12 до 18 месяцев.</li>
<li><strong>Цифровая продукция:</strong> поддержка определяется самим Продавцом.</li>
</ul>
<p>Начало срока гарантии отсчитывается с момента передачи товара покупателю.</p>
<p>Замена товара продлевает гарантийный срок заново с момента выдачи замены.</p>
<p>Если срок гарантии не обозначен Продавцом, покупатель имеет право предъявлять претензии в течение 2-х лет с момента приобретения товара (согласно ст. 19 Закона РФ «О защите прав потребителей»).</p>
</section>
<section class="legal-section">
<h2>3. Условия предоставления гарантии 📝</h2>
<p>Гарантия действительна при выполнении следующих требований:</p>
<ul>
<li>Использование товара строго по инструкции.</li>
<li>Отсутствие самостоятельной разборки, ремонта или модификации устройства.</li>
<li>Нет механических повреждений внешнего корпуса и внутренних элементов.</li>
<li>Сохранены оригинальные пломбы и серийные номера (если предусмотрены).</li>
<li>Устройство не подвергалось влиянию высоких температур, влажности или химикатов.</li>
<li>Имеются гарантийный талон и подтверждение покупки (чек, квитанция).</li>
</ul>
<p><strong>Документы для обращения по гарантии:</strong></p>
<ul>
<li>Сам товар с полной комплектацией.</li>
<li>Гарантийный талон (если прилагался).</li>
<li>Документ, подтверждающий приобретение (чек, кассовый ордер).</li>
<li>Удостоверение личности владельца товара (например, паспорт).</li>
</ul>
</section>
<section class="legal-section">
<h2>4. Гарантийный ремонт и замена 🛠</h2>
<h3>Права покупателя при выявлении брака:</h3>
<p>Если недостаток найден в пределах гарантийного периода, вы имеете право:</p>
<ul>
<li>Бесплатно устранить неисправность.</li>
<li>Получить аналогичный товар взамен испорченного.</li>
<li>Потребовать замену на другой товар с перерасчетом стоимости.</li>
<li>Снизить цену товара пропорционально дефекту.</li>
<li>Вернуть полную сумму за товар.</li>
</ul>
<h3>Сроки ремонта:</h3>
<p>Ремонт выполняется быстро, но максимальный срок составляет 45 дней (статья 20 Закона РФ «О защите прав потребителей»). Если срок нарушен, вы можете попросить заменить товар или вернуть деньги.</p>
<h3>Временная замена товара:</h3>
<p>Если срок ремонта превышает неделю, продавец обязан предоставить временный заменитель для технически сложных товаров.</p>
<h3>Доставка для ремонта:</h3>
<p>Расходы на транспортировку товара в сервисный центр и обратно берет на себя продавец или специализированный сервисный центр.</p>
</section>
<section class="legal-section">
<h2>5. Случаи, не подлежащие гарантии 🔍</h2>
<p>Гарантия не работает, если выявлены следующие обстоятельства:</p>
<ul>
<li>Механическое повреждение (удары, падение, трещины, царапины);</li>
<li>Нарушения правил эксплуатации (неправильное подключение, превышение нагрузки, нестандартное применение);</li>
<li>Повреждения из-за внешних воздействий (жидкость, грязь, высокие температуры, сырость);</li>
<li>Самостоятельный ремонт (разборка, модернизация, замена комплектующих);</li>
<li>Действие форс-мажорных обстоятельств (пожар, затопление, кража, погодные катаклизмы);</li>
<li>Естественное старение материалов (потеря цвета, блеск, незначительный износ);</li>
<li>Незаконное нарушение заводских пломб или уничтожение серийных номеров.</li>
</ul>
<p><strong>Также не относятся к гарантийному случаю:</strong></p>
<ul>
<li>Косметические изъяны, не влияющие на работу (поверхностные царапинки, небольшие пятна);</li>
<li>Изменения внешнего вида вследствие обычной эксплуатации;</li>
<li>Программные неполадки, вызванные установками постороннего программного обеспечения;</li>
<li>Проблемы совместимости с устройствами или ПО других производителей.</li>
</ul>
<p>Отдельно оговорено ограничение гарантии на расходники (батарейки, лампочки, фильтры), указанные в описании товара.</p>
</section>
<section class="legal-section">
<h2>6. Процедура подачи заявки на гарантийное обслуживание 🗒</h2>
<p>Чтобы воспользоваться гарантийным сервисом, выполните следующие шаги:</p>
<ol>
<li>Связаться с продавцом через контактные данные, указанные в вашем заказе.</li>
<li>Объяснить суть проблемы и приложить фотоматериалы или видеозапись (если необходимо).</li>
<li>Получить от продавца инструкцию по обращению в сервисный центр или адрес, куда отправить товар.</li>
<li>Доставить товар в сервис с документами, подтверждающими покупку (гарантийный талон, чек).</li>
<li>Получить акт приёма товара с указанием срока ремонтных работ.</li>
<li>Забрать восстановленный товар после оповещения о завершении ремонта.</li>
</ol>
<h3>Правила отправки товара почтой или курьером:</h3>
<ul>
<li>Надежно упакуйте устройство, предотвращая возможные повреждения при перевозке.</li>
<li>Положите копии документов о покупке и подробное описание проблемы внутрь упаковки.</li>
<li>Оформите почтовое отправление с оценочной стоимостью.</li>
<li>Обязательно сохраняйте номер трека для контроля местонахождения груза.</li>
</ul>
<p>Если возникли трудности, покупатели также могут обращаться в нашу службу поддержки через email: <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a>.</p>
</section>
<section class="legal-section">
<h2>7. Дополнительные права покупателя 🎯</h2>
<p>Если товар имеет серьёзный недостаток, вы вправе:</p>
<ul>
<li>Требовать полного возврата денег.</li>
<li>Просить замену на товар другой модели с соответствующим перерасчётом стоимости.</li>
</ul>
<p><strong>Серьёзный недостаток</strong> — это ситуация, когда:</p>
<ul>
<li>Невозможно исправить поломку.</li>
<li>Устранение поломки требует больших затрат или долгого времени.</li>
<li>Недостаток появляется снова после ремонта.</li>
<li>Одна и та же проблема возникает многократно.</li>
</ul>
<p>Кроме того, вы можете взыскать убытки, понесённые из-за продажи некачественного товара.</p>
</section>
<section class="legal-section">
<h2>8. Контактная информация 📞</h2>
<p>По любым вопросам гарантийного обслуживания обращайтесь сначала к продавцу (см. страницу товара или ваше уведомление о доставке).</p>
<p><strong>Если возникла необходимость решения спора:</strong></p>
<p>Отправьте письмо на email Маркетплейса: <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a> с темой: «Гарантийный вопрос — Заказ №[номер заказа]».</p>
<p>В случае отказа продавца принять претензию, вы имеете право инициировать независимую экспертизу качества товара и подать иск в судебные органы.</p>
</section>
</div>
</div>

View File

@@ -1,102 +0,0 @@
<div class="legal-page">
<div class="legal-container">
<h1>Реквизиты организации</h1>
<section class="legal-section">
<h2>Полное наименование организации</h2>
<p>ОБЩЕСТВО С ОГРАНИЧЕННОЙ ОТВЕТСТВЕННОСТЬЮ «ИНТ ФИН ЛОГИСТИК»</p>
<p><strong>Сокращенное наименование:</strong> ООО «ИНТ ФИН ЛОГИСТИК»</p>
</section>
<section class="legal-section">
<h2>Юридический адрес</h2>
<p>АРМЕНИЯ, 2301, КОТАЙКСКАЯ ОБЛАСТЬ, РАЗДАН, ХАЧАТРЯНА ул, 31, 4</p>
</section>
<section class="legal-section">
<h2>Фактический адрес</h2>
<p><strong>Офис в Армении:</strong> 0033, Ереван, улица Братьев Орбели, 47</p>
<p><strong>Офис в России:</strong> 121059, Москва, наб. Тараса Шевченко, 3к2</p>
</section>
<section class="legal-section">
<h2>Основные реквизиты</h2>
<div class="details-grid">
<div class="detail-item">
<strong>ИНН (RUS):</strong>
<span>9909697628</span>
</div>
<div class="detail-item">
<strong>ИНН (ARM):</strong>
<span>03033502</span>
</div>
<div class="detail-item">
<strong>КПП:</strong>
<span>770287001</span>
</div>
<div class="detail-item">
<strong>ОГРН:</strong>
<span>85.110.1408711</span>
</div>
</div>
</section>
<section class="legal-section">
<h2>Банковские реквизиты</h2>
<div class="details-grid">
<div class="detail-item">
<strong>Банк:</strong>
<span>АО "Райффайзенбанк"</span>
</div>
<div class="detail-item">
<strong>Расчетный счет:</strong>
<span>40807810500000002376</span>
</div>
<div class="detail-item">
<strong>Корр. счет:</strong>
<span>30101810200000000700</span>
</div>
<div class="detail-item">
<strong>БИК:</strong>
<span>044525700</span>
</div>
</div>
</section>
<section class="legal-section">
<h2>Контактная информация</h2>
<div class="details-grid">
<div class="detail-item">
<strong>Телефон (RUS):</strong>
<span><a href="tel:+79264593157">+7 (926) 459-31-57</a></span>
</div>
<div class="detail-item">
<strong>Телефон (ARM):</strong>
<span><a href="tel:+37494861816">+374 94 86 18 16</a></span>
</div>
<div class="detail-item">
<strong>Email:</strong>
<span><a href="mailto:info@dexarmarket.ru">info&#64;dexarmarket.ru</a></span>
</div>
<div class="detail-item">
<strong>Сайт:</strong>
<span><a href="https://dexarmarket.ru" target="_blank">dexarmarket.ru</a></span>
</div>
<div class="detail-item">
<strong>Часы работы офиса:</strong>
<span>10:00 - 19:00 (МСК)</span>
</div>
<div class="detail-item">
<strong>Техподдержка:</strong>
<span>24/7</span>
</div>
</div>
</section>
<section class="legal-section">
<h2>Руководство</h2>
<p><strong>Генеральный директор:</strong> Оганнисян Ашот Рафикович</p>
<p><strong>Основание действий:</strong> Устав</p>
</section>
</div>
</div>

View File

@@ -1,119 +0,0 @@
<div class="legal-page">
<div class="legal-container">
<h1>Правила оплаты</h1>
<section class="legal-section">
<h2>1. Общие положения</h2>
<p>1.1. Настоящие Правила определяют порядок оплаты Товаров и Услуг, приобретаемых Покупателями через Маркетплейс DexarMarket.</p>
<p>1.2. Оплата производится за Товары/Услуги, размещенные независимыми Продавцами. Маркетплейс выступает в качестве информационного посредника и обеспечивает техническую инфраструктуру для проведения платежей.</p>
<p>1.3. Оплата товаров и услуг на Маркетплейсе осуществляется в российских рублях (RUB).</p>
<p>1.4. Цены на Товары/Услуги устанавливаются Продавцами самостоятельно и указываются на странице соответствующего Товара/Услуги.</p>
</section>
<section class="legal-section">
<h2>2. Способы оплаты</h2>
<p>2.1. Маркетплейс поддерживает следующие способы оплаты:</p>
<div class="payment-methods">
<div class="payment-logos">
<img src="/assets/images/mir-logo.svg" alt="МИР" loading="lazy" width="80" height="50" />
<img src="/assets/images/visa-logo.svg" alt="Visa" loading="lazy" width="80" height="50" />
<img src="/assets/images/mastercard-logo.svg" alt="Mastercard" loading="lazy" width="80" height="50" />
</div>
</div>
<ul>
<li><strong>Банковские карты:</strong> Visa, Mastercard, МИР</li>
<li><strong>Системы быстрых платежей (СБП):</strong> мгновенный перевод через мобильное приложение банка</li>
<li><strong>Электронные кошельки:</strong> ЮMoney, QIWI (при наличии)</li>
<li><strong>Оплата по ссылке:</strong> генерация уникальной платежной ссылки для каждого заказа</li>
</ul>
<p>2.2. Доступные способы оплаты могут различаться в зависимости от Продавца и типа Товара/Услуги.</p>
<p>2.3. Все платежи обрабатываются через сертифицированные платежные системы с соблюдением стандартов безопасности PCI DSS.</p>
</section>
<section class="legal-section">
<h2>3. Процесс оплаты</h2>
<p>3.1. Процедура оплаты заказа включает следующие этапы:</p>
<ol>
<li>Выбор Товаров/Услуг и добавление их в корзину</li>
<li>Оформление заказа с указанием контактных данных и способа доставки (при необходимости)</li>
<li>Выбор способа оплаты из доступных вариантов</li>
<li>Перенаправление на защищенную страницу платежной системы или получение платежной ссылки</li>
<li>Ввод платежных данных и подтверждение оплаты</li>
<li>Получение уведомления об успешной оплате</li>
</ol>
<p>3.2. При оплате банковской картой Покупатель может быть перенаправлен на страницу банка-эмитента для прохождения дополнительной аутентификации (3D-Secure).</p>
<p>3.3. Обязательство Покупателя по оплате считается исполненным с момента поступления денежных средств на счет платежной системы.</p>
</section>
<section class="legal-section">
<h2>4. Безопасность платежей</h2>
<p>4.1. Все платежи обрабатываются через защищенное HTTPS-соединение с использованием протокола TLS 1.2 и выше.</p>
<p>4.2. Маркетплейс не хранит полные данные банковских карт Покупателей. Обработка платежных данных осуществляется сертифицированными платежными агрегаторами.</p>
<p>4.3. Для защиты от мошенничества применяется технология 3D-Secure, требующая подтверждения платежа через SMS-код или push-уведомление от банка.</p>
<p>4.4. В случае подозрительной активности платежная система имеет право запросить дополнительную верификацию личности Покупателя.</p>
</section>
<section class="legal-section">
<h2>5. Подтверждение оплаты</h2>
<p>5.1. После успешной оплаты Покупатель получает подтверждение на указанный при оформлении заказа адрес электронной почты.</p>
<p>5.2. Подтверждение содержит следующую информацию:</p>
<ul>
<li>Номер заказа</li>
<li>Дата и время оплаты</li>
<li>Сумма платежа</li>
<li>Состав заказа</li>
<li>Контактные данные Продавца</li>
</ul>
<p>5.3. Информация о заказе также отображается в личном кабинете Покупателя на Маркетплейсе (при наличии регистрации).</p>
<p>5.4. Фискальный чек направляется Продавцом в соответствии с требованиями законодательства РФ.</p>
</section>
<section class="legal-section">
<h2>6. Возврат средств</h2>
<p>6.1. Порядок возврата денежных средств регулируется <a routerLink="/return-policy">Политикой возврата</a> и зависит от типа приобретенного Товара/Услуги.</p>
<p>6.2. Возврат средств производится на тот же платежный инструмент, с которого была произведена оплата.</p>
<p>6.3. Срок возврата денежных средств составляет:</p>
<ul>
<li>На банковскую карту: от 3 до 30 банковских дней (в зависимости от банка-эмитента)</li>
<li>На электронный кошелек: от 1 до 5 рабочих дней</li>
<li>Через СБП: от 1 до 3 рабочих дней</li>
</ul>
<p>6.4. За обработку возврата средств Маркетплейс комиссию не взимает. Комиссии платежных систем и банков могут применяться в соответствии с их тарифами.</p>
</section>
<section class="legal-section">
<h2>7. Неуспешные платежи</h2>
<p>7.1. Платеж может быть отклонен по следующим причинам:</p>
<ul>
<li>Недостаточно средств на счете</li>
<li>Неверно введены платежные данные</li>
<li>Карта заблокирована или просрочена</li>
<li>Превышены лимиты на операции, установленные банком</li>
<li>Отказ в проведении транзакции системой безопасности</li>
</ul>
<p>7.2. В случае неуспешной оплаты Покупатель получает уведомление с указанием причины отказа.</p>
<p>7.3. При возникновении проблем с оплатой рекомендуется:</p>
<ul>
<li>Проверить правильность введенных данных</li>
<li>Связаться с банком-эмитентом карты для уточнения причины отказа</li>
<li>Попробовать альтернативный способ оплаты</li>
<li>Обратиться в службу поддержки: <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a></li>
</ul>
</section>
<section class="legal-section">
<h2>8. Контакты для вопросов по оплате</h2>
<p>По вопросам, связанным с оплатой заказов, вы можете обратиться:</p>
<ul>
<li><strong>Email:</strong> <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a></li>
<li><strong>Телефон (Россия):</strong> <a href="tel:+79264593157">+7 (926) 459-31-57</a></li>
<li><strong>Телефон (Армения):</strong> <a href="tel:+37494861816">+374 94 86 18 16</a></li>
<li><strong>Время работы:</strong> Круглосуточно (техническая поддержка)</li>
<li><strong>Среднее время ответа:</strong> До 24 часов в рабочие дни</li>
</ul>
<p>При обращении указывайте номер заказа и краткое описание проблемы для более быстрого решения вопроса.</p>
</section>
</div>
</div>

View File

@@ -1,258 +0,0 @@
<div class="legal-page">
<div class="legal-container">
<h1>ПОЛИТИКА В ОТНОШЕНИИ ОБРАБОТКИ ПЕРСОНАЛЬНЫХ ДАННЫХ</h1>
<section class="legal-section">
<h2>1. ОБЩИЕ ПОЛОЖЕНИЯ</h2>
<p>1.1. Настоящая политика ООО "ИНТ ФИН ЛОГИСТИК" (ИНН 9909697628), именуемого далее как «Оператор», описывает порядок обработки персональных данных и направлена на защиту прав и законных интересов субъектов данных. Документ разработан в соответствии с Федеральным законом №152-ФЗ от 27 июля 2006 года «О персональных данных».</p>
<p>1.2. Политика определяет порядок и меры обеспечения безопасности обработки персональных данных на сайте <a href="https://dexarmarket.ru">https://dexarmarket.ru</a>, ставя своей задачей защитить права и свободы человека и гражданина, включая право на неприкосновенность частной жизни, личную и семейную тайны.</p>
<p>1.3. Документ охватывает все процессы, осуществляемые Оператором, касающиеся обработки персональных данных.</p>
<p>1.4. Политика обязательна для изучения и выполнения всеми лицами, допущенными к обработке персональных данных.</p>
<p>1.5. Действует в отношении всех действий, связанных с обработкой персональных данных на сайте <a href="https://dexarmarket.ru">https://dexarmarket.ru</a> и в информационных системах Оператора.</p>
<p>1.6. Пользователь, оформляющий заказ, открывающий личный кабинет или иным образом взаимодействующий с Оператором, выражает согласие на обработку своих персональных данных в соответствии с Политикой и законодательством РФ. Продолжительное использование сайта свидетельствует о согласии с Положениями Политики. Пользователь, не готовый согласиться с условиями, должен воздержаться от использования ресурса.</p>
<p><strong>Дополнительно:</strong> Настоящая Политика распространяется на персональные данные, собранные как до вступления документа в силу, так и после.</p>
</section>
<section class="legal-section">
<h2>2. ТЕРМИНЫ И ОПРЕДЕЛЕНИЯ</h2>
<p>В данной Политике используются следующие основные термины и определения:</p>
<p><strong>Персональные данные (ПДн)</strong> — любая информация, прямо или косвенно относящаяся к определённому физическому лицу (субъекту персональных данных).</p>
<p><strong>Информационная система персональных данных (ИСПДн)</strong> — совокупность персональных данных, хранимых в базах данных, а также технологий и средств для их обработки.</p>
<p><strong>Автоматизированная обработка ПДн</strong> — обработка данных с использованием компьютерных средств.</p>
<p><strong>Блокировка ПДн</strong> — временная приостановка обработки данных (за исключением случаев уточнения данных).</p>
<p><strong>Обезличивание ПДн</strong> — действия, ведущие к невозможности установления принадлежности данных конкретному лицу без дополнительной информации.</p>
<p><strong>Интернет-сайт (Сайт)</strong> — автоматизированная информационная система, доступная в сети Интернет по адресу: <a href="https://dexarmarket.ru">https://dexarmarket.ru</a>.</p>
<p><strong>Обработка ПДн</strong> — любые действия с персональными данными, включая сбор, запись, хранение, обновление, использование, передачу, уничтожение и другие операции.</p>
<p><strong>Оператор</strong> — государственный или частный орган, самостоятельно или совместно организующий обработку персональных данных.</p>
<p><strong>Предоставление ПДн</strong> — передача данных определённому лицу или группе лиц.</p>
<p><strong>Распространение ПДн</strong> — открытие данных неопределённому кругу лиц, включая публикацию в СМИ или сети Интернет.</p>
<p><strong>Трансграничная передача ПДн</strong> — передача данных зарубежным властям, компаниям или физическим лицам.</p>
<p><strong>Уничтожение ПДн</strong> — действия, приводящие к утрате возможности восстановления данных или уничтожения материальных носителей.</p>
<p><strong>Субъект ПДн</strong> — физическое лицо, чья информация обрабатывается.</p>
<p><strong>Конфиденциальность ПДн</strong> — обязанность Оператора защищать данные от распространения без согласия субъекта или законного основания.</p>
<p><strong>Продавец (Исполнитель)</strong> — лицо, предлагающее товары или услуги на сайте <a href="https://dexarmarket.ru">https://dexarmarket.ru</a>.</p>
<p><strong>Пользователь</strong> — лицо, посещающее или использующее ресурсы, управляемые Оператором, включая сайт <a href="https://dexarmarket.ru">https://dexarmarket.ru</a>.</p>
<p><strong>Заказ</strong> — оформленный Пользователем заказ товаров или услуг на сайте.</p>
<p><strong>Файлы cookie</strong> — небольшие файлы, сохраняемые на устройстве пользователя для запоминания предпочтений и действий при последующих посещениях сайта.</p>
</section>
<section class="legal-section">
<h2>3. ПРАВОВЫЕ ОСНОВАНИЯ ОБРАБОТКИ ПЕРСОНАЛЬНЫХ ДАННЫХ</h2>
<p>3.1. Правовым основанием Обработки ПДн в зависимости от целей процесса, предусматривающего Обработку ПДн может являться:</p>
<h3>3.1.1. Конституция Российской Федерации, а также совокупность правовых актов:</h3>
<ul>
<li>Налоговый кодекс Российской Федерации;</li>
<li>Гражданский Кодекс Российской Федерации;</li>
<li>ст. 86 - 90 Трудового кодекса Российской Федерации;</li>
<li>Федеральный закон от 07.08.2001 № 115-ФЗ «О противодействии легализации (отмыванию) доходов, полученных преступным путем, и финансированию терроризма»;</li>
<li>Федеральный закон от 27.07.2006 г. № 152-ФЗ «О персональных данных»;</li>
<li>Федеральный закон от 22.04.1996 № 39-ФЗ «О рынке ценных бумаг»;</li>
<li>Федеральный закон от 26.12.1995 №208-ФЗ «Об акционерных обществах»;</li>
<li>Федеральный закон от 27.07.2006 № 149-ФЗ «Об информации, информационных технологиях и о защите информации»;</li>
<li>Федеральный закон от 01.04.1996 № 27-ФЗ «Об индивидуальном (персонифицированном) учете в системе обязательного пенсионного страхования»;</li>
<li>Федеральный закон от 06.04.2011 № 63-ФЗ «Об электронной подписи»;</li>
<li>Федеральный закон от 06.12.2011 № 402-ФЗ «О бухгалтерском учете»;</li>
<li>Федеральный закон от 27.06.2011 № 161-ФЗ «О национальной платежной системе»;</li>
<li>Постановление Правительства Российской Федерации от 15.09.2008 № 687 «Об утверждении положения об особенностях обработки персональных данных, осуществляемой без использования средств автоматизации»;</li>
<li>Постановлением Правительства РФ от 01.11.2012 № 1119 "Об утверждении требований к защите персональных данных при их обработке в информационных системах персональных данных"</li>
<li>иные нормативные правовые акты Российской Федерации и нормативные документы исполнительных органов государственной власти.</li>
</ul>
<p>3.1.2. Устав Оператора.</p>
<p>3.1.3. Договоры, заключаемые между Оператором и Субъектом Персональных данных, в том числе в случае реализации Оператором своего права на уступку прав (требований) по таким договорам, между Оператором и иным лицом, поручившим Оператору Обработку ПДн, а также для заключения договоров, стороной которых являются Субъекты Персональных данных.</p>
<p>3.1.4. Согласие на Обработку ПДн (в случаях, прямо не предусмотренных законодательством Российской Федерации, но соответствующих полномочиям Оператора), в т.ч. согласие соискателей на замещение вакантных должностей на Обработку ПДн, согласие практиканта на Обработку ПДн, согласие работников на Обработку ПДн; согласие клиентов на Обработку ПДн, согласие Пользователей соответствующего Сайта, согласие иных Субъектов Персональных данных.</p>
<p>3.1.5. Договор между оператором и третьим лицом, где последнее поручает Оператору обработку персональных данных Субъекта Персональных данных или передает на основании заключенного договора персональные данные Субъекта Персональных данных.</p>
</section>
<section class="legal-section">
<h2>4. КАТЕГОРИИ СУБЪЕКТОВ ПЕРСОНАЛЬНЫХ ДАННЫХ</h2>
<p>4.1. Оператором осуществляется Обработка полученных в установленном законом порядке ПДн, принадлежащих:</p>
<ul>
<li>Кандидатам на работу и работникам Оператора;</li>
<li>Уволенным работникам Оператора;</li>
<li>Близким родственникам/членам семьи работников Оператора, практикантам;</li>
<li>Потенциальным клиентам, клиентам - физическим лицам, клиентам - индивидуальным предпринимателям;</li>
<li>Физическим лицам, заключившим с Оператором гражданско-правовые договоры;</li>
<li>Пользователям Сайтов Оператора, получателям Заказов;</li>
<li>Клиентам других юридических лиц;</li>
<li>Собственникам Оператора;</li>
<li>Иным субъектам, вступившим или намеревающимися вступить в договорные отношения с Оператором.</li>
</ul>
</section>
<section class="legal-section">
<h2>5. КАТЕГОРИИ ОБРАБАТЫВАЕМЫХ ПЕРСОНАЛЬНЫХ ДАННЫХ</h2>
<p>5.1. Оператор обрабатывает следующие категории ПДн Пользователей:</p>
<ul>
<li>Сведения, полученные при регистрации и/или оформлении Заказа (фамилию, имя, фактический адрес, номер телефона, адрес электронной почты, cookie);</li>
<li>Сведения, полученные при взаимодействии с Пользователями (фамилия, имя, отчество, пол, место рождения, дата рождения, паспортные данные, адрес, контакты);</li>
<li>Сведения о способе доставки и оплаты Заказа;</li>
<li>Сведения о претензиях Пользователя;</li>
<li>Сведения о геолокации (местонахождении).</li>
</ul>
<p>5.2. Персональные данные могут быть получены Оператором путем:</p>
<ul>
<li>Предоставления Субъектами через формы на Сайте или по email;</li>
<li>Получения от третьих лиц (Продавцов, контрагентов) в рамках законодательства РФ.</li>
</ul>
</section>
<section class="legal-section">
<h2>6. ПРИНЦИПЫ, ПОРЯДОК И УСЛОВИЯ ОБРАБОТКИ</h2>
<h3>6.1. Принципы обработки Персональных данных</h3>
<p>Обработка ПДн у Оператора осуществляется на основе следующих принципов:</p>
<ul>
<li>законности и справедливой основы;</li>
<li>ограничения Обработки ПДн достижением конкретных, заранее определенных и законных целей;</li>
<li>недопущения Обработки ПДн, несовместимой с целями сбора ПДн;</li>
<li>обеспечения точности, достаточности и актуальности ПДн;</li>
<li>хранение ПДн не дольше, чем этого требуют цели Обработки;</li>
<li>уничтожения либо обезличивания ПДн по достижении целей их Обработки.</li>
</ul>
<h3>6.2. Обязанности работников Оператора</h3>
<p>Работники Оператора, допущенные к Обработке Персональных данных, обязаны:</p>
<ul>
<li>Знать и выполнять положения законодательства РФ в области ПДн;</li>
<li>Знать и выполнять положения настоящей Политики;</li>
<li>Обрабатывать ПДн только в рамках должностных обязанностей;</li>
<li>Не разглашать ПДн, обрабатываемые Оператором;</li>
<li>Сообщать о действиях, которые могут привести к нарушению Политики.</li>
</ul>
</section>
<section class="legal-section">
<h2>7. ПРАВА СУБЪЕКТА ПЕРСОНАЛЬНЫХ ДАННЫХ</h2>
<h3>7.1. Согласие Субъекта</h3>
<p>Субъект ПДн дает согласие на Обработку свободно, своей волей и в своем интересе.</p>
<h3>7.2. Права Субъекта</h3>
<p>Субъект ПДн имеет право на получение информации о:</p>
<ul>
<li>подтверждение факта Обработки ПДн;</li>
<li>правовые основания и цели Обработки;</li>
<li>применяемые способы Обработки;</li>
<li>сроки Обработки и хранения данных;</li>
<li>уточнение, блокирование или уничтожение данных.</li>
</ul>
<p><strong>Субъект ПДн имеет право отозвать свое Согласие</strong> и потребовать удалить свои ПДн, направив сообщение на: <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a></p>
<p>Субъект также имеет право на защиту своих прав, возмещение убытков и компенсацию морального вреда.</p>
</section>
<section class="legal-section">
<h2>8. ОБЯЗАННОСТИ ОПЕРАТОРА</h2>
<p>8.1. Оператор обязан предоставить Субъекту информацию о обработке его данных при обращении.</p>
<p>8.2. Оператор обеспечивает хранение данных граждан РФ на территории Российской Федерации.</p>
<p>8.3. Оператор несет иные обязанности, установленные ФЗ-152.</p>
</section>
<section class="legal-section">
<h2>9. ОБЕСПЕЧЕНИЕ БЕЗОПАСНОСТИ</h2>
<p>9.1-9.3. Безопасность обеспечивается комплексом организационных и технических мер:</p>
<ul>
<li>назначение ответственных лиц;</li>
<li>ограничение доступа к ПДн;</li>
<li>обучение сотрудников;</li>
<li>учет и хранение носителей с ПДн;</li>
<li>использование антивирусных средств;</li>
<li>средства шифрования и межсетевого экранирования;</li>
<li>физическая защита помещений;</li>
<li>контроль мер безопасности.</li>
</ul>
</section>
<section class="legal-section">
<h2>10. ОТВЕТСТВЕННОСТЬ</h2>
<p>10.1. Лица, виновные в нарушении норм обработки и защиты Персональных данных, несут ответственность согласно законодательству РФ.</p>
</section>
<section class="legal-section">
<h2>11. ЦЕЛИ ОБРАБОТКИ</h2>
<p>11.1. Оператор обрабатывает ПДн для следующих целей:</p>
<ul>
<li>Предоставления доступа к Сайту и личному кабинету;</li>
<li>Исполнения договоров купли-продажи и оказания услуг;</li>
<li>Доставки товаров;</li>
<li>Урегулирования претензий;</li>
<li>Обработки платежей;</li>
<li>Улучшения качества обслуживания;</li>
<li>Получения обратной связи;</li>
<li>Проведения маркетинговых исследований;</li>
<li>Направления рекламных сообщений;</li>
<li>В иных случаях, предусмотренных законодательством РФ.</li>
</ul>
</section>
<section class="legal-section">
<h2>12. АВТОМАТИЧЕСКИ СОБИРАЕМАЯ ИНФОРМАЦИЯ</h2>
<p>12.1. Оператор собирает и обрабатывает:</p>
<ul>
<li>информацию об интересах на основе поисковых запросов;</li>
<li>информацию для формирования рейтинга (отзывы, данные об исполнении Заказов);</li>
<li>статистику об использовании Сайта.</li>
</ul>
<p>12.2. Оператор использует cookies, веб-отметки и другие технологии мониторинга. Эти технологии не дают возможность автоматически получать ПДн.</p>
<p>12.3. Если собранные сведения можно соотнести с личным кабинетом Пользователя, они могут обрабатываться совместно с ПДн.</p>
</section>
<section class="legal-section">
<h2>13. КОНТАКТНАЯ ИНФОРМАЦИЯ</h2>
<p>По всем вопросам обработки персональных данных обращайтесь:</p>
<ul>
<li><strong>Email:</strong> <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a></li>
<li><strong>Телефон (Россия):</strong> <a href="tel:+79264593157">+7 (926) 459-31-57</a></li>
<li><strong>Телефон (Армения):</strong> <a href="tel:+37494861816">+374 94 86 18 16</a></li>
</ul>
<p>Мы ответим в течение 30 дней согласно законодательству РФ.</p>
</section>
</div>
</div>

View File

@@ -1,465 +0,0 @@
<div class="legal-page">
<div class="legal-container">
<h1>СОГЛАШЕНИЕ ПУБЛИЧНОЙ ОФЕРТЫ</h1>
<section class="legal-section">
<h2>Основные понятия</h2>
<p>В данном документе приводятся ключевые термины и пояснения, применяемые в публичном соглашении:</p>
<ul>
<li><strong>Маркетплейс, Интернет-сайт или Сайт</strong> — это комплекс технических и программных средств, предназначенный для функционирования веб-ресурса по адресу <a href="https://dexarmarket.ru">https://dexarmarket.ru</a>. Сайт принадлежит владельцу и служит платформой для организации взаимодействия между независимыми продавцами и покупателями. Сам владелец сайта не занимается продажей товаров и услуг, а предоставляет пространство для размещения объявлений и заключения сделок.</li>
<li><strong>Пользователь</strong> — физлицо, которое пользуется сайтом, регистрируясь и принимая условия данного соглашения.</li>
<li><strong>Личный кабинет</strong> — персональная страница Пользователя, защищённая индивидуальными регистрационными данными (логином и паролем). Логином может выступать электронная почта или мобильный телефон, используемый для авторизации.</li>
<li><strong>Учетные данные</strong> — комбинация имени пользователя (логина) и пароля, создаваемая при регистрации.</li>
<li><strong>Покупатель</strong> — зарегистрированный Пользователь, который сделал заказ через сайт.</li>
<li><strong>Администратор или Владелец Сайта</strong> — юридическое лицо ООО «ИНТ ФИН ЛОГИСТИК», идентификационный налоговый номер (ИНН) 9909697628.</li>
<li><strong>Продавец или Селлер</strong> — физические или юридические лица, предприниматели, предлагающие товары и услуги на ресурсе. Продавцы несут личную ответственность за качество, безопасность и соответствие описания товаров.</li>
<li><strong>Контент Сайта</strong> — совокупные материалы, находящиеся на ресурсе, включая дизайн, тексты, графику, видео, аудиозаписи и прочие объекты.</li>
<li><strong>Товар</strong> — материальные и цифровые продукты, а также услуги, предлагаемые на продажу через сайт.</li>
<li><strong>Цифровой товар</strong> — товары, распространяемые в электронной форме, такие как ПО, подписка на онлайн-курсы, виртуальные активы, музыкальные треки, электронные книги и подобные виды продукции.</li>
<li><strong>Заказ</strong> — оформленное заявление на приобретение товаров или услуг от Покупателя.</li>
<li><strong>Сервис</strong> — специальное программное обеспечение, интегрированное в ресурс, дающее возможность пользоваться функциональностью сайта.</li>
<li><strong>Продукты Владельца Сайта</strong> — информационные и сопутствующие услуги, предоставляемые владельцем сайта.</li>
</ul>
</section>
<section class="legal-section">
<h2>1. Общие положения</h2>
<p>1.1. Настоящим документом устанавливается порядок использования ресурсов, принадлежащих администратору, включая сайт, мобильные версии и приложения, управляемые Администрацией.</p>
<p>1.2. Документ является обязательным соглашением между Пользователем и Владельцем ресурса.</p>
<p>1.3. Настоящее соглашение и информация о продуктах, размещённая на сайте, соответствуют определению публичной оферты согласно статье 435 и пункту 2 статьи 437 ГК РФ.</p>
<p>1.4. Пользователь соглашается с условиями договора автоматически, начиная с первого посещения сайта, регистрации или оформления заказа без авторизации, нажатия кнопок «Оформить заказ», «Отправить сообщение» или «Купить».</p>
<p>1.5. Заключение соглашения путём акцептования оферты не требует подписи сторон и признается действительным в электронном виде.</p>
<p>1.6. Использование сайта подразумевает согласие с условиями соглашения, вступающего в силу сразу после выражения согласия пользователем.</p>
<p>1.7. В случае несогласия с условиями Пользователь обязуется незамедлительно прекратить пользование ресурсом.</p>
<p>1.8. Дополнительно регулирование использования сайта осуществляется <a routerLink="/privacy-policy">Политикой обработки персональных данных</a>.</p>
<p>1.9. Изменения в соглашение могут вноситься Владельцем без предварительного уведомления и становятся обязательными с момента публикации изменений.</p>
<p>1.10. Во время проведения рекламных кампаний могут устанавливаться особые условия оформления заказов, возврата или обмена товаров.</p>
<p>1.14. Оферта предназначена для любых пользователей ресурса, включая юридических лиц и индивидуальных предпринимателей.</p>
</section>
<section class="legal-section">
<h2>2. Предмет соглашения</h2>
<p>2.1. Целью соглашения является предоставление возможности Пользователям покупать товары и услуги, представляемые на ресурсе, а также использование продуктов, предоставляемых Владельцем сайта.</p>
<p>2.2. Соглашение регулирует порядок использования сайта и функций, предоставляемых Владельцем.</p>
<p>2.3. Действие документа распространяется на все типы товаров, услуг и продуктов, имеющихся на сайте.</p>
</section>
<section class="legal-section">
<h2>3. Условия продажи товаров и оказания услуг</h2>
<p><strong>3.1. Принятие условий продажи</strong></p>
<p>Пользователь, делая заказы через маркетплейс, выражает полное согласие с условиями продажи товаров и оказания услуг, определёнными в данном соглашении.</p>
<p><strong>3.2. Заключение договоров</strong></p>
<p>Договор розничной купли-продажи или договор оказания услуг заключается непосредственно между Продавцом и Покупателем с момента выдачи Продавцом кассовых или товарных чеков, подтверждающих оплату. Маркетплейс играет роль информационного посредника, предоставляя инфраструктуру для совершения сделок, но не является участником данного договора. Ответственность за выполнение договора, качество товаров и услуг лежит на Продавце.</p>
<p><strong>3.3. Согласие на обработку контактов</strong></p>
<p>Пользователь даёт согласие на использование его контактных данных (адрес электронной почты, номер телефона) администрацией сайта и Продавцом, а также привлечёнными третьими сторонами для выполнения обязательств перед Покупателем, включая рассылки рекламной и иной информации.</p>
<p><strong>3.4. Привлечение третьих лиц</strong></p>
<p>Пользователь соглашается с возможностью привлечения Продавцом третьих лиц для исполнения договора купли-продажи или оказания услуг, сохраняя ответственность Продавца за выполнение обязательств.</p>
<p><strong>3.5. Права и обязательства по договорам</strong></p>
<p>Права и обязанности по договорам купли-продажи возникают непосредственно у Продавца. Пользователь осознаёт, что Владелец сайта исполняет роль оператора маркетплейса и не несёт ответственности за действия Продавцов, качество товаров, законное основание Продавца осуществлять сделки и фактическое исполнение обязательств.</p>
<p><strong>3.6. Функции владельца сайта</strong></p>
<p>Владелец сайта предоставляет информационное и техническое сопровождение: координирует взаимодействие между Покупателем и Продавцом, передает информацию о заказе, может помогать в урегулировании споров. Тем не менее, ответственность за исполнение договора остаётся за Продавцом.</p>
<p><strong>3.7. Переуступка прав Продавцом</strong></p>
<p>Покупатель осведомлён и соглашается с правом Продавца уступать или передавать свои права и обязанности третьим сторонам.</p>
<p><strong>3.8. Применение законов</strong></p>
<p>Отношения между Пользователем и Продавцом регулируются положениями Федерального закона «О защите прав потребителей» (№ 2300-1 от 07 февраля 1992 года) и Гражданского кодекса РФ.</p>
<p><strong>3.10. Рекламные сообщения</strong></p>
<p>Пользователь дает согласие на получение рекламных сообщений в соответствии с Федеральным законом «О рекламе».</p>
</section>
<section class="legal-section">
<h2>4. Регистрация на сайте и Личный кабинет Пользователя</h2>
<p><strong>4.1. Процедуры регистрации</strong></p>
<p>Пользователю предлагается зарегистрироваться на сайте для полноценного использования отдельных функций и сервисов. Хотя регистрация необязательна для оформления заказа, она создаёт уникальные возможности, включая Личный кабинет.</p>
<p><strong>4.2. Обязанности Пользователя при регистрации</strong></p>
<p>Регистрируясь, Пользователь берёт обязательство предоставлять точную и актуальную информацию, заполняя анкету регистрации. Необходимо поддерживать данные в актуальном состоянии.</p>
<p><strong>4.3. Идентификация пользователя</strong></p>
<p>Любые действия, совершённые с использованием индивидуального логина и пароля, считаются действиями самого Пользователя, пока не доказана противоположная позиция.</p>
<p><strong>4.4. Конфиденциальность учетных данных</strong></p>
<p>Пользователь обязуется держать в тайне логин и пароль, предоставленные при регистрации. При подозрении на нарушение безопасности необходимо срочно проинформировать администрацию сайта письмом на адрес <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a>.</p>
<p><strong>4.7. Подтверждение данных</strong></p>
<p>Владелец сайта имеет право запросить подтверждение предоставленной информации в любой момент.</p>
<p><strong>4.11. Завершение сеанса работы</strong></p>
<p>Пользователь обязан самостоятельно завершать работу в Личном кабинете («Выход»), покидая сайт, для обеспечения безопасности аккаунта.</p>
</section>
<section class="legal-section">
<h2>5. Права и обязанности Владельца сайта</h2>
<p><strong>5.1. Права Владельца сайта</strong></p>
<p>Владелец сайта наделён следующими полномочиями:</p>
<ul>
<li>Устанавливать ограничения в использовании ресурса для всех или отдельных групп пользователей.</li>
<li>Направлять Пользователям информацию о нововведениях и изменениях на сайте.</li>
<li>Изменять поставщика товаров и/или компанию-доставщика без предварительного согласия Покупателя.</li>
<li>Изменять условия проводимых акций в одностороннем порядке.</li>
<li>Ограничивать действия Пользователей, создающих риски для работоспособности сайта.</li>
<li>Проводить технические работы без предупреждения пользователей.</li>
<li>Использовать статистику, собранную на сайте, в собственных интересах.</li>
<li>Менять список товаров и услуг, ценники и условия в любое время.</li>
<li>Отказывать в обслуживании Пользователям, подозреваемым в неправомерных действиях.</li>
</ul>
<p><strong>5.2. Обязанности Владельца сайта</strong></p>
<p>Основной обязанностью Владельца сайта является оказание Пользователям услуг, предусмотренных пунктом 2.1 настоящего соглашения.</p>
</section>
<section class="legal-section">
<h2>6. Права и обязанности Пользователя</h2>
<p><strong>6.1. Обязанности Пользователя</strong></p>
<p>Пользователь обязуется соблюдать ряд важных обязанностей:</p>
<ul>
<li>Ознакомляться с текстом соглашения до момента заключения договора купли-продажи или оказания услуг.</li>
<li>Придерживаться этического поведения при написании отзывов и взаимодействии с персоналом сайта.</li>
<li>Общаться вежливо и уважительно с сотрудниками и коллегами.</li>
<li>Не допускать распространение ненормативной лексики, грубостей и оскорблений.</li>
<li>Не создавать помех нормальной работе сайта и его сервисов.</li>
<li>Не заниматься загрузкой вирусов, вредоносных программ и других опасных файлов.</li>
<li>Не применять запрещённые автоматизированные программы для сбора информации без разрешения Администрации.</li>
<li>Не пытаться получить доступ к чужим учётным данным.</li>
<li>Законно использовать контент сайта и избегать незаконного копирования материалов.</li>
<li>Зарегистрироваться только от собственного имени и не маскироваться под других лиц.</li>
<li>Своевременно оплачивать заказанные товары и услуги в соответствии с соглашением.</li>
<li>Использовать приобретённые товары исключительно для личных нужд, не преследуя коммерческих целей.</li>
<li>Беречь информационную безопасность ресурса, воздерживаясь от попыток взлома или нарушения целостности сайта.</li>
</ul>
<p><strong>6.2. Запрещённые действия Пользователя</strong></p>
<p>Пользователю категорически запрещается:</p>
<ul>
<li>Загрузка и публикация контента, противоречащего закону, содержащего вирусные программы, ложную информацию или уничижительную критику.</li>
<li>Нарушение прав других пользователей и нанесение вреда несовершеннолетним гражданам.</li>
<li>Любое поведение, нарушающее российское законодательство, включая нормы международного права.</li>
</ul>
<p><strong>6.3. Права Пользователя</strong></p>
<p>Пользователь имеет право отказаться от получения рекламных сообщений, воспользовавшись соответствующим инструментом на сайте или направив заявку по электронной почте <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a> или письмом по официальному адресу Владельца сайта.</p>
</section>
<section class="legal-section">
<h2>7. Исключительные права на контент сайта</h2>
<p><strong>7.1. Объекты интеллектуальной собственности</strong></p>
<p>Весь контент, доступный на сайте, включая:</p>
<ul>
<li>элементы дизайна,</li>
<li>текстовые материалы,</li>
<li>графики и изображения,</li>
<li>видеоролики,</li>
<li>компьютерные программы,</li>
<li>базы данных,</li>
<li>другие материалы —</li>
</ul>
<p>является объектом исключительных авторских прав Владельца сайта и других правообладателей.</p>
<p><strong>7.2. Использование контента</strong></p>
<p>Применение контента разрешено только в рамках функциональных возможностей сайта. Любое другое использование элементов сайта или размещённого контента без предварительного разрешения владельцев недопустимо.</p>
<p><strong>7.3. Использование для личного потребления</strong></p>
<p>Пользователь вправе использовать контент сайта для личного некоммерческого использования при условии обязательного сохранения обозначений авторских прав, смежных прав, товарных знаков и прочих уведомлений об авторстве.</p>
</section>
<section class="legal-section">
<h2>8. Сайты и контент третьих лиц</h2>
<p><strong>8.1. Наличие ссылок на внешние ресурсы</strong></p>
<p>Сайт может включать гиперссылки на сторонние ресурсы в Интернете. Эти ресурсы не подвергаются проверке Владельцем сайта на предмет соответствия законодательным нормам или другим критериям. Соответственно, ответственность за содержание и материалы на сайтах третьих лиц не относится к компетенции Владельца сайта.</p>
<p><strong>8.2. Характер ссылок</strong></p>
<p>Ссылки на сторонние сайты, а также упоминания продуктов, услуг или иной информации коммерческого или некоммерческого характера, присутствующие на сайте, не означают одобрения или рекомендаций со стороны Владельца сайта.</p>
<p><strong>8.3. Требования к цитированию</strong></p>
<p>При любом воспроизведении материалов сайта необходимо указывать активную ссылку на источник.</p>
<p><strong>8.4. Интеллектуальная собственность</strong></p>
<p>Логотип, фирменное название, визуальное оформление и общий облик сайта принадлежат интеллектуальным правам Владельца сайта. Их использование без прямой явной санкции от Владельца запрещено.</p>
</section>
<section class="legal-section">
<h2>9. Ответственность сторон</h2>
<p><strong>9.1. Общая ответственность</strong></p>
<p>Сайт является информационно-технологическим ресурсом, обеспечивающим размещение информации о товарах и услугах, а также безопасность совершения сделок. Владелец сайта принимает на себя ответственность за недопущение размещения запрещённых товаров на ресурсе, а также за качество и достоверность информации о товарах и услугах, представленных на платформе.</p>
<p><strong>9.2. Ограничения ответственности</strong></p>
<p>Владелец сайта не гарантирует:</p>
<ul>
<li>Соответствие сайта потребностям пользователя.</li>
<li>Постоянную доступность, скорость и отсутствие ошибок в сервисе.</li>
</ul>
<p><strong>9.3. Последствия использования информации</strong></p>
<p>Вся информация и материалы, получаемые через сайт, используются пользователем на его усмотрение и риск. Пользователь несёт ответственность за возможные негативные последствия использования этих сведений.</p>
<p><strong>9.4. Идентификация участников и контроль Продавцов</strong></p>
<p>Покупатель идентифицируется на основании номера телефона и данных, предоставляемых через Telegram. Каждый Продавец проходит полную процедуру идентификации (онбординг), и его данные доступны Владельцу сайта для использования при возникновении спорных ситуаций. Владелец сайта осуществляет проверку и контроль деятельности Продавцов на платформе.</p>
<p><strong>9.5. Безопасность аккаунта</strong></p>
<p>Пользователь самостоятельно отвечает за сохранение секретности используемых средств доступа к своему профилю.</p>
<p><strong>9.6. Ответственность Продавца</strong></p>
<p>Продавец несёт полную ответственность за качество, безопасность и соответствие реализуемой продукции заявленным характеристикам, а также за убытки, вызванные нарушением обязательств перед Покупателем.</p>
<p><strong>9.7. Ответственность Владельца сайта и порядок урегулирования претензий</strong></p>
<p>Владелец сайта несёт ответственность за качество, безопасность и достоверность информации о товарах и услугах, размещённых на платформе. При этом Владелец сайта не несёт ответственности за:</p>
<ul>
<li>Выполнение или ненадлежащее выполнение Продавцами своих обязательств перед Покупателями.</li>
<li>Повреждение прав третьих лиц, включая интеллектуальную собственность.</li>
<li>Вопросы доставки, комплектации и состояния товаров.</li>
</ul>
<p>Покупатель соглашается, что претензии по качеству, количеству, комплектности товаров и услугам могут быть направлены как Продавцу, так и Администрации сайта. Администрация сайта принимает на себя ответственность за качество и достоверность услуг, предоставляемых через платформу, и активно участвует в урегулировании спорных ситуаций.</p>
<p><strong>9.8. Ответственность за доставку</strong></p>
<p>Ответственность за сроки, условия и качество доставки товаров несут транспортные компании и курьерские службы. Владелец сайта выступает только в качестве информационного посредника и не несёт ответственности за действия служб доставки.</p>
<p><strong>9.9. Ответственность Пользователя перед третьими лицами</strong></p>
<p>Пользователь лично отвечает перед третьими лицами за свои действия, связанные с использованием сайта.</p>
<p><strong>9.10. Форс-мажорные обстоятельства</strong></p>
<p>Работа сайта может быть приостановлена в случае непредвиденных обстоятельств, аварий, сбоев оборудования или вмешательств третьих лиц без предварительных уведомлений.</p>
<p><strong>9.11. Ответственность за рекламу</strong></p>
<p>Ответственность за содержание рекламных объявлений несут Продавцы, размещающие информацию о своих товарах и услугах. Владелец сайта предоставляет только техническую платформу для размещения информации.</p>
<p><strong>9.12. Стихийные бедствия и чрезвычайные события</strong></p>
<p>Ни одна сторона не несёт ответственности за невыполнение обязательств, вызванное обстоятельствами непреодолимой силы, такими как природные катастрофы, войны или техногенные аварии.</p>
</section>
<section class="legal-section">
<h2>10. Товар и порядок совершения покупки</h2>
<p><strong>10.1. Оформление заказа</strong></p>
<p>Заказ оформляется Покупателем в строгом соответствии с процедурой, установленной на сайте.</p>
<p><strong>10.2. Ответственность за некорректные данные</strong></p>
<p>Покупатель принимает на себя риски неполучения заказа, связанные с ошибочной или неполной информацией, предоставленной при оформлении заказа.</p>
<p><strong>10.3. Предварительная информация о доставке</strong></p>
<p>После формирования заказа Покупатель получает уведомление о примерной дате доставки через электронную почту или телефон, указанный при регистрации.</p>
<p><strong>10.4. Конкретизация времени доставки</strong></p>
<p>Перед доставкой сотрудник магазина свяжется с Покупателем по телефону для уточнения точного времени доставки.</p>
<p><strong>10.5. Уточнение ожидаемого времени доставки</strong></p>
<p>Менеджер по заказу уведомляет Покупателя о планируемой дате передачи заказа в службу доставки через электронную почту или звонок.</p>
<p><strong>10.6. Возможность нехватки товара</strong></p>
<p>Продавец не гарантирует постоянное наличие заказанного товара на складе на момент обработки заказа.</p>
<p><strong>10.11. Законодательные рамки поставок</strong></p>
<p>Поставка товаров осуществляется в соответствии с законами Российской Федерации и страны происхождения Продавца.</p>
<p><strong>10.12. Применимость российского законодательства</strong></p>
<p>Физические товары поступают к покупателю в соответствии с законодательством Российской Федерации.</p>
</section>
<section class="legal-section">
<h2>11. Доставка заказа</h2>
<p><strong>11.1. Способы и сроки доставки</strong></p>
<p>Способы и ориентировочные сроки доставки товаров указаны на сайте. Фактические сроки могут быть уточнены при подтверждении заказа сотрудником call-центра или представителем Продавца.</p>
<p><strong>11.2. Подтверждение поставки цифровых товаров</strong></p>
<p>Факт поставки цифровых товаров подтверждается отправкой электронного письма на указанный при регистрации адрес с приложением цифрового файла или кода. Получение такого письма означает выполнение услуги по поставке цифровых товаров.</p>
<p>Физический товар считается доставленным в момент его реальной передачи Покупателю или назначенному им получателю согласно условиям выбранной доставки.</p>
<p><strong>11.3. Территория доставки</strong></p>
<p>Территориальные границы доставки товаров, предлагаемых Продавцом, опубликованы на сайте.</p>
<p><strong>11.4. Прием товара</strong></p>
<p>При доставке товар передается Покупателю или указанному в заказе третьему лицу.</p>
<p><strong>11.5. Проверка личности</strong></p>
<p>При передаче предварительно оплаченного заказа служба доставки вправе попросить предъявить удостоверение личности для исключения риска мошенничества.</p>
<p><strong>11.6. Переход риска утраты товара</strong></p>
<p>Риск случайной потери или порчи товара переходит к Покупателю в момент непосредственной передачи заказа.</p>
<p><strong>11.7. Расчёт стоимости доставки</strong></p>
<p>Стоимость доставки рассчитывается индивидуально для каждого заказа, учитывая вес, регион и выбранный способ транспортировки.</p>
<p><strong>11.8. Завершение обязательств Продавца</strong></p>
<p>Продавец выполнил свои обязательства по передаче товара, если товар передан Покупателю курьером или выдан Покупателем в почтовом отделении или другом согласованном месте.</p>
<p><strong>11.9. Осмотр товара при получении</strong></p>
<p>При получении товара Покупатель вправе визуально оценить его состояние и при необходимости провести осмотр в присутствии сотрудника Продавца или курьера.</p>
<p><strong>11.10. Проверка товара при приеме от курьера</strong></p>
<p>Покупатель может осмотреть полученный товар и убедиться в его соответствии заявленному количеству, ассортименту и комплектации.</p>
<p><strong>11.11. Лимиты времени для курьерской доставки</strong></p>
<p>Курьеры имеют ограниченное время пребывания по адресу Покупателя — максимум 20 минут.</p>
<p><strong>11.12. Сертификация товара</strong></p>
<p>Товары, размещённые на сайте, соответствуют государственным стандартам (ГОСТ) и техническим условиям (ТУ), что подтверждено сертификатами и прочими необходимыми документами.</p>
</section>
<section class="legal-section">
<h2>12. Оплата товара</h2>
<p><strong>12.1. Валюта и структура цены</strong></p>
<p>Цена товаров, размещённых на сайте, выражается в рублях Российской Федерации и включает все налоговые отчисления и обязательные сборы.</p>
<p><strong>12.2. Возможные ошибки в ценах</strong></p>
<p>Иногда на сайте могут возникать технические ошибки, приводящие к неверному отражению цен на товары или стоимости доставки. При обнаружении таких ошибок Продавец уведомляет Покупателя и уточняет цену, оставляя Покупателю выбор подтвердить заказ по обновлённым расценкам или отменить сделку.</p>
<p><strong>12.3. Изменение цен</strong></p>
<p>Продавец вправе изменять цены на товары в одностороннем порядке. Однако если товар уже оплачен Покупателем, изменение цены на этот товар не допускается.</p>
<p><strong>12.4. Способы оплаты</strong></p>
<p>Варианты оплаты, доступные Покупателю, приведены на сайте в процессе оформления заказа. Метод оплаты принимается на основании выбора Пользователя из числа доступных опций.</p>
<p><strong>12.6. Особенности оплаты с помощью банковских карт</strong></p>
<p>При оплате товаров с использованием банковских карт действуют следующие правила:</p>
<ul>
<li>Платежи осуществляются держателем карты или лицом, имеющим доверенность.</li>
<li>Авторизация операций проходит через банковскую организацию.</li>
<li>Продавец вправе запросить документ, удостоверяющий личность, для подтверждения полномочий на использование карты.</li>
<li>При осуществлении оплаты банковской картой на сайте Покупатель соглашается на получение кассового чека в электронной форме по электронной почте.</li>
<li>Заказы, оплаченные картой, проверяются Продавцом для предотвращения мошеннических действий.</li>
<li>Сбор и хранение данных банковских карт Покупателей не производятся ни Владельцем сайта, ни Продавцом.</li>
</ul>
<p><strong>12.7. Скидки и бонусы</strong></p>
<p>Продавец вправе назначать скидки и вводить бонусные программы. Типы скидок, порядок и условия начисления устанавливаются Продавцом и публикуются на сайте.</p>
<p><strong>12.13. Ограничения по сумме оплаты наличными средствами</strong></p>
<p>Оплата товара наличными средствами не осуществляется.</p>
<p><strong>12.14. Сроки возврата денежных средств</strong></p>
<p>Требования Покупателя о возврате средств за товар удовлетворяются в течение 10 дней с момента представления соответствующего заявления.</p>
</section>
<section class="legal-section">
<h2>13. Возврат и обмен товара</h2>
<p><strong>13.1. Общие правила возврата</strong></p>
<p>Цифровые товары (предоставляемые в электронной форме) не подлежат возврату согласно российскому законодательству. Возврат физических товаров осуществляется в соответствии с разделом <a routerLink="/return-policy">«Политика возврата»</a> и действующими законами о правах потребителей.</p>
<p><strong>13.2. Возврат товара</strong></p>
<p>Возврат или замена товаров, представленных на сайте и подлежащих возврату, происходят в соответствии с данным соглашением и законодательством Российской Федерации.</p>
<p><strong>13.4. Акционные наборы</strong></p>
<p>При приобретении набора товаров по акции с предоставлением скидки возврат или обмен возможен только в комплексе. Отдельные товары из комплекта вернуть нельзя.</p>
<p><strong>13.5. Компенсация затрат на доставку</strong></p>
<p>При возврате качественного товара Продавец или Владелец сайта вправе взыскать с Покупателя затраты на доставку товара.</p>
<p><strong>13.6. Сроки удовлетворения требований</strong></p>
<p>Заявления о возврате средств удовлетворяются в течение 10 дней с момента подачи.</p>
<p><strong>13.6.7. Документация при возврате товара</strong></p>
<p>При возврате товара Покупатель обязан предоставить следующие документы:</p>
<ul>
<li>Заявление на возврат.</li>
<li>Копию квитанции об оплате или чек.</li>
<li>Копию акта приема-передачи (опись вложения).</li>
</ul>
<p><strong>13.6.9. Механизм возврата средств</strong></p>
<p>Возврат средств осуществляется путем возвращения стоимости оплаченного товара. Способ возврата указывается в заявлении на возврат.</p>
</section>
<section class="legal-section">
<h2>14. Срок действия соглашения</h2>
<p><strong>14.1. Начало и прекращение действия</strong></p>
<p>Соглашение становится активным с момента его принятия (акцепта) Пользователем или Покупателем и действует вплоть до момента отзыва акцепта публичной оферты. Отзыв оферты влечет немедленное прекращение действия соглашения.</p>
<p><strong>14.2. Право отзыва оферты</strong></p>
<p>Владелец сайта имеет право отозвать данное предложение в порядке, предусмотренном статьей 436 Гражданского кодекса Российской Федерации.</p>
</section>
<section class="legal-section">
<h2>15. Порядок разрешения споров и урегулирования претензий</h2>
<p><strong>15.1. Добровольное урегулирование споров</strong></p>
<p>В случае возникновения разногласий между Пользователем и Владельцем сайта, связанных с исполнением условий соглашения, обе стороны обязаны попытаться урегулировать проблему путем взаимных консультаций и переговоров. Установлен обязательный досудебный порядок рассмотрения споров.</p>
<p><strong>15.2. Претензионный порядок</strong></p>
<p>Процедура рассмотрения претензий предусматривает следующие этапы:</p>
<ul>
<li>Пользователь, полагающий, что его права были нарушены действием или бездействием Владельца сайта, направляет соответствующую претензию, содержащую описание сути претензии.</li>
<li>В течение 25 рабочих дней с момента получения претензии Владельцем сайта последний обязан подготовить ответ и разъяснить свою позицию.</li>
<li>Если достичь компромисса не удается, спор рассматривается в судебном порядке в соответствии с пунктом 15.5 соглашения.</li>
</ul>
<p><strong>15.3. Рассмотрение претензий</strong></p>
<p>Владельцем сайта не принимаются к рассмотрению анонимные претензии или жалобы, содержащие недостаточно информации для идентификации заявителя.</p>
<p><strong>15.5. Судебное рассмотрение споров</strong></p>
<p>Если переговоры и претензионный порядок не приводят к соглашению, спор решается в судебном порядке по месту нахождения Владельца сайта.</p>
</section>
<section class="legal-section">
<h2>16. Прочие условия</h2>
<p><strong>16.1. Действие соглашения</strong></p>
<p>Данный документ представляет собой официальное соглашение между Пользователем и Владельцем сайта относительно использования ресурса и замещает собой все предшествующие договоренности.</p>
<p><strong>16.2. Согласие с условиями</strong></p>
<p>Пользователь, продолжая использовать сайт, выражает своё согласие с условиями соглашения. Несогласие предполагает удаление личного кабинета.</p>
<p><strong>16.3. Применимое законодательство</strong></p>
<p>Вопросы, не урегулированные соглашением, разрешаются в соответствии с законодательством Армении.</p>
<p><strong>16.4. Определение термина «Законодательство»</strong></p>
<p>Термин «законодательство» по всему тексту соглашения, если специально не указано иначе, подразумевает законы Армении.</p>
<p><strong>16.5. Бесплатные услуги</strong></p>
<p>Бесплатные услуги, предоставляемые в рамках соглашения, не предполагают применение норм законодательства о защите прав потребителей к взаимоотношениям между Пользователем и Продавцом.</p>
<p><strong>16.6. Отсутствующие отношения</strong></p>
<p>Никакие положения соглашения не могут трактоваться как установление агентских связей, партнёрства, совместного предприятия, трудовых отношений или иных видов взаимоотношений, прямо не предусмотренных соглашением.</p>
<p><strong>16.7. Признание недействительности пунктов</strong></p>
<p>Признание одного или нескольких положений соглашения недействительным не влияет на законную силу и применимость оставшихся пунктов.</p>
<p><strong>16.8. Реакция на нарушения</strong></p>
<p>Невмешательство Владельца сайта в случае нарушений соглашений Пользователями не препятствует последующим мерам защиты интересов Владельца позже.</p>
</section>
</div>
</div>

View File

@@ -1,134 +0,0 @@
<div class="legal-page">
<div class="legal-container">
<h1>Политика возврата товаров</h1>
<section class="legal-section">
<h2>1. Общие положения</h2>
<p>1.1. Настоящий документ устанавливает правила возврата товаров и отказ от услуг, приобретенных через маркетплейс DexarMarket.</p>
<p>1.2. Маркетплейс выполняет лишь роль информационного посредника, и все вопросы возврата регулируются между Покупателем и Продавцом в соответствии с нормами российского законодательства.</p>
<p>1.3. Возврат товаров надлежащего качества регламентируется статьей 26.1 Закона РФ «О защите прав потребителей».</p>
<p>1.4. Возврат некачественных товаров подчиняется статьям 1824 Закона РФ «О защите прав потребителей».</p>
<p>1.5. Особенности возврата цифровых товаров определены российским законодательством.</p>
</section>
<section class="legal-section">
<h2>2. Сроки возврата</h2>
<p><strong>2.1. Товары надлежащего качества:</strong></p>
<ul>
<li><strong>Дистанционный способ приобретения:</strong> 7 дней с момента получения товара.</li>
<li><strong>До передачи товара:</strong> в любое время.</li>
<li><strong>Без письменного извещения о правилах возврата:</strong> 3 месяца с момента получения.</li>
</ul>
<p><strong>2.2. Товары ненадлежащего качества:</strong></p>
<ul>
<li>Внутри установленного гарантийного срока.</li>
<li>Если гарантия не указана: 2 года с момента передачи товара.</li>
<li>Для существенных дефектов: весь срок службы товара.</li>
</ul>
<p><strong>2.3. Цифровые товары:</strong></p>
<p>Возврат доступен только до начала скачивания или активации продукта. После начала использования возврат невозможен (за исключением случаев наличия значительных дефектов, мешающих нормальному применению товара).</p>
</section>
<section class="legal-section">
<h2>3. Условия возврата товаров надлежащего качества</h2>
<p>Вернуть товар можно при выполнении следующих требований:</p>
<ul>
<li>Сохранён внешний вид и потребительские характеристики товара.</li>
<li>Полностью сохранена оригинальная упаковка и вся комплектация.</li>
<li>Сохранены все заводские ярлыки, пломбы и наклейки.</li>
<li>Товар не использовался и не имеет следов износа.</li>
<li>Имеются доказательства покупки (чек, квитанция и т.д.).</li>
</ul>
<p>Покупатель оплачивает расходы на доставку при возврате качественного товара, если иное не оговорено отдельно с Продавцом.</p>
<p>Продавец обязан возместить деньги за качественный товар в течение 10 дней после подачи заявления о возврате.</p>
</section>
<section class="legal-section">
<h2>4. Категории товаров, не подлежащих возврату</h2>
<p>Согласно Постановлению Правительства РФ №2463 от 31 декабря 2020 г., нижеперечисленные группы товаров надлежащего качества не подлежат возврату:</p>
<ul>
<li>Медицинские товары для домашнего пользования.</li>
<li>Предметы индивидуальной гигиены (расчёски, зубные щётки и т.д.).</li>
<li>Парфюмерия и косметика.</li>
<li>Метражные ткани, нити, ленты и аналогичные продукты.</li>
<li>Бельевые изделия, нижнее бельё, колготки.</li>
<li>Посуда и столовые принадлежности одноразового использования.</li>
<li>Бытовая химия, удобрения и химикаты.</li>
<li>Мебель.</li>
<li>Украшения и ювелирные изделия.</li>
<li>Автотранспортные средства и запчасти.</li>
<li>Сложнотехнические бытовые товары, имеющие гарантию.</li>
<li>Гражданское оружие и боеприпасы.</li>
<li>Животные и растения.</li>
<li>Периодически не выпускающиеся издания (книги, журналы, альбомы).</li>
</ul>
<p>Данные товары допускаются к возврату только при выявлении брака или дефекта.</p>
</section>
<section class="legal-section">
<h2>5. Процедура возврата</h2>
<p>Алгоритм возврата выглядит следующим образом:</p>
<ol>
<li>Связаться с Продавцом через сайт или предоставленный контакт.</li>
<li>Сообщить причину возврата и представить доказательства неисправности (фотографии, видеозаписи).</li>
<li>Получить инструкцию по отправке товара назад.</li>
<li>Упаковать товар в оригинальную коробку вместе с аксессуарами.</li>
<li>Отправить товар установленным методом.</li>
<li>Приложить почтовый трек-номер Продавцу.</li>
<li>Ждать проверки товара Продавцом (до 10 дней).</li>
<li>Деньги будут возвращены Покупателю.</li>
</ol>
<p>Маркетплейс готов поддержать разрешение конфликта, если такая необходимость возникнет.</p>
</section>
<section class="legal-section">
<h2>6. Возврат денежных средств</h2>
<p>Денежные средства возвращаются таким же способом, каким производилась оплата:</p>
<ul>
<li>Через банковскую карту.</li>
<li>Электронный кошелёк.</li>
<li>По ссылке на оплату.</li>
</ul>
<p><strong>Срок возврата:</strong></p>
<ul>
<li><strong>Качественный товар:</strong> 10 дней с момента принятия Продавцом заявления.</li>
<li><strong>Некачественный товар:</strong> 10 дней с момента обращения Покупателя.</li>
</ul>
<p>Покупатель вправе требовать возмещения стоимости дефектного товара и компенсации расходов на доставку.</p>
</section>
<section class="legal-section">
<h2>7. Обмен товара</h2>
<p>Если товар надлежащего качества не подходит по форме, размерам или характеристикам, Покупатель может обменять его на аналогичный продукт у Продавца.</p>
<p>Если подходящего товара нет в наличии, Покупатель вправе отказаться от покупки и вернуть потраченные средства.</p>
</section>
<section class="legal-section">
<h2>8. Гарантийное обслуживание</h2>
<p>Информация о гарантийных обязательствах доступна в соответствующем разделе каталога или у Продавца.</p>
<p>Гарантия выполняется самим Продавцом или официальным сервисом производителя.</p>
<p>Гарантийный случай не действует при механических повреждениях, неправильном использовании или самостоятельном ремонте.</p>
</section>
<section class="legal-section">
<h2>9. Ответственность сторон</h2>
<p>Продавец отвечает за качество товара и своевременность возврата средств.</p>
<p>Покупатель обязан сохранять целостность упаковки и комплектность товара до момента возврата.</p>
<p>Маркетплейс, выступая посредником, не несёт ответственности за невыполнение Продавцом обязательств, но помогает разрешать конфликты.</p>
</section>
<section class="legal-section">
<h2>10. Контактная информация</h2>
<p>Вопросы по возврату товаров можно задать Продавцу напрямую, контактные данные предоставляются в заказе.</p>
<p>Обращаясь к администрации Маркетплейса для разрешения разногласий:</p>
<ul>
<li><strong>Email Маркетплейса:</strong> <a href="mailto:info@dexarmarket.ru">info@dexarmarket.ru</a></li>
<li><strong>Тема письма:</strong> «Спор с Продавцом — №Заказа»</li>
<li><strong>Необходимые файлы:</strong> копии писем, фотографии товара, чек об оплате.</li>
</ul>
<p>Если конфликт невозможно разрешить мирно, Покупатель вправе подать жалобу в Роспотребнадзор или суд по месту расположения Продавца.</p>
</section>
</div>
</div>

View File

@@ -1,9 +1,10 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
@Component({ @Component({
selector: 'app-about-novo', selector: 'app-about-novo',
imports: [], imports: [],
templateUrl: './about.component.html', templateUrl: './about.component.html',
styleUrls: ['../../../../../pages/info/about/about.component.scss'] styleUrls: ['../../../../../pages/info/about/about.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class AboutNovoComponent {} export class AboutNovoComponent {}

View File

@@ -1,9 +1,10 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
@Component({ @Component({
selector: 'app-contacts-novo', selector: 'app-contacts-novo',
imports: [], imports: [],
templateUrl: './contacts.component.html', templateUrl: './contacts.component.html',
styleUrls: ['../../../../../pages/info/contacts/contacts.component.scss'] styleUrls: ['../../../../../pages/info/contacts/contacts.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class ContactsNovoComponent {} export class ContactsNovoComponent {}

View File

@@ -1,9 +1,10 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
@Component({ @Component({
selector: 'app-delivery-novo', selector: 'app-delivery-novo',
imports: [], imports: [],
templateUrl: './delivery.component.html', templateUrl: './delivery.component.html',
styleUrls: ['../../../../../pages/info/delivery/delivery.component.scss'] styleUrls: ['../../../../../pages/info/delivery/delivery.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class DeliveryNovoComponent {} export class DeliveryNovoComponent {}

View File

@@ -1,9 +1,10 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
@Component({ @Component({
selector: 'app-faq-novo', selector: 'app-faq-novo',
imports: [], imports: [],
templateUrl: './faq.component.html', templateUrl: './faq.component.html',
styleUrls: ['../../../../../pages/info/faq/faq.component.scss'] styleUrls: ['../../../../../pages/info/faq/faq.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class FaqNovoComponent {} export class FaqNovoComponent {}

View File

@@ -1,9 +1,10 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
@Component({ @Component({
selector: 'app-guarantee-novo', selector: 'app-guarantee-novo',
imports: [], imports: [],
templateUrl: './guarantee.component.html', templateUrl: './guarantee.component.html',
styleUrls: ['../../../../../pages/info/guarantee/guarantee.component.scss'] styleUrls: ['../../../../../pages/info/guarantee/guarantee.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class GuaranteeNovoComponent {} export class GuaranteeNovoComponent {}

View File

@@ -1,9 +1,10 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
@Component({ @Component({
selector: 'app-company-details-novo', selector: 'app-company-details-novo',
imports: [], imports: [],
templateUrl: './company-details.component.html', templateUrl: './company-details.component.html',
styleUrls: ['../../../../../pages/legal/company-details/company-details.component.scss'] styleUrls: ['../../../../../pages/legal/company-details/company-details.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class CompanyDetailsNovoComponent {} export class CompanyDetailsNovoComponent {}

View File

@@ -1,9 +1,10 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
@Component({ @Component({
selector: 'app-payment-terms-novo', selector: 'app-payment-terms-novo',
imports: [], imports: [],
templateUrl: './payment-terms.component.html', templateUrl: './payment-terms.component.html',
styleUrls: ['../../../../../pages/legal/payment-terms/payment-terms.component.scss'] styleUrls: ['../../../../../pages/legal/payment-terms/payment-terms.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class PaymentTermsNovoComponent {} export class PaymentTermsNovoComponent {}

View File

@@ -1,9 +1,10 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
@Component({ @Component({
selector: 'app-privacy-policy-novo', selector: 'app-privacy-policy-novo',
imports: [], imports: [],
templateUrl: './privacy-policy.component.html', templateUrl: './privacy-policy.component.html',
styleUrls: ['../../../../../pages/legal/privacy-policy/privacy-policy.component.scss'] styleUrls: ['../../../../../pages/legal/privacy-policy/privacy-policy.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class PrivacyPolicyNovoComponent {} export class PrivacyPolicyNovoComponent {}

View File

@@ -1,9 +1,10 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
@Component({ @Component({
selector: 'app-public-offer-novo', selector: 'app-public-offer-novo',
imports: [], imports: [],
templateUrl: './public-offer.component.html', templateUrl: './public-offer.component.html',
styleUrls: ['../../../../../pages/legal/public-offer/public-offer.component.scss'] styleUrls: ['../../../../../pages/legal/public-offer/public-offer.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class PublicOfferNovoComponent {} export class PublicOfferNovoComponent {}

View File

@@ -1,9 +1,10 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
@Component({ @Component({
selector: 'app-return-policy-novo', selector: 'app-return-policy-novo',
imports: [], imports: [],
templateUrl: './return-policy.component.html', templateUrl: './return-policy.component.html',
styleUrls: ['../../../../../pages/legal/return-policy/return-policy.component.scss'] styleUrls: ['../../../../../pages/legal/return-policy/return-policy.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class ReturnPolicyNovoComponent {} export class ReturnPolicyNovoComponent {}

View File

@@ -1,4 +1,4 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
import { Location } from '@angular/common'; import { Location } from '@angular/common';
import { environment } from '../../../environments/environment'; import { environment } from '../../../environments/environment';
@@ -55,7 +55,8 @@ import { environment } from '../../../environments/environment';
} }
} }
} }
`] `],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class BackButtonComponent { export class BackButtonComponent {
isnovo = environment.theme === 'novo'; isnovo = environment.theme === 'novo';

View File

@@ -1,8 +1,9 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
@Component({ @Component({
selector: 'app-empty-cart-icon', selector: 'app-empty-cart-icon',
templateUrl: './empty-cart-icon.component.html', templateUrl: './empty-cart-icon.component.html',
styleUrls: ['./empty-cart-icon.component.scss'] styleUrls: ['./empty-cart-icon.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class EmptyCartIconComponent {} export class EmptyCartIconComponent {}

View File

@@ -1,4 +1,4 @@
import { Component, ChangeDetectionStrategy } from '@angular/core'; import { Component, ChangeDetectionStrategy, Renderer2, inject, DOCUMENT } from '@angular/core';
import { Router, RouterLink, RouterLinkActive } from '@angular/router'; import { Router, RouterLink, RouterLinkActive } from '@angular/router';
import { CartService } from '../../services'; import { CartService } from '../../services';
import { environment } from '../../../environments/environment'; import { environment } from '../../../environments/environment';
@@ -19,18 +19,25 @@ export class HeaderComponent {
logo = environment.logo; logo = environment.logo;
isnovo = environment.theme === 'novo'; isnovo = environment.theme === 'novo';
private renderer = inject(Renderer2);
private document = inject(DOCUMENT);
constructor(private cartService: CartService, private router: Router) { constructor(private cartService: CartService, private router: Router) {
this.cartItemCount = this.cartService.itemCount; this.cartItemCount = this.cartService.itemCount;
} }
toggleMenu(): void { toggleMenu(): void {
this.menuOpen = !this.menuOpen; this.menuOpen = !this.menuOpen;
document.body.classList.toggle('dexar-menu-open', this.menuOpen); if (this.menuOpen) {
this.renderer.addClass(this.document.body, 'dexar-menu-open');
} else {
this.renderer.removeClass(this.document.body, 'dexar-menu-open');
}
} }
closeMenu(): void { closeMenu(): void {
this.menuOpen = false; this.menuOpen = false;
document.body.classList.remove('dexar-menu-open'); this.renderer.removeClass(this.document.body, 'dexar-menu-open');
} }
navigateToSearch(): void { navigateToSearch(): void {
@@ -41,7 +48,7 @@ export class HeaderComponent {
this.closeMenu(); this.closeMenu();
this.router.navigate(['/']).then(() => { this.router.navigate(['/']).then(() => {
setTimeout(() => { setTimeout(() => {
document.getElementById('catalog')?.scrollIntoView({ behavior: 'smooth' }); this.document.getElementById('catalog')?.scrollIntoView({ behavior: 'smooth' });
}, 100); }, 100);
}); });
} }

View File

@@ -21,7 +21,7 @@ export class ItemsCarouselComponent implements OnInit {
loading = signal(true); loading = signal(true);
isnovo = environment.theme === 'novo'; isnovo = environment.theme === 'novo';
responsiveOptions: any[] | undefined; responsiveOptions: { breakpoint: string; numVisible: number; numScroll: number }[] | undefined;
constructor( constructor(
private apiService: ApiService, private apiService: ApiService,
@@ -68,7 +68,7 @@ export class ItemsCarouselComponent implements OnInit {
]; ];
} }
getSeverity(remainings: string) { getSeverity(remainings: string): 'success' | 'info' | 'warn' | 'danger' | 'secondary' | 'contrast' {
switch (remainings) { switch (remainings) {
case 'high': case 'high':
return 'success'; return 'success';

View File

@@ -1,4 +1,4 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
import { environment } from '../../../environments/environment'; import { environment } from '../../../environments/environment';
@Component({ @Component({
@@ -10,7 +10,8 @@ import { environment } from '../../../environments/environment';
height: 100%; height: 100%;
object-fit: contain; object-fit: contain;
} }
`] `],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class LogoComponent { export class LogoComponent {
brandName = environment.brandName; brandName = environment.brandName;

View File

@@ -2,7 +2,7 @@ import { HttpInterceptorFn, HttpResponse } from '@angular/common/http';
import { of } from 'rxjs'; import { of } from 'rxjs';
import { tap } from 'rxjs/operators'; import { tap } from 'rxjs/operators';
const cache = new Map<string, { response: HttpResponse<any>, timestamp: number }>(); const cache = new Map<string, { response: HttpResponse<unknown>, timestamp: number }>();
const CACHE_DURATION = 5 * 60 * 1000; // 5 минут const CACHE_DURATION = 5 * 60 * 1000; // 5 минут
export const cacheInterceptor: HttpInterceptorFn = (req, next) => { export const cacheInterceptor: HttpInterceptorFn = (req, next) => {
@@ -17,6 +17,9 @@ export const cacheInterceptor: HttpInterceptorFn = (req, next) => {
return next(req); return next(req);
} }
// Cleanup expired entries before checking
cleanupExpiredCache();
const cachedResponse = cache.get(req.url); const cachedResponse = cache.get(req.url);
// Проверяем наличие и актуальность кэша // Проверяем наличие и актуальность кэша
@@ -25,7 +28,6 @@ export const cacheInterceptor: HttpInterceptorFn = (req, next) => {
if (age < CACHE_DURATION) { if (age < CACHE_DURATION) {
return of(cachedResponse.response.clone()); return of(cachedResponse.response.clone());
} else { } else {
// Кэш устарел, удаляем
cache.delete(req.url); cache.delete(req.url);
} }
} }
@@ -43,19 +45,16 @@ export const cacheInterceptor: HttpInterceptorFn = (req, next) => {
); );
}; };
// Функция для очистки кэша (можно использовать при необходимости) /** Clear all cached responses */
export function clearCache(): void { export function clearCache(): void {
cache.clear(); cache.clear();
// console.log('[Cache] Cache cleared');
} }
// Функция для очистки устаревшего кэша function cleanupExpiredCache(): void {
export function cleanupExpiredCache(): void {
const now = Date.now(); const now = Date.now();
for (const [url, data] of cache.entries()) { for (const [url, data] of cache.entries()) {
if (now - data.timestamp >= CACHE_DURATION) { if (now - data.timestamp >= CACHE_DURATION) {
cache.delete(url); cache.delete(url);
} }
} }
// console.log('[Cache] Expired cache cleaned up');
} }

View File

@@ -3,7 +3,7 @@ export interface Category {
name: string; name: string;
parentID: number; parentID: number;
icon?: string; icon?: string;
wideBanner?: string | boolean; wideBanner?: string;
itemCount?: number; itemCount?: number;
priority?: number; priority?: number;
} }

View File

@@ -5,7 +5,7 @@ export interface Photo {
type?: string; type?: string;
} }
export interface Callback { export interface Review {
rating?: number; rating?: number;
content?: string; content?: string;
userID?: string; userID?: string;
@@ -13,6 +13,9 @@ export interface Callback {
timestamp?: string; timestamp?: string;
} }
/** @deprecated Use {@link Review} instead */
export type Callback = Review;
export interface Question { export interface Question {
question: string; question: string;
answer: string; answer: string;
@@ -31,10 +34,9 @@ export interface Item {
discount: number; discount: number;
remainings?: string; remainings?: string;
rating: number; rating: number;
callbacks: Callback[] | null; callbacks: Review[] | null;
questions: Question[] | null; questions: Question[] | null;
partnerID?: string; partnerID?: string;
quantity?: number; // For cart items
} }
export interface CartItem extends Item { export interface CartItem extends Item {

View File

@@ -1,4 +1,4 @@
import { Component, computed, ChangeDetectionStrategy, signal, OnDestroy, OnInit } from '@angular/core'; import { Component, computed, ChangeDetectionStrategy, signal, OnDestroy } from '@angular/core';
import { DecimalPipe } from '@angular/common'; import { DecimalPipe } from '@angular/common';
import { Router, RouterLink } from '@angular/router'; import { Router, RouterLink } from '@angular/router';
import { FormsModule } from '@angular/forms'; import { FormsModule } from '@angular/forms';
@@ -17,7 +17,7 @@ import { getDiscountedPrice, getMainImage, trackByItemId } from '../../utils/ite
styleUrls: ['./cart.component.scss'], styleUrls: ['./cart.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class CartComponent implements OnInit, OnDestroy { export class CartComponent implements OnDestroy {
items; items;
itemCount; itemCount;
totalPrice; totalPrice;
@@ -59,10 +59,6 @@ export class CartComponent implements OnInit, OnDestroy {
this.totalPrice = this.cartService.totalPrice; this.totalPrice = this.cartService.totalPrice;
} }
ngOnInit(): void {
// Component initialized
}
ngOnDestroy(): void { ngOnDestroy(): void {
this.stopPolling(); this.stopPolling();
if (this.closeTimeout) { if (this.closeTimeout) {
@@ -109,16 +105,16 @@ export class CartComponent implements OnInit, OnDestroy {
}; };
const cleanup = () => { const cleanup = () => {
document.removeEventListener('touchmove', onMove as any); document.removeEventListener('touchmove', onMove);
document.removeEventListener('touchend', cleanup); document.removeEventListener('touchend', cleanup);
}; };
document.addEventListener('touchmove', onMove as any); document.addEventListener('touchmove', onMove);
document.addEventListener('touchend', cleanup); document.addEventListener('touchend', cleanup);
} }
clearCart(): void { clearCart(): void {
if (confirm('<EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>, <20><><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>?')) { if (confirm('Вы уверены, что хотите очистить корзину?')) {
this.cartService.clearCart(); this.cartService.clearCart();
} }
} }
@@ -129,7 +125,7 @@ export class CartComponent implements OnInit, OnDestroy {
checkout(): void { checkout(): void {
if (!this.termsAccepted) { if (!this.termsAccepted) {
alert('<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>, <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>, <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>.'); alert('Пожалуйста, примите условия оферты, политику возврата и возврата для подтверждения оформления заказа.');
return; return;
} }
this.openPaymentPopup(); this.openPaymentPopup();
@@ -251,7 +247,7 @@ export class CartComponent implements OnInit, OnDestroy {
this.linkCopied.set(true); this.linkCopied.set(true);
setTimeout(() => this.linkCopied.set(false), 2000); setTimeout(() => this.linkCopied.set(false), 2000);
}).catch(err => { }).catch(err => {
console.error('<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>:', err); console.error('Ошибка копирования:', err);
}); });
} }
} }
@@ -316,7 +312,7 @@ export class CartComponent implements OnInit, OnDestroy {
next: () => { next: () => {
this.emailSubmitting.set(false); this.emailSubmitting.set(false);
// Show success message // Show success message
alert('Email <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>! <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>.'); alert('Email успешно отправлен! Проверьте свою почту.');
// Close popup and redirect to home page // Close popup and redirect to home page
setTimeout(() => { setTimeout(() => {
this.closePaymentPopup(); this.closePaymentPopup();
@@ -326,7 +322,7 @@ export class CartComponent implements OnInit, OnDestroy {
error: (err) => { error: (err) => {
console.error('Error submitting email:', err); console.error('Error submitting email:', err);
this.emailSubmitting.set(false); this.emailSubmitting.set(false);
alert('<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> email. <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>, <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>.'); alert('Произошла ошибка при отправке email. Пожалуйста, попробуйте снова.');
} }
}); });
} }
@@ -387,11 +383,11 @@ export class CartComponent implements OnInit, OnDestroy {
} }
if (digitsOnly.length === 0) { if (digitsOnly.length === 0) {
this.phoneError.set('<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>'); this.phoneError.set('Номер телефона обязателен');
} else if (digitsOnly.length < 11) { } else if (digitsOnly.length < 11) {
this.phoneError.set(`<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD> ${11 - digitsOnly.length} <EFBFBD><EFBFBD><EFBFBD><EFBFBD>`); this.phoneError.set(`Введите ещё ${11 - digitsOnly.length} цифр`);
} else if (digitsOnly.length > 11) { } else if (digitsOnly.length > 11) {
this.phoneError.set('<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD>'); this.phoneError.set('Слишком много цифр');
} else { } else {
this.phoneError.set(''); this.phoneError.set('');
} }
@@ -419,19 +415,19 @@ export class CartComponent implements OnInit, OnDestroy {
} }
if (email.length === 0) { if (email.length === 0) {
this.emailError.set('Email <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>'); this.emailError.set('Email обязателен');
} else if (email.length < 5) { } else if (email.length < 5) {
this.emailError.set('Email <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> (<28><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> 5 <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>)'); this.emailError.set('Email слишком короткий (минимум 5 символов)');
} else if (email.length > 100) { } else if (email.length > 100) {
this.emailError.set('Email <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> (<28><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> 100 <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>)'); this.emailError.set('Email слишком длинный (максимум 100 символов)');
} else if (!email.includes('@')) { } else if (!email.includes('@')) {
this.emailError.set('Email <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> @'); this.emailError.set('Email должен содержать @');
} else if (!email.includes('.')) { } else if (!email.includes('.')) {
this.emailError.set('Email <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD> (.com, .ru <EFBFBD> <20>.<2E>.)'); this.emailError.set('Email должен содержать домен (.com, .ru и т.д.)');
} else { } else {
const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/; const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
if (!emailRegex.test(email)) { if (!emailRegex.test(email)) {
this.emailError.set('<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> email'); this.emailError.set('Некорректный формат email');
} else { } else {
this.emailError.set(''); this.emailError.set('');
} }

View File

@@ -24,6 +24,7 @@ export class CategoryComponent implements OnInit, OnDestroy {
private readonly count = 20; private readonly count = 20;
private isLoadingMore = false; private isLoadingMore = false;
private routeSubscription?: Subscription; private routeSubscription?: Subscription;
private scrollTimeout?: ReturnType<typeof setTimeout>;
constructor( constructor(
private route: ActivatedRoute, private route: ActivatedRoute,
@@ -41,6 +42,7 @@ export class CategoryComponent implements OnInit, OnDestroy {
ngOnDestroy(): void { ngOnDestroy(): void {
this.routeSubscription?.unsubscribe(); this.routeSubscription?.unsubscribe();
if (this.scrollTimeout) clearTimeout(this.scrollTimeout);
} }
resetAndLoad(): void { resetAndLoad(): void {
@@ -80,8 +82,6 @@ export class CategoryComponent implements OnInit, OnDestroy {
}); });
} }
private scrollTimeout: any;
@HostListener('window:scroll') @HostListener('window:scroll')
onScroll(): void { onScroll(): void {
if (this.scrollTimeout) clearTimeout(this.scrollTimeout); if (this.scrollTimeout) clearTimeout(this.scrollTimeout);

View File

@@ -1,7 +1,8 @@
import { Component, OnInit, signal, ChangeDetectionStrategy } from '@angular/core'; import { Component, OnInit, OnDestroy, signal, ChangeDetectionStrategy } from '@angular/core';
import { ActivatedRoute, Router, RouterLink } from '@angular/router'; import { ActivatedRoute, Router, RouterLink } from '@angular/router';
import { ApiService } from '../../services'; import { ApiService } from '../../services';
import { Category } from '../../models'; import { Category } from '../../models';
import { Subscription } from 'rxjs';
@Component({ @Component({
selector: 'app-subcategories', selector: 'app-subcategories',
@@ -10,13 +11,15 @@ import { Category } from '../../models';
styleUrls: ['./subcategories.component.scss'], styleUrls: ['./subcategories.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class SubcategoriesComponent implements OnInit { export class SubcategoriesComponent implements OnInit, OnDestroy {
categories = signal<Category[]>([]); categories = signal<Category[]>([]);
subcategories = signal<Category[]>([]); subcategories = signal<Category[]>([]);
loading = signal(true); loading = signal(true);
error = signal<string | null>(null); error = signal<string | null>(null);
parentName = signal<string>(''); parentName = signal<string>('');
private routeSubscription?: Subscription;
constructor( constructor(
private route: ActivatedRoute, private route: ActivatedRoute,
private router: Router, private router: Router,
@@ -24,12 +27,16 @@ export class SubcategoriesComponent implements OnInit {
) {} ) {}
ngOnInit(): void { ngOnInit(): void {
this.route.params.subscribe(params => { this.routeSubscription = this.route.params.subscribe(params => {
const id = parseInt(params['id'], 10); const id = parseInt(params['id'], 10);
this.loadForParent(id); this.loadForParent(id);
}); });
} }
ngOnDestroy(): void {
this.routeSubscription?.unsubscribe();
}
private loadForParent(parentID: number): void { private loadForParent(parentID: number): void {
this.loading.set(true); this.loading.set(true);
this.apiService.getCategories().subscribe({ this.apiService.getCategories().subscribe({

View File

@@ -130,7 +130,7 @@
class="dexar-category-card" class="dexar-category-card"
[class.dexar-category-card--wide]="isWideCategory(category.categoryID)"> [class.dexar-category-card--wide]="isWideCategory(category.categoryID)">
<div class="dexar-category-image"> <div class="dexar-category-image">
@if (isWideCategory(category.categoryID) && category.wideBanner && category.wideBanner !== true) { @if (isWideCategory(category.categoryID) && category.wideBanner) {
<img [src]="category.wideBanner" [alt]="category.name" loading="lazy" decoding="async" /> <img [src]="category.wideBanner" [alt]="category.name" loading="lazy" decoding="async" />
} @else if (category.icon) { } @else if (category.icon) {
<img [src]="category.icon" [alt]="category.name" loading="lazy" decoding="async" /> <img [src]="category.icon" [alt]="category.name" loading="lazy" decoding="async" />

View File

@@ -87,12 +87,6 @@ export class HomeComponent implements OnInit {
topLevel.forEach(cat => { topLevel.forEach(cat => {
if (!cat.wideBanner) return; if (!cat.wideBanner) return;
// API may send wideBanner as a boolean flag instead of a URL
if (cat.wideBanner === true) {
this.wideCategories.update(set => { const next = new Set(set); next.add(cat.categoryID); return next; });
return;
}
const img = new Image(); const img = new Image();
img.onload = () => { img.onload = () => {
const ratio = img.naturalWidth / img.naturalHeight; const ratio = img.naturalWidth / img.naturalHeight;
@@ -104,7 +98,7 @@ export class HomeComponent implements OnInit {
}); });
} }
}; };
img.src = cat.wideBanner as string; img.src = cat.wideBanner;
}); });
} }

View File

@@ -1,11 +1,12 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
import { environment } from '../../../../environments/environment'; import { environment } from '../../../../environments/environment';
@Component({ @Component({
selector: 'app-about', selector: 'app-about',
imports: [], imports: [],
templateUrl: './about.component.html', templateUrl: './about.component.html',
styleUrls: ['./about.component.scss'] styleUrls: ['./about.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class AboutComponent { export class AboutComponent {
brandName = environment.brandName; brandName = environment.brandName;

View File

@@ -1,11 +1,12 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
import { environment } from '../../../../environments/environment'; import { environment } from '../../../../environments/environment';
@Component({ @Component({
selector: 'app-contacts', selector: 'app-contacts',
imports: [], imports: [],
templateUrl: './contacts.component.html', templateUrl: './contacts.component.html',
styleUrls: ['./contacts.component.scss'] styleUrls: ['./contacts.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class ContactsComponent { export class ContactsComponent {
brandName = environment.brandName; brandName = environment.brandName;

View File

@@ -1,11 +1,12 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
import { environment } from '../../../../environments/environment'; import { environment } from '../../../../environments/environment';
@Component({ @Component({
selector: 'app-delivery', selector: 'app-delivery',
imports: [], imports: [],
templateUrl: './delivery.component.html', templateUrl: './delivery.component.html',
styleUrls: ['./delivery.component.scss'] styleUrls: ['./delivery.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class DeliveryComponent { export class DeliveryComponent {
brandName = environment.brandName; brandName = environment.brandName;

View File

@@ -1,11 +1,12 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
import { environment } from '../../../../environments/environment'; import { environment } from '../../../../environments/environment';
@Component({ @Component({
selector: 'app-faq', selector: 'app-faq',
imports: [], imports: [],
templateUrl: './faq.component.html', templateUrl: './faq.component.html',
styleUrls: ['./faq.component.scss'] styleUrls: ['./faq.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class FaqComponent { export class FaqComponent {
brandName = environment.brandName; brandName = environment.brandName;

View File

@@ -1,11 +1,12 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
import { environment } from '../../../../environments/environment'; import { environment } from '../../../../environments/environment';
@Component({ @Component({
selector: 'app-guarantee', selector: 'app-guarantee',
imports: [], imports: [],
templateUrl: './guarantee.component.html', templateUrl: './guarantee.component.html',
styleUrls: ['./guarantee.component.scss'] styleUrls: ['./guarantee.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class GuaranteeComponent { export class GuaranteeComponent {
brandName = environment.brandName; brandName = environment.brandName;

View File

@@ -1,12 +1,14 @@
import { Component, OnInit, OnDestroy, signal, ChangeDetectionStrategy } from '@angular/core'; import { Component, OnInit, OnDestroy, signal, ChangeDetectionStrategy, inject } from '@angular/core';
import { DecimalPipe } from '@angular/common'; import { DecimalPipe } from '@angular/common';
import { FormsModule } from '@angular/forms'; import { FormsModule } from '@angular/forms';
import { ActivatedRoute, RouterLink } from '@angular/router'; import { ActivatedRoute, RouterLink } from '@angular/router';
import { ApiService, CartService, TelegramService } from '../../services'; import { ApiService, CartService, TelegramService, SeoService } from '../../services';
import { Item } from '../../models'; import { Item } from '../../models';
import { DomSanitizer, SafeHtml } from '@angular/platform-browser'; import { DomSanitizer, SafeHtml } from '@angular/platform-browser';
import { Subscription } from 'rxjs'; import { Subscription } from 'rxjs';
import { environment } from '../../../environments/environment'; import { environment } from '../../../environments/environment';
import { SecurityContext } from '@angular/core';
import { getDiscountedPrice } from '../../utils/item.utils';
@Component({ @Component({
selector: 'app-item-detail', selector: 'app-item-detail',
@@ -31,6 +33,11 @@ export class ItemDetailComponent implements OnInit, OnDestroy {
reviewSubmitStatus = signal<'idle' | 'loading' | 'success' | 'error'>('idle'); reviewSubmitStatus = signal<'idle' | 'loading' | 'success' | 'error'>('idle');
private routeSubscription?: Subscription; private routeSubscription?: Subscription;
private reviewResetTimeout?: ReturnType<typeof setTimeout>;
private reviewErrorTimeout?: ReturnType<typeof setTimeout>;
private reloadTimeout?: ReturnType<typeof setTimeout>;
private seoService = inject(SeoService);
constructor( constructor(
private route: ActivatedRoute, private route: ActivatedRoute,
@@ -49,6 +56,10 @@ export class ItemDetailComponent implements OnInit, OnDestroy {
ngOnDestroy(): void { ngOnDestroy(): void {
this.routeSubscription?.unsubscribe(); this.routeSubscription?.unsubscribe();
if (this.reviewResetTimeout) clearTimeout(this.reviewResetTimeout);
if (this.reviewErrorTimeout) clearTimeout(this.reviewErrorTimeout);
if (this.reloadTimeout) clearTimeout(this.reloadTimeout);
this.seoService.resetToDefaults();
} }
loadItem(itemID: number): void { loadItem(itemID: number): void {
@@ -57,6 +68,7 @@ export class ItemDetailComponent implements OnInit, OnDestroy {
this.apiService.getItem(itemID).subscribe({ this.apiService.getItem(itemID).subscribe({
next: (item) => { next: (item) => {
this.item.set(item); this.item.set(item);
this.seoService.setItemMeta(item);
this.loading.set(false); this.loading.set(false);
}, },
error: (err) => { error: (err) => {
@@ -81,18 +93,18 @@ export class ItemDetailComponent implements OnInit, OnDestroy {
getDiscountedPrice(): number { getDiscountedPrice(): number {
const currentItem = this.item(); const currentItem = this.item();
if (!currentItem) return 0; if (!currentItem) return 0;
return currentItem.price * (1 - currentItem.discount / 100); return getDiscountedPrice(currentItem);
} }
getSafeHtml(html: string): SafeHtml { getSafeHtml(html: string): SafeHtml {
return this.sanitizer.sanitize(1, html) || ''; return this.sanitizer.sanitize(SecurityContext.HTML, html) || '';
} }
getRatingStars(rating: number): string { getRatingStars(rating: number): string {
const fullStars = Math.floor(rating); const fullStars = Math.floor(rating);
const hasHalfStar = rating % 1 >= 0.5; const hasHalfStar = rating % 1 >= 0.5;
let stars = '?'.repeat(fullStars); let stars = ''.repeat(fullStars);
if (hasHalfStar) stars += '?'; if (hasHalfStar) stars += '';
return stars; return stars;
} }
@@ -102,10 +114,10 @@ export class ItemDetailComponent implements OnInit, OnDestroy {
const diffMs = now.getTime() - date.getTime(); const diffMs = now.getTime() - date.getTime();
const diffDays = Math.floor(diffMs / (1000 * 60 * 60 * 24)); const diffDays = Math.floor(diffMs / (1000 * 60 * 60 * 24));
if (diffDays === 0) return '<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>'; if (diffDays === 0) return 'Сегодня';
if (diffDays === 1) return '<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>'; if (diffDays === 1) return 'Вчера';
if (diffDays < 7) return `${diffDays} <EFBFBD><EFBFBD>. <20><><EFBFBD><EFBFBD><EFBFBD>`; if (diffDays < 7) return `${diffDays} дн. назад`;
if (diffDays < 30) return `${Math.floor(diffDays / 7)} <EFBFBD><EFBFBD><EFBFBD>. <20><><EFBFBD><EFBFBD><EFBFBD>`; if (diffDays < 30) return `${Math.floor(diffDays / 7)} нед. назад`;
return date.toLocaleDateString('ru-RU', { return date.toLocaleDateString('ru-RU', {
day: 'numeric', day: 'numeric',
@@ -120,7 +132,7 @@ export class ItemDetailComponent implements OnInit, OnDestroy {
getUserDisplayName(): string | null { getUserDisplayName(): string | null {
if (!this.telegramService.isTelegramApp()) { if (!this.telegramService.isTelegramApp()) {
return '<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>'; return 'Пользователь';
} }
return this.telegramService.getDisplayName(); return this.telegramService.getDisplayName();
} }
@@ -149,13 +161,13 @@ export class ItemDetailComponent implements OnInit, OnDestroy {
this.reviewSubmitStatus.set('success'); this.reviewSubmitStatus.set('success');
this.newReview = { rating: 0, comment: '', anonymous: false }; this.newReview = { rating: 0, comment: '', anonymous: false };
// <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD> 3 <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> // Сброс состояния через 3 секунды
setTimeout(() => { this.reviewResetTimeout = setTimeout(() => {
this.reviewSubmitStatus.set('idle'); this.reviewSubmitStatus.set('idle');
}, 3000); }, 3000);
// <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> // Перезагрузить данные товара после отправки отзыва
setTimeout(() => { this.reloadTimeout = setTimeout(() => {
this.loadItem(currentItem.itemID); this.loadItem(currentItem.itemID);
}, 500); }, 500);
}, },
@@ -163,8 +175,8 @@ export class ItemDetailComponent implements OnInit, OnDestroy {
console.error('Error submitting review:', err); console.error('Error submitting review:', err);
this.reviewSubmitStatus.set('error'); this.reviewSubmitStatus.set('error');
// <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD> 5 <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> // Сброс состояния об ошибке через 5 секунд
setTimeout(() => { this.reviewErrorTimeout = setTimeout(() => {
this.reviewSubmitStatus.set('idle'); this.reviewSubmitStatus.set('idle');
}, 5000); }, 5000);
} }

View File

@@ -1,11 +1,12 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
import { environment } from '../../../../environments/environment'; import { environment } from '../../../../environments/environment';
@Component({ @Component({
selector: 'app-company-details', selector: 'app-company-details',
imports: [], imports: [],
templateUrl: './company-details.component.html', templateUrl: './company-details.component.html',
styleUrls: ['./company-details.component.scss'] styleUrls: ['./company-details.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class CompanyDetailsComponent { export class CompanyDetailsComponent {
brandName = environment.brandName; brandName = environment.brandName;

View File

@@ -1,4 +1,4 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
import { RouterLink } from '@angular/router'; import { RouterLink } from '@angular/router';
import { environment } from '../../../../environments/environment'; import { environment } from '../../../../environments/environment';
@@ -6,7 +6,8 @@ import { environment } from '../../../../environments/environment';
selector: 'app-payment-terms', selector: 'app-payment-terms',
imports: [RouterLink], imports: [RouterLink],
templateUrl: './payment-terms.component.html', templateUrl: './payment-terms.component.html',
styleUrls: ['./payment-terms.component.scss'] styleUrls: ['./payment-terms.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class PaymentTermsComponent { export class PaymentTermsComponent {
brandName = environment.brandName; brandName = environment.brandName;

View File

@@ -1,11 +1,12 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
import { environment } from '../../../../environments/environment'; import { environment } from '../../../../environments/environment';
@Component({ @Component({
selector: 'app-privacy-policy', selector: 'app-privacy-policy',
imports: [], imports: [],
templateUrl: './privacy-policy.component.html', templateUrl: './privacy-policy.component.html',
styleUrls: ['./privacy-policy.component.scss'] styleUrls: ['./privacy-policy.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class PrivacyPolicyComponent { export class PrivacyPolicyComponent {
brandName = environment.brandName; brandName = environment.brandName;

View File

@@ -1,4 +1,4 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
import { RouterLink } from '@angular/router'; import { RouterLink } from '@angular/router';
import { environment } from '../../../../environments/environment'; import { environment } from '../../../../environments/environment';
@@ -6,7 +6,8 @@ import { environment } from '../../../../environments/environment';
selector: 'app-public-offer', selector: 'app-public-offer',
imports: [RouterLink], imports: [RouterLink],
templateUrl: './public-offer.component.html', templateUrl: './public-offer.component.html',
styleUrls: ['./public-offer.component.scss'] styleUrls: ['./public-offer.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class PublicOfferComponent { export class PublicOfferComponent {
brandName = environment.brandName; brandName = environment.brandName;

View File

@@ -1,12 +1,12 @@
import { Component } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
import { RouterLink } from '@angular/router';
import { environment } from '../../../../environments/environment'; import { environment } from '../../../../environments/environment';
@Component({ @Component({
selector: 'app-return-policy', selector: 'app-return-policy',
imports: [], imports: [],
templateUrl: './return-policy.component.html', templateUrl: './return-policy.component.html',
styleUrls: ['./return-policy.component.scss'] styleUrls: ['./return-policy.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush
}) })
export class ReturnPolicyComponent { export class ReturnPolicyComponent {
brandName = environment.brandName; brandName = environment.brandName;

View File

@@ -48,6 +48,7 @@ export class SearchComponent implements OnDestroy {
ngOnDestroy(): void { ngOnDestroy(): void {
this.searchSubscription.unsubscribe(); this.searchSubscription.unsubscribe();
this.searchSubject.complete(); this.searchSubject.complete();
if (this.scrollTimeout) clearTimeout(this.scrollTimeout);
} }
onSearchInput(query: string): void { onSearchInput(query: string): void {
@@ -106,7 +107,7 @@ export class SearchComponent implements OnDestroy {
}); });
} }
private scrollTimeout: any; private scrollTimeout?: ReturnType<typeof setTimeout>;
@HostListener('window:scroll') @HostListener('window:scroll')
onScroll(): void { onScroll(): void {

View File

@@ -1,6 +1,7 @@
import { Injectable, signal, computed, effect } from '@angular/core'; import { Injectable, signal, computed, effect } from '@angular/core';
import { ApiService } from './api.service'; import { ApiService } from './api.service';
import { Item, CartItem } from '../models'; import { Item, CartItem } from '../models';
import { getDiscountedPrice } from '../utils/item.utils';
import { environment } from '../../environments/environment'; import { environment } from '../../environments/environment';
import type { } from '../types/telegram.types'; import type { } from '../types/telegram.types';
@@ -11,6 +12,7 @@ export class CartService {
private readonly STORAGE_KEY = `${environment.brandName.toLowerCase().replace(/\s+/g, '_')}_cart`; private readonly STORAGE_KEY = `${environment.brandName.toLowerCase().replace(/\s+/g, '_')}_cart`;
private cartItems = signal<CartItem[]>([]); private cartItems = signal<CartItem[]>([]);
private isTelegram = typeof window !== 'undefined' && !!window.Telegram?.WebApp; private isTelegram = typeof window !== 'undefined' && !!window.Telegram?.WebApp;
private addingItems = new Set<number>();
items = this.cartItems.asReadonly(); items = this.cartItems.asReadonly();
itemCount = computed(() => { itemCount = computed(() => {
@@ -22,8 +24,7 @@ export class CartService {
const items = this.cartItems(); const items = this.cartItems();
if (!Array.isArray(items)) return 0; if (!Array.isArray(items)) return 0;
return items.reduce((total, item) => { return items.reduce((total, item) => {
const price = item.price * (1 - item.discount / 100); return total + (getDiscountedPrice(item) * item.quantity);
return total + (price * item.quantity);
}, 0); }, 0);
}); });
@@ -40,8 +41,8 @@ export class CartService {
private saveToStorage(items: CartItem[]): void { private saveToStorage(items: CartItem[]): void {
const data = JSON.stringify(items); const data = JSON.stringify(items);
// Always save to sessionStorage // Always save to localStorage
sessionStorage.setItem(this.STORAGE_KEY, data); localStorage.setItem(this.STORAGE_KEY, data);
// Also save to Telegram CloudStorage if available // Also save to Telegram CloudStorage if available
if (this.isTelegram) { if (this.isTelegram) {
@@ -59,21 +60,21 @@ export class CartService {
window.Telegram!.WebApp.CloudStorage.getItem(this.STORAGE_KEY, (err, value) => { window.Telegram!.WebApp.CloudStorage.getItem(this.STORAGE_KEY, (err, value) => {
if (err) { if (err) {
console.error('Error loading from Telegram CloudStorage:', err); console.error('Error loading from Telegram CloudStorage:', err);
this.loadFromSessionStorage(); this.loadFromLocalStorage();
} else if (value) { } else if (value) {
this.parseAndSetCart(value) || this.loadFromSessionStorage(); this.parseAndSetCart(value) || this.loadFromLocalStorage();
} else { } else {
// No data in CloudStorage, try sessionStorage // No data in CloudStorage, try localStorage
this.loadFromSessionStorage(); this.loadFromLocalStorage();
} }
}); });
} else { } else {
this.loadFromSessionStorage(); this.loadFromLocalStorage();
} }
} }
private loadFromSessionStorage(): void { private loadFromLocalStorage(): void {
const stored = sessionStorage.getItem(this.STORAGE_KEY); const stored = localStorage.getItem(this.STORAGE_KEY);
if (stored) { if (stored) {
this.parseAndSetCart(stored); this.parseAndSetCart(stored);
} }
@@ -98,6 +99,9 @@ export class CartService {
} }
addItem(itemID: number, quantity: number = 1): void { addItem(itemID: number, quantity: number = 1): void {
// Prevent duplicate API calls for same item
if (this.addingItems.has(itemID)) return;
const currentItems = this.cartItems(); const currentItems = this.cartItems();
const existingItem = currentItems.find(i => i.itemID === itemID); const existingItem = currentItems.find(i => i.itemID === itemID);
@@ -106,14 +110,16 @@ export class CartService {
this.updateQuantity(itemID, existingItem.quantity + quantity); this.updateQuantity(itemID, existingItem.quantity + quantity);
} else { } else {
// Get item details from API and add to cart // Get item details from API and add to cart
this.addingItems.add(itemID);
this.apiService.getItem(itemID).subscribe({ this.apiService.getItem(itemID).subscribe({
next: (item) => { next: (item) => {
const cartItem: CartItem = { ...item, quantity }; const cartItem: CartItem = { ...item, quantity };
this.cartItems.set([...this.cartItems(), cartItem]); this.cartItems.set([...this.cartItems(), cartItem]);
this.addingItems.delete(itemID);
}, },
error: (err) => { error: (err) => {
console.error('Error adding to cart:', err); console.error('Error adding to cart:', err);
alert('Ошибка добавления в корзину: ' + (err.error?.message || err.message)); this.addingItems.delete(itemID);
} }
}); });
} }

View File

@@ -2,3 +2,4 @@ export * from './api.service';
export * from './cart.service'; export * from './cart.service';
export * from './telegram.service'; export * from './telegram.service';
export * from './language.service'; export * from './language.service';
export * from './seo.service';

View File

@@ -0,0 +1,117 @@
import { Injectable, inject } from '@angular/core';
import { Meta, Title } from '@angular/platform-browser';
import { environment } from '../../environments/environment';
import { Item } from '../models';
import { getDiscountedPrice, getMainImage } from '../utils/item.utils';
@Injectable({
providedIn: 'root'
})
export class SeoService {
private meta = inject(Meta);
private title = inject(Title);
private readonly siteUrl = `https://${environment.domain}`;
private readonly siteName = environment.brandFullName;
/**
* Set Open Graph & Twitter Card meta tags for a product/item page.
*/
setItemMeta(item: Item): void {
const price = item.discount > 0 ? getDiscountedPrice(item) : item.price;
const imageUrl = this.resolveUrl(getMainImage(item));
const itemUrl = `${this.siteUrl}/item/${item.itemID}`;
const description = this.truncate(this.stripHtml(item.description), 160);
const titleText = `${item.name}${this.siteName}`;
this.title.setTitle(titleText);
this.setOrUpdate([
// Open Graph
{ property: 'og:type', content: 'product' },
{ property: 'og:title', content: item.name },
{ property: 'og:description', content: description },
{ property: 'og:image', content: imageUrl },
{ property: 'og:url', content: itemUrl },
{ property: 'og:site_name', content: this.siteName },
{ property: 'og:locale', content: 'ru_RU' },
// Product-specific OG tags
{ property: 'product:price:amount', content: price.toFixed(2) },
{ property: 'product:price:currency', content: item.currency || 'RUB' },
// Twitter Card
{ name: 'twitter:card', content: 'summary_large_image' },
{ name: 'twitter:title', content: item.name },
{ name: 'twitter:description', content: description },
{ name: 'twitter:image', content: imageUrl },
// Standard meta
{ name: 'description', content: description },
]);
}
/**
* Reset meta tags back to defaults (call on navigation away from item page).
*/
resetToDefaults(): void {
const defaultTitle = `${this.siteName} — Маркетплейс товаров и услуг`;
const defaultDescription = 'Современный маркетплейс для покупки цифровых товаров. Широкий выбор товаров, удобный поиск, быстрая доставка.';
const defaultImage = `${this.siteUrl}/og-image.jpg`;
this.title.setTitle(defaultTitle);
this.setOrUpdate([
{ property: 'og:type', content: 'website' },
{ property: 'og:title', content: defaultTitle },
{ property: 'og:description', content: defaultDescription },
{ property: 'og:image', content: defaultImage },
{ property: 'og:url', content: this.siteUrl },
{ property: 'og:site_name', content: this.siteName },
{ property: 'og:locale', content: 'ru_RU' },
{ name: 'twitter:card', content: 'summary_large_image' },
{ name: 'twitter:title', content: defaultTitle },
{ name: 'twitter:description', content: defaultDescription },
{ name: 'twitter:image', content: defaultImage },
{ name: 'description', content: defaultDescription },
]);
// Remove product-specific tags
this.meta.removeTag("property='product:price:amount'");
this.meta.removeTag("property='product:price:currency'");
}
private setOrUpdate(tags: Array<{ property?: string; name?: string; content: string }>): void {
for (const tag of tags) {
const selector = tag.property
? `property='${tag.property}'`
: `name='${tag.name}'`;
const existing = this.meta.getTag(selector);
if (existing) {
this.meta.updateTag(tag as any, selector);
} else {
this.meta.addTag(tag as any);
}
}
}
/** Convert relative URLs to absolute */
private resolveUrl(url: string): string {
if (!url || url.startsWith('http')) return url;
return `${this.siteUrl}${url.startsWith('/') ? '' : '/'}${url}`;
}
/** Strip HTML tags from a string */
private stripHtml(html: string): string {
return html?.replace(/<[^>]*>/g, '') || '';
}
/** Truncate text to maxLength, adding ellipsis */
private truncate(text: string, maxLength: number): string {
if (!text || text.length <= maxLength) return text || '';
return text.substring(0, maxLength - 1) + '…';
}
}

View File

@@ -5,7 +5,7 @@ export function getDiscountedPrice(item: Item): number {
} }
export function getMainImage(item: Item): string { export function getMainImage(item: Item): string {
return item.photos?.[0]?.url || ''; return item.photos?.[0]?.url || '/assets/images/placeholder.svg';
} }
export function trackByItemId(index: number, item: Item): number { export function trackByItemId(index: number, item: Item): number {

View File

@@ -49,8 +49,11 @@
<!-- Preload critical assets for better LCP --> <!-- Preload critical assets for better LCP -->
<link rel="preload" href="/assets/images/dexar-logo.svg" as="image" type="image/svg+xml"> <link rel="preload" href="/assets/images/dexar-logo.svg" as="image" type="image/svg+xml">
<link rel="modulepreload" href="/polyfills-6ISPNSXF.js">
<link rel="modulepreload" href="/main-XRBN6CKL.js"> <!-- Google Fonts -->
<link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=DM+Sans:wght@400;500;600;700&display=swap">
<!-- Critical CSS for faster FCP --> <!-- Critical CSS for faster FCP -->
<style> <style>

View File

@@ -38,6 +38,11 @@
<!-- Preconnect to API --> <!-- Preconnect to API -->
<link rel="preconnect" href="https://api.novo.market"> <link rel="preconnect" href="https://api.novo.market">
<!-- Google Fonts -->
<link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=DM+Sans:wght@400;500;600;700&display=swap">
<!-- Structured Data --> <!-- Structured Data -->
<script type="application/ld+json"> <script type="application/ld+json">
{ {

View File

@@ -3,8 +3,7 @@
/* PrimeNG and PrimeIcons */ /* PrimeNG and PrimeIcons */
@import 'primeicons/primeicons.css'; @import 'primeicons/primeicons.css';
/* Google Fonts - DM Sans for Dexar redesign */ /* Google Fonts loaded via <link> in index.html for non-blocking rendering */
@import url('https://fonts.googleapis.com/css2?family=DM+Sans:wght@400;500;600;700&display=swap');
/* Font optimization */ /* Font optimization */
@font-face { @font-face {

View File

@@ -117,7 +117,7 @@
} }
.highlight { .highlight {
background: linear-gradient(135deg, rgba(var(--primary-color), 0.1) 0%, rgba(var(--secondary-color), 0.1) 100%); background: linear-gradient(135deg, color-mix(in srgb, var(--primary-color) 10%, transparent) 0%, color-mix(in srgb, var(--secondary-color) 10%, transparent) 100%);
padding: 1rem; padding: 1rem;
border-radius: var(--radius-sm); border-radius: var(--radius-sm);
border-left: 3px solid var(--accent-color); border-left: 3px solid var(--accent-color);

View File

@@ -4,6 +4,7 @@
"extends": "./tsconfig.json", "extends": "./tsconfig.json",
"compilerOptions": { "compilerOptions": {
"outDir": "./out-tsc/spec", "outDir": "./out-tsc/spec",
"rootDir": "./src",
"types": [ "types": [
"jasmine" "jasmine"
] ]