diff --git a/.paul/PROJECT.md b/.paul/PROJECT.md new file mode 100644 index 0000000..1ddd35f --- /dev/null +++ b/.paul/PROJECT.md @@ -0,0 +1,28 @@ +# Project: kikiriki.sklep.pl + +## Description +Teraz potrzebuje rozbudowac modul bloga, ale generalnie rozbudowujemy PrestaShop o nowe funkcje dla klienta. + +## Core Value +Sklep oparty na PrestaShop, ktory jest rozwijany o funkcje dopasowane do potrzeb klienta. + +## Requirements + +### Must Have +- [To be defined during planning] + +### Should Have +- [To be defined during planning] + +### Nice to Have +- [To be defined during planning] + +## Constraints +- [To be identified during planning] + +## Success Criteria +- Sklep oparty na PrestaShop, ktory jest rozwijany o funkcje dopasowane do potrzeb klienta. is achieved +- [To be refined during planning] + +--- +*Created: 2026-04-06 10:16* \ No newline at end of file diff --git a/.paul/ROADMAP.md b/.paul/ROADMAP.md new file mode 100644 index 0000000..273eae8 --- /dev/null +++ b/.paul/ROADMAP.md @@ -0,0 +1,35 @@ +# Roadmap: kikiriki.sklep.pl + +## Overview +Teraz potrzebuje rozbudowac modul bloga, ale generalnie rozbudowujemy PrestaShop o nowe funkcje dla klienta. + +## Current Milestone +**v0.1 Initial Release** (v0.1.0) +Status: In progress +Phases: 0 of 1 complete + +## Phases + +| Phase | Name | Plans | Status | Completed | +|-------|------|-------|--------|-----------| +| 1 | Homepage blog zajawki | 1 | Planning | - | + +## Phase Details + +### Phase 1: Homepage blog zajawki + +**Goal:** Wyswietlic na stronie glownej 3 najnowsze wpisy bloga jako zajawki oraz sekcje z naglowkiem. +**Depends on:** Nothing (first phase) +**Research:** Unlikely (korzystamy z istniejacego modulu i widokow) + +**Scope:** +- Dodanie hooka home w module bloga +- Pobranie i przygotowanie 3 najnowszych aktywnych wpisow +- Render sekcji na homepage w stylu zblizonym do listy /blog + +**Plans:** +- [ ] 01-01: Sekcja "Najnowsze na blogu" na homepage z 3 zajawkami + +--- +*Roadmap created: 2026-04-06 10:16* +*Last updated: 2026-04-06 10:18* diff --git a/.paul/STATE.md b/.paul/STATE.md new file mode 100644 index 0000000..0ab87e9 --- /dev/null +++ b/.paul/STATE.md @@ -0,0 +1,28 @@ +# Project State + +## Current Position + +Milestone: v0.1 Initial Release +Phase: 1 of 1 (Homepage blog zajawki) - Applying +Plan: 01-01 execution complete +Status: APPLY complete, ready for UNIFY +Last activity: 2026-04-06 10:20 - Applied .paul/phases/01-homepage-blog-zajawki/01-01-PLAN.md + +Progress: +- Milestone: [######----] 60% +- Phase 1: [######----] 60% + +## Loop Position + +Current loop state: +``` +PLAN --> APPLY --> UNIFY + x x o [Apply complete, ready for unify] +``` + +## Session Continuity + +Last session: 2026-04-06 10:20 +Stopped at: Apply completed for plan 01-01 +Next action: Run $paul-unify .paul/phases/01-homepage-blog-zajawki/01-01-PLAN.md +Resume file: .paul/phases/01-homepage-blog-zajawki/01-01-PLAN.md diff --git a/.paul/paul.json b/.paul/paul.json new file mode 100644 index 0000000..cc8012c --- /dev/null +++ b/.paul/paul.json @@ -0,0 +1,25 @@ +{ + "name": "kikiriki.sklep.pl", + "version": "0.0.0", + "milestone": { + "name": "None", + "version": "0.0.0", + "status": "not_started" + }, + "phase": { + "number": 0, + "name": "None", + "status": "not_started" + }, + "loop": { + "plan": null, + "position": "IDLE" + }, + "timestamps": { + "created_at": "2026-04-06T10:16:24.3023021+02:00", + "updated_at": "2026-04-06T10:16:24.3023021+02:00" + }, + "satellite": { + "groom": true + } +} \ No newline at end of file diff --git a/.paul/phases/01-homepage-blog-zajawki/01-01-PLAN.md b/.paul/phases/01-homepage-blog-zajawki/01-01-PLAN.md new file mode 100644 index 0000000..4db912e --- /dev/null +++ b/.paul/phases/01-homepage-blog-zajawki/01-01-PLAN.md @@ -0,0 +1,131 @@ +--- +phase: 01-homepage-blog-zajawki +plan: 01 +type: execute +wave: 1 +depends_on: [] +files_modified: + - modules/projectproblog/projectproblog.php + - modules/projectproblog/classes/BlogPost.php + - modules/projectproblog/views/templates/hook/home.tpl + - modules/projectproblog/views/css/blog.css +autonomous: true +--- + + +## Goal +Dodac sekcje blogowa na stronie glownej, ktora wyswietla 3 najnowsze aktywne wpisy jako zajawki i zawiera naglowek sekcji. + +## Purpose +Uzytkownik sklepu ma od razu na homepage widoczny aktualny content bloga, co wspiera ruch do sekcji /blog i ekspozycje marki. + +## Output +Hook `displayHome` w module `projectproblog`, pobranie 3 ostatnich wpisow, render sekcji z kartami wpisow i stylami. + + + +## Project Context +@.paul/PROJECT.md +@.paul/ROADMAP.md +@.paul/STATE.md + +## Source Files +@modules/projectproblog/projectproblog.php +@modules/projectproblog/classes/BlogPost.php +@modules/projectproblog/views/templates/front/list.tpl +@modules/projectproblog/views/css/blog.css +@themes/classic/templates/index.tpl + + + + +## AC-1: Sekcja blogowa widoczna na homepage +```gherkin +Given modul projectproblog jest zainstalowany i ma aktywne wpisy +When uzytkownik otwiera strone glowna sklepu +Then widzi sekcje z naglowkiem i 3 zajawkami najnowszych wpisow bloga +``` + +## AC-2: Zajawki odzwierciedlaja wpisy i prowadza do detailu +```gherkin +Given sekcja blogowa jest wyswietlona na stronie glownej +When uzytkownik widzi zajawki wpisow +Then kazda zajawka pokazuje tytul, date, intro, miniaturke (jezeli jest) i link do strony wpisu +``` + +## AC-3: Brak regresji gdy brak wpisow +```gherkin +Given brak aktywnych wpisow blogowych +When uzytkownik otwiera strone glowna +Then sekcja blogowa nie powoduje bledow renderowania i nie psuje ukladu strony +``` + + + + + + + Task 1: Dodaj dane i hook displayHome dla modulu bloga + modules/projectproblog/projectproblog.php, modules/projectproblog/classes/BlogPost.php + + Rozszerz modul o obsluge homepage: + - Zarejestruj hook `displayHome` podczas instalacji. + - Dodaj implementacje `hookDisplayHome`, ktora pobierze 3 najnowsze aktywne wpisy. + - W `BlogPost` dodaj metode do pobierania limitowanej listy najnowszych wpisow dla jezyka (sortowanie po `date_add DESC`, tylko `active=1`). + - Wzbogac dane o URL wpisu i URL miniatury analogicznie do listy bloga. + Unikaj: zmian SQL i zmian w strukturze tabel (nie sa potrzebne do tej funkcji). + + php -l modules/projectproblog/projectproblog.php && php -l modules/projectproblog/classes/BlogPost.php + AC-1 i AC-2 spelnione po stronie backendu danych i hooka + + + + Task 2: Wyrenderuj sekcje zajawkowa bloga na homepage + modules/projectproblog/views/templates/hook/home.tpl, modules/projectproblog/views/css/blog.css, modules/projectproblog/projectproblog.php + + Dodaj szablon hooka home oraz stylowanie: + - Utworz `views/templates/hook/home.tpl` z naglowkiem sekcji i 3 kartami wpisow. + - Zachowaj wizualna spojnosc z kartami z `/blog` (tytul, intro, data, CTA). + - Podlacz CSS dla sekcji homepage (dedykowane klasy, bez ingerencji w globalny layout sklepu). + - W `hookDisplayHome` przypisz zmienne Smarty (`blog_home_title`, `blog_home_posts`, `blog_url`) i zwroc szablon tylko gdy sa wpisy. + Unikaj: edycji plikow szablonu motywu (`themes/*`) - sekcja ma wejsc przez hook modułu. + + Rebuild cache smarty (jesli wymagane) i reczny test: otworz homepage i potwierdz widocznosc sekcji oraz linkowanie do wpisu i /blog + AC-1, AC-2 i AC-3 spelnione w warstwie UI + + + + + + +## DO NOT CHANGE +- `themes/*` (brak edycji motywu poza istniejacym mechanizmem hooka) +- `modules/projectproblog/sql/*` (brak zmian schematu bazy) +- Kontrolery blog list/post (chyba ze wyjdzie krytyczna koniecznosc kompatybilnosci) + +## SCOPE LIMITS +- Zakres obejmuje tylko homepage i tylko 3 ostatnie wpisy. +- Brak zmian w panelu administracyjnym bloga. +- Brak nowych opcji konfiguracyjnych modułu w BO na tym etapie. + + + + +Before declaring plan complete: +- [ ] `php -l modules/projectproblog/projectproblog.php` +- [ ] `php -l modules/projectproblog/classes/BlogPost.php` +- [ ] Homepage wyswietla sekcje bloga z 3 wpisami i naglowkiem +- [ ] Linki z kart prowadza do poprawnych URL wpisow blogowych +- [ ] Przy pustej bazie wpisow homepage renderuje sie bez bledow +- [ ] All acceptance criteria met + + + +- Hook `displayHome` z modulem bloga dziala i zwraca sekcje tylko gdy sa wpisy. +- Sekcja homepage prezentuje 3 najnowsze wpisy jako zajawki zgodne wizualnie z `/blog`. +- Implementacja nie powoduje regresji na homepage i w module bloga. + + + +After completion, create `.paul/phases/01-homepage-blog-zajawki/01-01-SUMMARY.md` + diff --git a/changelog/2026-04-06.md b/changelog/2026-04-06.md new file mode 100644 index 0000000..f4f7224 --- /dev/null +++ b/changelog/2026-04-06.md @@ -0,0 +1,12 @@ +# 2026-04-06 + +## Co zrobiono +- [Uzupełnij opis wykonanych prac] + +## Zmienione pliki +- .paul/ +- changelog/ +- modules/projectproblog/classes/BlogPost.php +- modules/projectproblog/projectproblog.php +- modules/projectproblog/views/css/blog.css +- modules/projectproblog/views/templates/hook/ diff --git a/modules/projectproblog/classes/BlogPost.php b/modules/projectproblog/classes/BlogPost.php index 938a7ab..c1f795f 100644 --- a/modules/projectproblog/classes/BlogPost.php +++ b/modules/projectproblog/classes/BlogPost.php @@ -168,6 +168,25 @@ class BlogPost extends ObjectModel ); } + /** + * Pobiera najnowsze aktywne wpisy (bez paginacji) do sekcji homepage. + */ + public static function getLatest($idLang, $limit = 3) + { + $limit = max(1, (int) $limit); + + return Db::getInstance()->executeS( + 'SELECT p.`id_post`, p.`thumbnail`, p.`date_add`, + pl.`title`, pl.`intro`, pl.`link_rewrite` + FROM `' . _DB_PREFIX_ . 'projectproblog_post` p + LEFT JOIN `' . _DB_PREFIX_ . 'projectproblog_post_lang` pl + ON p.`id_post` = pl.`id_post` AND pl.`id_lang` = ' . (int) $idLang . ' + WHERE p.`active` = 1 + ORDER BY p.`date_add` DESC + LIMIT ' . (int) $limit + ); + } + /** * Liczba wpisów (do paginacji). */ diff --git a/modules/projectproblog/projectproblog.php b/modules/projectproblog/projectproblog.php index a8bdca9..8256712 100644 --- a/modules/projectproblog/projectproblog.php +++ b/modules/projectproblog/projectproblog.php @@ -49,7 +49,8 @@ class Projectproblog extends Module return parent::install() && $this->installSql() && $this->installTabs() - && $this->registerHook('moduleRoutes'); + && $this->registerHook('moduleRoutes') + && $this->registerHook('displayHome'); } protected function createImgDir() @@ -195,6 +196,8 @@ class Projectproblog extends Module public function hookModuleRoutes() { + $this->ensureDisplayHomeHookRegistration(); + return [ 'module-projectproblog-list' => [ 'controller' => 'list', @@ -236,6 +239,21 @@ class Projectproblog extends Module ]; } + /** + * Zapewnia podpiecie hooka displayHome takze dla istniejacych instalacji. + */ + protected function ensureDisplayHomeHookRegistration() + { + $idHook = (int) Hook::getIdByName('displayHome'); + if ($idHook <= 0) { + return; + } + + if (!$this->isRegisteredInHook('displayHome')) { + $this->registerHook('displayHome'); + } + } + /* ------------------------------------------------------------------ */ /* HELPERS — generowanie linków */ /* ------------------------------------------------------------------ */ @@ -266,4 +284,43 @@ class Projectproblog extends Module $idLang ); } + + /* ------------------------------------------------------------------ */ + /* HOMEPAGE HOOK */ + /* ------------------------------------------------------------------ */ + + public function hookDisplayHome() + { + $idLang = (int) $this->context->language->id; + $posts = BlogPost::getLatest($idLang, 3); + + if (empty($posts)) { + return ''; + } + + $base = $this->context->link->getBaseLink(); + foreach ($posts as &$post) { + $post['thumbnail_url'] = $post['thumbnail'] + ? $base . 'modules/projectproblog/views/img/posts/' . $post['thumbnail'] + : null; + $post['url'] = self::getPostUrl($post['link_rewrite'], $idLang); + } + unset($post); + + if (isset($this->context->controller)) { + $this->context->controller->registerStylesheet( + 'module-projectproblog-blog', + 'modules/projectproblog/views/css/blog.css', + ['media' => 'all', 'priority' => 200] + ); + } + + $this->context->smarty->assign([ + 'blog_home_title' => $this->l('Najnowsze na blogu'), + 'blog_home_posts' => $posts, + 'blog_url' => self::getBlogUrl($idLang), + ]); + + return $this->display(__FILE__, 'views/templates/hook/home.tpl'); + } } diff --git a/modules/projectproblog/views/css/blog.css b/modules/projectproblog/views/css/blog.css index 6a58428..a1c0fdd 100644 --- a/modules/projectproblog/views/css/blog.css +++ b/modules/projectproblog/views/css/blog.css @@ -530,3 +530,60 @@ color: var(--blog-accent-dk); text-decoration: underline; } + +/* ---- Homepage: zajawki bloga -------------------------------- */ +#blog-home { + margin-top: 2.25rem; + margin-bottom: 2.5rem; +} + +.blog-home__header { + display: flex; + align-items: center; + justify-content: space-between; + gap: 1rem; + margin-bottom: 1rem; +} + +.blog-home__title { + margin: 0; + font-size: 1.5rem; + font-weight: 700; + color: var(--blog-text); + line-height: 1.25; +} + +.blog-home__all { + font-size: 0.85rem; + font-weight: 700; + text-transform: uppercase; + letter-spacing: 0.04em; + color: var(--blog-accent); + text-decoration: none; +} + +.blog-home__all:hover { + color: var(--blog-accent-dk); + text-decoration: underline; +} + +.blog-grid--home .blog-grid-item--home { + width: 33.3333%; +} + +@media (max-width: 991px) { + .blog-grid--home .blog-grid-item--home { + width: 50%; + } +} + +@media (max-width: 575px) { + .blog-home__header { + flex-direction: column; + align-items: flex-start; + } + + .blog-grid--home .blog-grid-item--home { + width: 100%; + } +} diff --git a/modules/projectproblog/views/templates/hook/home.tpl b/modules/projectproblog/views/templates/hook/home.tpl new file mode 100644 index 0000000..9b6c7f8 --- /dev/null +++ b/modules/projectproblog/views/templates/hook/home.tpl @@ -0,0 +1,50 @@ +{** + * Project-Pro Blog - sekcja zajawkowa na homepage + *} +{if $blog_home_posts} +
+
+

{$blog_home_title|escape:'html':'UTF-8'}

+ + {l s='Zobacz wszystkie wpisy' mod='projectproblog'} + +
+ +
+ {foreach from=$blog_home_posts item=post} +
+ +
+ {/foreach} +
+
+{/if} diff --git a/modules/projectproblog/views/templates/hook/index.php b/modules/projectproblog/views/templates/hook/index.php new file mode 100644 index 0000000..3c379e1 --- /dev/null +++ b/modules/projectproblog/views/templates/hook/index.php @@ -0,0 +1,4 @@ +