Skip to content

Commit ff638ec

Browse files
committed
Progress on getting started
1 parent 3378358 commit ff638ec

File tree

2 files changed

+161
-5
lines changed

2 files changed

+161
-5
lines changed

src/guide/start/creating-project.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ It can serve as a good starting point for your projects.
1212

1313
You can create a new project from a template using the [Composer](https://getcomposer.org) package manager:
1414

15-
```
15+
```sh
1616
composer create-project yiisoft/app your_project
1717
```
1818

@@ -38,7 +38,7 @@ APP_ENV=dev ./yii serve --port=80
3838

3939
For Docker users, run:
4040

41-
```
41+
```sh
4242
make up
4343
```
4444

src/guide/start/databases.md

Lines changed: 159 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -331,19 +331,175 @@ final readonly class PageRepository
331331
);
332332
}
333333
334-
public function delete(string $id): void
334+
public function deleteBySlug(string $slug): void
335335
{
336-
$this->connection->createCommand()->delete('{{%page}}', ['id' => $id])->execute();
336+
$this->connection->createCommand()->delete('{{%page}}', ['slug' => $slug])->execute();
337337
}
338338
}
339339
```
340340

341341
## Actions and routes
342342

343-
You need actions to:
343+
You need to be able to:
344344

345345
1. List all pages.
346346
2. View a page.
347347
3. Delete a page.
348348
4. Create a page.
349349
5. Edit a page.
350+
351+
Let's tackle these one by one.
352+
353+
354+
### List all pages
355+
356+
Create `src/Web/Page/ListAction.php`:
357+
358+
```php
359+
<?php
360+
361+
declare(strict_types=1);
362+
363+
namespace App\Web\Page;
364+
365+
use Psr\Http\Message\ResponseInterface;
366+
use Yiisoft\Yii\View\Renderer\ViewRenderer;
367+
368+
final readonly class ListAction
369+
{
370+
public function __construct(
371+
private ViewRenderer $viewRenderer,
372+
private PageRepository $pageRepository,
373+
)
374+
{
375+
}
376+
377+
public function __invoke(): ResponseInterface
378+
{
379+
return $this->viewRenderer->render(__DIR__ . '/list', [
380+
'pages' => $this->pageRepository->findAll(),
381+
]);
382+
}
383+
}
384+
```
385+
386+
Define list view in `src/Web/Page/list.php`:
387+
388+
```php
389+
<?php
390+
use App\Web\Page\Page;
391+
use Yiisoft\Html\Html;
392+
393+
/** @var iterable<Page> $pages */
394+
?>
395+
396+
<ul>
397+
<?php foreach ($pages as $page): ?>
398+
<li>
399+
<?= Html::a($page->title, $this->urlGenerator->generate('page/view', ['slug' => $page->slug])) ?>
400+
</li>
401+
<?php endforeach ?>
402+
</ul>
403+
```
404+
405+
### View a page
406+
407+
Create `src/Web/Page/ViewAction.php`:
408+
409+
```php
410+
<?php
411+
412+
declare(strict_types=1);
413+
414+
namespace App\Web\Page;
415+
416+
use Psr\Http\Message\ResponseFactoryInterface;
417+
use Psr\Http\Message\ResponseInterface;
418+
use Yiisoft\Http\Status;
419+
use Yiisoft\Router\HydratorAttribute\RouteArgument;
420+
use Yiisoft\Yii\View\Renderer\ViewRenderer;
421+
422+
final readonly class ViewAction
423+
{
424+
public function __construct(
425+
private ViewRenderer $viewRenderer,
426+
private PageRepository $pageRepository,
427+
private ResponseFactoryInterface $responseFactory
428+
)
429+
{
430+
}
431+
432+
public function __invoke(
433+
#[RouteArgument('slug')]
434+
string $slug
435+
): ResponseInterface
436+
{
437+
$page = $this->pageRepository->findOneBySlug($slug);
438+
if ($page === null || $page->isDeleted()) {
439+
return $this->responseFactory->createResponse(Status::NOT_FOUND);
440+
}
441+
442+
return $this->viewRenderer->render(__DIR__ . '/view', [
443+
'page' => $page,
444+
]);
445+
}
446+
}
447+
```
448+
449+
Now, a template in `src/Web/Page/view.php`:
450+
451+
```php
452+
<?php
453+
use App\Web\Page\Page;
454+
use Yiisoft\Html\Html;
455+
456+
/** @var Page $page */
457+
?>
458+
459+
<h1><?= Html::encode($page->title) ?></h1>
460+
461+
<p>
462+
<?= Html::encode($page->text) ?>
463+
</p>
464+
```
465+
466+
### Delete a page
467+
468+
Create `src/Web/Page/DeleteAction.php`:
469+
470+
```php
471+
<?php
472+
473+
declare(strict_types=1);
474+
475+
namespace App\Web\Page;
476+
477+
use Psr\Http\Message\ResponseFactoryInterface;
478+
use Psr\Http\Message\ResponseInterface;
479+
use Yiisoft\Http\Status;
480+
use Yiisoft\Router\UrlGeneratorInterface;
481+
482+
final readonly class DeleteAction
483+
{
484+
public function __construct(
485+
private PageRepository $pageRepository,
486+
private ResponseFactoryInterface $responseFactory,
487+
private UrlGeneratorInterface $urlGenerator,
488+
)
489+
{}
490+
491+
public function __invoke(string $slug): ResponseInterface
492+
{
493+
$this->pageRepository->deleteBySlug($slug);
494+
495+
return $this->responseFactory
496+
->createResponse()
497+
->withStatus(Status::PERMANENT_REDIRECT)
498+
->withHeader('Location', $this->urlGenerator->generate('page/list'));
499+
}
500+
}
501+
```
502+
503+
### Create a page
504+
505+

0 commit comments

Comments
 (0)