diff --git a/.github/workflows/phpstan.yml b/.github/workflows/phpstan.yml
index ccfa9d9..a3a4bab 100644
--- a/.github/workflows/phpstan.yml
+++ b/.github/workflows/phpstan.yml
@@ -16,7 +16,8 @@ jobs:
- name: Setup PHP
uses: shivammathur/setup-php@v2
with:
- php-version: '8.1'
+ extensions: pdo_sqlite
+ php-version: '8.2'
coverage: none
- name: Install composer dependencies
diff --git a/.github/workflows/run-tests.yml b/.github/workflows/run-tests.yml
index 7fefe35..94cf9b3 100644
--- a/.github/workflows/run-tests.yml
+++ b/.github/workflows/run-tests.yml
@@ -13,13 +13,16 @@ jobs:
fail-fast: true
matrix:
os: [ubuntu-latest, windows-latest]
- php: [8.2, 8.1]
- laravel: [10.*]
+ php: [8.2, 8.4]
+ laravel: [11.*, 12.*]
stability: [prefer-lowest, prefer-stable]
include:
- - laravel: 10.*
- testbench: 8.*
+ - laravel: 11.*
+ testbench: 9.*
carbon: ^2.63
+ - laravel: 12.*
+ testbench: 10.*
+ carbon: ^3.8.4
name: P${{ matrix.php }} - L${{ matrix.laravel }} - ${{ matrix.stability }} - ${{ matrix.os }}
diff --git a/composer.json b/composer.json
index 0e016f7..697fc31 100644
--- a/composer.json
+++ b/composer.json
@@ -28,16 +28,15 @@
"symfony/yaml": "^7.0"
},
"require-dev": {
+ "larastan/larastan": "^3.0",
"laravel/pint": "^1.0",
"nunomaduro/collision": "^8.0",
- "nunomaduro/larastan": "^2.0.1",
"orchestra/testbench": "^9.0|^10.0",
- "pestphp/pest": "^2.0",
- "pestphp/pest-plugin-arch": "^2.0",
- "pestphp/pest-plugin-laravel": "^2.0",
- "phpstan/extension-installer": "^1.1",
- "phpstan/phpstan-deprecation-rules": "^1.0",
- "phpstan/phpstan-phpunit": "^1.0"
+ "pestphp/pest": "^3.0",
+ "pestphp/pest-plugin-arch": "^3.0",
+ "pestphp/pest-plugin-laravel": "^3.0",
+ "phpstan/phpstan-deprecation-rules": "^2.0",
+ "phpstan/phpstan-phpunit": "^2.0"
},
"autoload": {
"psr-4": {
@@ -72,8 +71,7 @@
"config": {
"sort-packages": true,
"allow-plugins": {
- "pestphp/pest-plugin": true,
- "phpstan/extension-installer": true
+ "pestphp/pest-plugin": true
}
},
"extra": {
diff --git a/config/filament-knowledge-base.php b/config/filament-knowledge-base.php
index d6c43b5..13395cc 100644
--- a/config/filament-knowledge-base.php
+++ b/config/filament-knowledge-base.php
@@ -1,11 +1,19 @@
\Guava\FilamentKnowledgeBase\Models\FlatfileNode::class,
'cache' => [
'prefix' => env('FILAMENT_KB_CACHE_PREFIX', 'filament_kb_'),
- 'ttl' => env('FILAMENT_KB_CACHE_TTL', 'forever'),
+ 'ttl' => env('FILAMENT_KB_CACHE_TTL', 86400),
+ ],
+
+ 'icons' => [
+ NodeType::Documentation->value => 'heroicon-o-document',
+ NodeType::Link->value => 'heroicon-o-link',
+ NodeType::Group->value => null,
],
];
diff --git a/dist/js/anchors-component.js b/dist/js/anchors-component.js
index c2c0c75..041c0ce 100644
--- a/dist/js/anchors-component.js
+++ b/dist/js/anchors-component.js
@@ -24,7 +24,7 @@ function anchorsComponent() {
if (entry.isIntersecting) {
let section = "#" + entry.target.id;
document.querySelectorAll(".fi-sidebar-item-button .fi-sidebar-item-label").forEach((el2) => el2.classList.remove(...classes));
- let el = document.querySelector(".fi-sidebar-item-button[href='" + section + "'] .fi-sidebar-item-label");
+ let el = document.querySelector(".fi-sidebar-item-btn[href='" + section + "'] .fi-sidebar-item-label");
el.classList.add(...classes);
}
});
diff --git a/docs/v2/introduction.md b/docs/v2/introduction.md
index 5e00e99..93a00b1 100644
--- a/docs/v2/introduction.md
+++ b/docs/v2/introduction.md
@@ -57,7 +57,7 @@ And lastly, add the following to your custom filament theme to correctly build t
```css
@plugin "@tailwindcss/typography";
@source '../../../../vendor/guava/filament-knowledge-base/src/**/*';
-@source '../../../../vendor/guava/filament-knowledge-base/resources/view/**/*';
+@source '../../../../vendor/guava/filament-knowledge-base/resources/views/**/*';
```
> [!IMPORTANT]
diff --git a/phpstan.neon.dist b/phpstan.neon.dist
index aeda032..d00ec24 100644
--- a/phpstan.neon.dist
+++ b/phpstan.neon.dist
@@ -1,6 +1,6 @@
includes:
- phpstan-baseline.neon
- - ./vendor/nunomaduro/larastan/extension.neon
+ - vendor/larastan/larastan/extension.neon
parameters:
level: 4
@@ -11,5 +11,3 @@ parameters:
tmpDir: build/phpstan
checkOctaneCompatibility: true
checkModelProperties: true
- checkMissingIterableValueType: false
-
diff --git a/resources/lang/fr/translations.php b/resources/lang/fr/translations.php
index 1125ba0..4a77003 100644
--- a/resources/lang/fr/translations.php
+++ b/resources/lang/fr/translations.php
@@ -6,6 +6,6 @@
'open-documentation' => 'Ouvrir la documentation',
'close' => 'Fermer',
'back-to-default-panel' => 'Retour',
- 'url-copied' => 'URL copiée dans votre presse-papiers.',
- 'code-copied' => 'Code copié dans votre presse-papiers.',
+ 'url-copied' => 'URL copiée dans votre presse-papier.',
+ 'code-copied' => 'Code copié dans votre presse-papier.',
];
diff --git a/resources/lang/it/translations.php b/resources/lang/it/translations.php
new file mode 100644
index 0000000..626867d
--- /dev/null
+++ b/resources/lang/it/translations.php
@@ -0,0 +1,11 @@
+ 'Documentazione',
+ 'help' => 'Aiuto',
+ 'open-documentation' => 'Apri documentazione',
+ 'close' => 'Chiudi',
+ 'back-to-default-panel' => 'Indietro',
+ 'url-copied' => 'La URL è stata copiata nei tuoi appunti.',
+ 'code-copied' => 'Il codice è stato copiato nei tuoi appunti.',
+];
diff --git a/src/Actions/Forms/Components/HelpAction.php b/src/Actions/Forms/Components/HelpAction.php
index 5b3b285..9c37be1 100644
--- a/src/Actions/Forms/Components/HelpAction.php
+++ b/src/Actions/Forms/Components/HelpAction.php
@@ -31,13 +31,13 @@ protected static function getContentView(Documentable $documentable): HtmlString
return new HtmlString(\Str::replace($replacementStringId, $html, $parsed));
}
- public static function forDocumentable(Documentable | string $documentable): static
+ public static function forDocumentable(Documentable | string $documentable, ?string $panelId = null): static
{
- $documentable = KnowledgeBase::documentable($documentable);
+ $documentable = KnowledgeBase::documentable($documentable, $panelId);
return static::make("help.{$documentable->getId()}")
->label($documentable->getTitle())
-// ->icon($documentable->getIcon())
+ // ->icon($documentable->getIcon())
->icon('heroicon-o-question-mark-circle')
->when(
KnowledgeBase::companion()->hasModalPreviews(),
diff --git a/src/Actions/HelpAction.php b/src/Actions/HelpAction.php
index 9ac9447..7e2b53e 100644
--- a/src/Actions/HelpAction.php
+++ b/src/Actions/HelpAction.php
@@ -9,7 +9,10 @@
class HelpAction extends Action
{
- protected function setUp(): void {}
+ protected function setUp(): void
+ {
+ parent::setUp();
+ }
public function generic(): HelpAction
{
@@ -21,9 +24,9 @@ public function generic(): HelpAction
;
}
- public static function forDocumentable(Documentable | string $documentable): HelpAction
+ public static function forDocumentable(Documentable | string $documentable, ?string $panelId = null): HelpAction
{
- $documentable = KnowledgeBase::documentable($documentable);
+ $documentable = KnowledgeBase::documentable($documentable, $panelId);
return static::make("help.{$documentable->getId()}")
->label($documentable->getTitle())
@@ -31,10 +34,17 @@ public static function forDocumentable(Documentable | string $documentable): Hel
->when(
KnowledgeBase::companion()->hasModalPreviews(),
fn (HelpAction $action) => $action
- ->modal()
- ->modalContent(new HtmlString('test'))
- ->action(fn () => dd('test'))
-// ->alpineClickHandler('$dispatch(\"open-modal\", {id: "' . $documentable->getId() . '"})')
+ ->modalHeading(function () use ($documentable) {
+ return new HtmlString("
{$documentable->getTitle()}
");
+ })
+ ->modalContent(function () use ($documentable) {
+ $content = data_get($documentable->getData(), 'content', '');
+ $body = new HtmlString("{$content}
");
+
+ return $body;
+ })
+ ->modalCancelActionLabel(__('filament-knowledge-base::translations.close'))
+ ->modalSubmitAction(false)
->when(
KnowledgeBase::companion()->hasSlideOverPreviews(),
fn (HelpAction $action) => $action->slideOver()
diff --git a/src/Actions/Tables/Components/HelpAction.php b/src/Actions/Tables/Components/HelpAction.php
index c690bf5..6718644 100644
--- a/src/Actions/Tables/Components/HelpAction.php
+++ b/src/Actions/Tables/Components/HelpAction.php
@@ -31,13 +31,13 @@ protected static function getContentView(Documentable $documentable): HtmlString
return new HtmlString(\Str::replace($replacementStringId, $html, $parsed));
}
- public static function forDocumentable(Documentable | string $documentable): static
+ public static function forDocumentable(Documentable | string $documentable, ?string $panelId = null): static
{
- $documentable = KnowledgeBase::documentable($documentable);
+ $documentable = KnowledgeBase::documentable($documentable, $panelId);
return static::make("help.{$documentable->getId()}")
->label($documentable->getTitle())
-// ->icon($documentable->getIcon())
+ // ->icon($documentable->getIcon())
->icon('heroicon-o-question-mark-circle')
->when(
KnowledgeBase::companion()->hasModalPreviews(),
diff --git a/src/Commands/MakeDocumentationCommand.php b/src/Commands/MakeDocumentationCommand.php
index d5a9cb1..a85db21 100644
--- a/src/Commands/MakeDocumentationCommand.php
+++ b/src/Commands/MakeDocumentationCommand.php
@@ -2,15 +2,24 @@
namespace Guava\FilamentKnowledgeBase\Commands;
-use Guava\FilamentKnowledgeBase\KnowledgeBaseRegistry;
+use Filament\Facades\Filament;
+use Filament\Panel;
+use Guava\FilamentKnowledgeBase\Enums\NodeType;
+use Guava\FilamentKnowledgeBase\Plugins\KnowledgeBasePlugin;
use Illuminate\Console\GeneratorCommand;
+use Illuminate\Support\Arr;
use Illuminate\Support\Facades\App;
use Illuminate\Support\Facades\File;
use Illuminate\Support\Stringable;
+use function Laravel\Prompts\error;
+use function Laravel\Prompts\info;
+use function Laravel\Prompts\select;
+use function Laravel\Prompts\text;
+
class MakeDocumentationCommand extends GeneratorCommand
{
- protected $signature = 'docs:make {panel} {name} {--L|locale=*}';
+ protected $signature = 'docs:make {panel?} {type?} {name?} {--L|locale=*}';
protected $aliases = [
'kb:make',
@@ -20,9 +29,19 @@ class MakeDocumentationCommand extends GeneratorCommand
protected $type = 'Documentation';
+ protected NodeType $nodeType = NodeType::Documentation;
+
+ protected ?string $panelId = null;
+
+ protected ?string $docsId = null;
+
protected function getStub(): string
{
- return __DIR__ . '/../../stubs/markdown.md.stub';
+ return match ($this->nodeType) {
+ NodeType::Documentation => __DIR__ . '/../../stubs/documentation.md.stub',
+ NodeType::Group => __DIR__ . '/../../stubs/group.md.stub',
+ NodeType::Link => __DIR__ . '/../../stubs/link.md.stub',
+ };
}
protected function qualifyClass($name): string
@@ -30,53 +49,106 @@ protected function qualifyClass($name): string
return $name;
}
- // protected function getPath($name)
- // {
- // dd(\app(KnowledgeBaseRegistry::class)->getDocsPaths());
- // return str(base_path(config('filament-knowledge-base.docs-path')))
- // ->rtrim('/')
- // ->append(
- // '/',
- // str($name)
- // ->replaceEnd('.md', '')
- // ->append('.md')
- // )
- // ;
- // }
-
- // protected function getNameInput()
- // {
- // return str(parent::getNameInput())
- // ->trim('/')
- // ->replace('.', '/')
- // ->when(
- // ! $this->option('class'),
- // fn (Stringable $str) => $str->prepend($this->currentLocale, '/')
- // )
- // ->toString()
- // ;
- // }
-
- protected string $currentLocale;
-
- public function handle()
+ protected function getPath($name): string
{
- dd(\app(KnowledgeBaseRegistry::class)->getDocsPaths());
- $path = str(base_path(config('filament-knowledge-base.docs-path')))
+ return str($this->getDocsPath())
->rtrim('/')
- ->append('/')
+ ->when(
+ $this->currentLocale,
+ fn (Stringable $str) => $str
+ ->append(
+ '/',
+ $this->currentLocale
+ )
+ )
+ ->append(
+ '/',
+ str($name)
+ ->replaceEnd('.md', '')
+ ->append('.md')
+ )
+ ;
+ }
+
+ protected function getDocsPath(): string
+ {
+ /** @var KnowledgeBasePlugin $plugin */
+ $plugin = Filament::getPanel($this->panelId)->getPlugin(KnowledgeBasePlugin::ID);
+
+ return $plugin->getDocsPath();
+ }
+
+ protected function getNameInput(): string
+ {
+ return str($this->docsId)
+ ->trim('/')
+ ->replace('.', '/')
->toString()
;
- if (! File::exists($path)) {
- File::makeDirectory($path);
+ }
+
+ protected ?string $currentLocale = null;
+
+ public function handle(): bool
+ {
+ $knowledgeBasePanels = collect(Filament::getPanels())
+ ->filter(static fn (Panel $panel) => $panel->hasPlugin(KnowledgeBasePlugin::ID))
+ ->keys()
+ ;
+
+ if ($knowledgeBasePanels->isEmpty()) {
+ error('Please create a knowledge base panel first.');
+
+ return false;
+ }
+
+ $this->panelId = $knowledgeBasePanels->count() > 1
+ ? select(
+ label: 'Which knowledge base panel do you want to add a documentation page to?',
+ options: $knowledgeBasePanels,
+ required: true
+ )
+ : $knowledgeBasePanels->first();
+
+ $this->nodeType = NodeType::from(
+ select(
+ label: 'What node type do you want to create?',
+ options: collect(NodeType::cases())
+ ->mapWithKeys(fn (NodeType $type) => [$type->value => $type->name])->toArray(),
+ default: NodeType::Documentation->value,
+ )
+ );
+
+ $this->docsId = text(
+ label: 'Enter the ID of the documentation page in dot-notation:',
+ placeholder: 'Such as "users.introduction"',
+ required: true,
+ validate: ['name' => 'required|regex:/^[\w\-\.]+$/i']
+ );
+
+ $maximumNestingLevel = $this->nodeType === NodeType::Group ? 1 : 3;
+
+ if (count(explode('.', $this->docsId)) > $maximumNestingLevel) {
+ error("Maximum nesting level for type [{$this->nodeType->name}] is {$maximumNestingLevel}.");
+
+ return false;
+ }
+
+ $docsPath = $this->getDocsPath();
+ // Create docs path if not existing
+ if (! File::exists($docsPath)) {
+ File::makeDirectory(
+ path: $docsPath,
+ recursive: true
+ );
}
$locales = $this->option('locale');
$locales = empty($locales)
- ? File::directories($path)
+ ? File::directories($docsPath)
: $locales;
if (empty($locales)) {
- $locales[] = App::getLocale();
+ $locales = Arr::wrap(App::getLocale());
}
foreach ($locales as $locale) {
@@ -86,6 +158,10 @@ public function handle()
}
}
+ if ($this->nodeType === NodeType::Group) {
+ info('A group needs one or more child items in order to appear in your knowledge base panel. Call this command again to create the items.');
+ }
+
return true;
}
}
diff --git a/src/Concerns/HasKnowledgeBasePanelButton.php b/src/Concerns/HasKnowledgeBasePanelButton.php
index 6275701..a05ee77 100644
--- a/src/Concerns/HasKnowledgeBasePanelButton.php
+++ b/src/Concerns/HasKnowledgeBasePanelButton.php
@@ -49,7 +49,7 @@ protected function getDefaultKnowledgeBasePanelButton(): Action
->icon('heroicon-o-book-open')
->color('gray')
->extraAttributes([
- 'class' => '!font-medium !text-gray-700 dark:!text-gray-200 !mx-4 !mt-2 !mb-4 !py-2.5 !bg-transparent !flex !gap-0 space-x-1.5 !justify-start hover:!bg-gray-100 focus-visible:!bg-gray-100 dark:hover:!bg-white/5 dark:focus-visible:!bg-white/5',
+ 'class' => '!mx-4 !mb-4 !py-2.5 !flex space-x-1.5 !justify-start',
])
->url(KnowledgeBase::url(
Filament::getPanel($this->getKnowledgeBasePanelId())
diff --git a/src/Filament/Resources/DocumentationResource.php b/src/Filament/Resources/DocumentationResource.php
index 46a2f1e..f6b1c33 100644
--- a/src/Filament/Resources/DocumentationResource.php
+++ b/src/Filament/Resources/DocumentationResource.php
@@ -7,6 +7,7 @@
use Guava\FilamentKnowledgeBase\Facades\KnowledgeBase;
use Guava\FilamentKnowledgeBase\Filament\Pages\ViewDocumentation;
use Illuminate\Contracts\Support\Htmlable;
+use Illuminate\Database\Eloquent\Builder;
use Illuminate\Database\Eloquent\Model;
class DocumentationResource extends Resource
@@ -18,9 +19,20 @@ public static function getModel(): string
public static function getGloballySearchableAttributes(): array
{
- return ['title', 'content'];
+ return [
+ 'title',
+ 'data',
+ ];
}
+ // public static function modifyGlobalSearchQuery(Builder $query, string $search): void
+ // {
+ // // $query->orWhereRaw("
+ // // json_extract(data, '$.content') LIKE '%$search%';
+ // // ");
+ // $query->orWhereLike('data', "%$search%");
+ // }
+
protected static string | null | \BackedEnum $navigationIcon = 'heroicon-o-rectangle-stack';
public static function getPages(): array
@@ -44,9 +56,9 @@ public static function getGlobalSearchResultUrl(Model $record): ?string
public static function getGlobalSearchResultTitle(Model $record): string | Htmlable
{
- return str($record->slug)
- ->replace('/', ' -> ')
- ;
+ return $record->title;
+ // return str($record->slug)
+ // ->replace('/', ' -> ');
}
public static function resolveRecordRouteBinding(int | string $key, ?\Closure $modifyQuery = null): ?Model
diff --git a/src/KnowledgeBase.php b/src/KnowledgeBase.php
index 6714095..502533a 100755
--- a/src/KnowledgeBase.php
+++ b/src/KnowledgeBase.php
@@ -111,17 +111,23 @@ public function url(Panel $panel): ?string
return $url;
}
- public function documentable(Documentable | string $documentable): Documentable
+ public function documentable(Documentable | string $documentable, ?string $panelId = null): Documentable
{
if ($documentable instanceof Documentable) {
return $documentable;
}
- if ($model = static::model()::query()->find(static::panel()->getId() . '.' . $documentable)) {
+ $panelId ??= static::panel()->getId();
+
+ if (! Filament::getPanel($panelId)) {
+ throw new Exception('The provided panel does not exist.');
+ }
+
+ if ($model = $this->model()::query()->find($panelId . '.' . $documentable)) {
return $model;
- } else {
- throw new Exception("'The provided documentable \"$documentable\" could not be found.'");
}
+
+ throw new Exception("'The provided documentable \"$documentable\" could not be found.'");
}
public function markdown(Documentable | string $documentable): HtmlString
diff --git a/src/Markdown/MarkdownRenderer.php b/src/Markdown/MarkdownRenderer.php
index d865ee8..90c30a2 100644
--- a/src/Markdown/MarkdownRenderer.php
+++ b/src/Markdown/MarkdownRenderer.php
@@ -65,6 +65,7 @@ protected function getOptions(): array
],
'heading_permalink' => [
'id_prefix' => '',
+ 'fragment_prefix' => '',
'symbol' => $anchorSymbol ?? '',
'html_class' => Arr::toCssClasses([
'gu-kb-anchor md:absolute md:-left-8 mr-2 md:mr-0 text-primary-600 dark:text-primary-500 font-bold !no-underline -mt-20 pt-20',
diff --git a/src/Models/FlatfileNode.php b/src/Models/FlatfileNode.php
index 87aa155..9498f7c 100644
--- a/src/Models/FlatfileNode.php
+++ b/src/Models/FlatfileNode.php
@@ -14,6 +14,7 @@
use Illuminate\Database\Eloquent\Builder;
use Illuminate\Database\Eloquent\Collection;
use Illuminate\Database\Eloquent\Model;
+use Illuminate\Support\Arr;
use Illuminate\Support\Facades\App;
use Illuminate\Support\Facades\File;
use League\CommonMark\Extension\HeadingPermalink\HeadingPermalink;
@@ -187,7 +188,7 @@ public function toNavigationItem(): NavigationItem
return $item;
}
- public function toNavigationGroup(bool $canHaveIcon = true): NavigationGroup
+ public function toNavigationGroup(): NavigationGroup
{
if ($this->type !== NodeType::Group) {
throw new \Exception('Cannot convert a document to a navigation group');
@@ -281,10 +282,12 @@ public function getRouteKeyName(): string
protected function getDefaultIcon(): ?string
{
+ $icons = config('filament-knowledge-base.icons');
+
return match ($this->getType()) {
- NodeType::Documentation => 'heroicon-o-document',
- NodeType::Link => 'heroicon-o-link',
- NodeType::Group => null,
+ NodeType::Documentation => Arr::get($icons, NodeType::Documentation->value, 'heroicon-o-document'),
+ NodeType::Link => Arr::get($icons, NodeType::Link->value, 'heroicon-o-link'),
+ NodeType::Group => Arr::get($icons, NodeType::Group->value),
};
}
}
diff --git a/src/Plugins/KnowledgeBaseCompanionPlugin.php b/src/Plugins/KnowledgeBaseCompanionPlugin.php
index a528bd5..c72e12a 100644
--- a/src/Plugins/KnowledgeBaseCompanionPlugin.php
+++ b/src/Plugins/KnowledgeBaseCompanionPlugin.php
@@ -97,8 +97,11 @@ public function register(Panel $panel): void
'label' => null,
'items' => [
NavigationItem::make(__('filament-knowledge-base::translations.knowledge-base'))
- ->url(Filament::getPanel($this->getKnowledgeBasePanelId())->getUrl())
- ->icon('heroicon-o-home'),
+ ->url(
+ Filament::getPanel($this->getKnowledgeBasePanelId())->getUrl(),
+ $this->shouldOpenKnowledgeBasePanelInNewTab()
+ )
+ ->icon('heroicon-o-book-open'),
],
])
// fn (): string => Blade::render('filament-panels::components.sidebar.item', [
@@ -106,7 +109,7 @@ public function register(Panel $panel): void
// 'icon' => 'heroicon-o-user',
// 'slot' => new HtmlString('test'),
// ]),
- // fn (): string => $this->getKnowledgeBasePanelButton()->render(),
+ // fn (): string => $this->getKnowledgeBasePanelButton()->toHtml(),
)
)
// ->renderHook(
diff --git a/src/Plugins/KnowledgeBasePlugin.php b/src/Plugins/KnowledgeBasePlugin.php
index d6589b3..cedb5ed 100644
--- a/src/Plugins/KnowledgeBasePlugin.php
+++ b/src/Plugins/KnowledgeBasePlugin.php
@@ -3,6 +3,7 @@
namespace Guava\FilamentKnowledgeBase\Plugins;
use Filament\Contracts\Plugin;
+use Filament\Facades\Filament;
use Filament\Panel;
use Filament\Support\Concerns\EvaluatesClosures;
use Filament\View\PanelsRenderHook;
@@ -72,7 +73,10 @@ public function register(Panel $panel): void
public function boot(Panel $panel): void
{
- Navigation::make($panel)->build();
+ // Defer building navigation until Filament is serving a request to avoid early model autoloading
+ Filament::serving(function () use ($panel) {
+ Navigation::make($panel)->build();
+ });
}
public static function make(?string $docsPath = null): static
diff --git a/src/Support/FlatfileParser.php b/src/Support/FlatfileParser.php
index 4f9e482..2be0f1c 100644
--- a/src/Support/FlatfileParser.php
+++ b/src/Support/FlatfileParser.php
@@ -25,6 +25,7 @@ public function __construct(
public function get(): Collection
{
collect(File::allFiles($this->path))
+ ->filter(fn (SplFileInfo $file) => in_array(strtolower($file->getExtension()), ['md', 'markdown']))
->each(fn (SplFileInfo $file) => $this->processFile($file))
;
diff --git a/stubs/documentation.md.stub b/stubs/documentation.md.stub
new file mode 100644
index 0000000..bb5805b
--- /dev/null
+++ b/stubs/documentation.md.stub
@@ -0,0 +1,4 @@
+---
+type: documentation
+---
+
diff --git a/stubs/group.md.stub b/stubs/group.md.stub
new file mode 100644
index 0000000..5749321
--- /dev/null
+++ b/stubs/group.md.stub
@@ -0,0 +1,4 @@
+---
+type: group
+---
+
diff --git a/stubs/link.md.stub b/stubs/link.md.stub
new file mode 100644
index 0000000..bf4faba
--- /dev/null
+++ b/stubs/link.md.stub
@@ -0,0 +1,5 @@
+---
+type: link
+url: "#"
+---
+
diff --git a/stubs/markdown.md.stub b/stubs/markdown.md.stub
deleted file mode 100644
index 7390094..0000000
--- a/stubs/markdown.md.stub
+++ /dev/null
@@ -1,4 +0,0 @@
----
-
----
-
diff --git a/tests/TestCase.php b/tests/TestCase.php
index e4e19fd..78ddc27 100644
--- a/tests/TestCase.php
+++ b/tests/TestCase.php
@@ -2,7 +2,7 @@
namespace Guava\FilamentKnowledgeBase\Tests;
-use Guava\FilamentKnowledgeBase\FilamentKnowledgeBaseServiceProvider;
+use Guava\FilamentKnowledgeBase\KnowledgeBaseServiceProvider;
use Illuminate\Database\Eloquent\Factories\Factory;
use Orchestra\Testbench\TestCase as Orchestra;
@@ -20,7 +20,7 @@ protected function setUp(): void
protected function getPackageProviders($app)
{
return [
- FilamentKnowledgeBaseServiceProvider::class,
+ KnowledgeBaseServiceProvider::class,
];
}