Is there any simple way to create a collection of pages that will use users list
check if they have any posts and on a detailed page show info about author and the list of the pages related to him
For now, I understand how to do it in this way:
- create blueprint authors
- create blueprint author with field user (to select from users list) and maybe some additional fields that not used in users collection
- create templates authors / author
- create manually all needed authors in backend and attach to them users
but how it could be done with virtual pages…? or any other algorithm to do it automaticly
I think i found solution, but still need to double check
First I check all unique authors that have some posts here:
$pages = pages('reviews', 'news')->children()->listed();
$ids = $pages->pluck('author', '-', true);
// get a list of all authors filtered by the ones with articles
$array = kirby()->users()->filter(fn ($user) => in_array($user->uuid()->toString(), $ids, true))->toArray();
Then I create virtual pages for these authors
$authors = array_map(function ($author) {
$slug = Str::slug($author['username']);
return [
'slug' => $slug,
'num' => 0,
'template' => 'author',
'content' => $author['content']
];
}, $array);
the full model is looks like this:
<?php
use Kirby\Cms\User;
use Kirby\Cms\Users;
use Kirby\Cms\Page;
use Kirby\Cms\Pages;
class AuthorsPage extends Page
{
public function children(): Kirby\Cms\Pages
{
$pages = pages('reviews', 'news')->children()->listed();
$ids = $pages->pluck('author', '-', true);
// get a list of all authors filtered by the ones with articles
$array = kirby()->users()->filter(fn ($user) => in_array($user->uuid()->toString(), $ids, true))->toArray();
$authors = array_map(function ($author) {
$slug = Str::slug($author['username']);
return [
'slug' => $slug,
'num' => 0,
'template' => 'author',
'content' => $author['content']
];
}, $array);
return Pages::factory($authors, $this);
}
}
Than on Author page I will be able to get username / avatar and find his articles by author uid
So it looks like this should works.