initial COmmit: Add KB Antora Importer plugin files
This commit is contained in:
231
kb-antora-importer/includes/Plugin.php
Normal file
231
kb-antora-importer/includes/Plugin.php
Normal file
@@ -0,0 +1,231 @@
|
||||
<?php
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace KbAntoraImporter;
|
||||
|
||||
use KbAntoraImporter\Admin\SettingsPage;
|
||||
use KbAntoraImporter\Admin\StatusPage;
|
||||
use KbAntoraImporter\Admin\SyncPage;
|
||||
use KbAntoraImporter\Frontend\Router;
|
||||
use KbAntoraImporter\Frontend\SearchController;
|
||||
use KbAntoraImporter\Import\ImportManager;
|
||||
|
||||
final class Plugin
|
||||
{
|
||||
private static ?self $instance = null;
|
||||
|
||||
public static function instance(): self
|
||||
{
|
||||
if (null === self::$instance) {
|
||||
self::$instance = new self();
|
||||
}
|
||||
|
||||
return self::$instance;
|
||||
}
|
||||
|
||||
public function boot(): void
|
||||
{
|
||||
add_action('init', [$this, 'registerContentTypes']);
|
||||
add_action('init', [$this, 'registerShortcodes']);
|
||||
add_action('admin_menu', [$this, 'registerAdminPages']);
|
||||
add_action('admin_init', [SettingsPage::class, 'registerSettings']);
|
||||
add_action('rest_api_init', [$this, 'registerRestRoutes']);
|
||||
add_filter('cron_schedules', [$this, 'addCronSchedules']);
|
||||
add_action('kb_antora_importer_cron_sync', [$this, 'runCronSync']);
|
||||
add_action('wp_enqueue_scripts', [$this, 'enqueueFrontendAssets']);
|
||||
|
||||
(new Router())->boot();
|
||||
}
|
||||
|
||||
public static function activate(): void
|
||||
{
|
||||
self::instance()->registerContentTypes();
|
||||
(new Router())->addRewriteRules();
|
||||
self::grantCapabilities();
|
||||
self::ensureDefaultSettings();
|
||||
flush_rewrite_rules();
|
||||
}
|
||||
|
||||
public static function deactivate(): void
|
||||
{
|
||||
wp_clear_scheduled_hook('kb_antora_importer_cron_sync');
|
||||
flush_rewrite_rules();
|
||||
}
|
||||
|
||||
public function registerContentTypes(): void
|
||||
{
|
||||
register_post_type('kb_doc_page', [
|
||||
'labels' => [
|
||||
'name' => __('Documentation Pages', 'kb-antora-importer'),
|
||||
'singular_name' => __('Documentation Page', 'kb-antora-importer'),
|
||||
],
|
||||
'public' => false,
|
||||
'show_ui' => true,
|
||||
'show_in_menu' => 'kb-antora-importer',
|
||||
'show_in_rest' => true,
|
||||
'supports' => ['title', 'editor', 'excerpt', 'custom-fields'],
|
||||
'capability_type' => 'post',
|
||||
]);
|
||||
|
||||
register_taxonomy('kb_product', ['kb_doc_page'], [
|
||||
'labels' => [
|
||||
'name' => __('Products', 'kb-antora-importer'),
|
||||
'singular_name' => __('Product', 'kb-antora-importer'),
|
||||
],
|
||||
'public' => false,
|
||||
'show_ui' => true,
|
||||
'show_in_rest' => true,
|
||||
'hierarchical' => false,
|
||||
'rewrite' => false,
|
||||
]);
|
||||
|
||||
register_taxonomy('kb_version', ['kb_doc_page'], [
|
||||
'labels' => [
|
||||
'name' => __('Versions', 'kb-antora-importer'),
|
||||
'singular_name' => __('Version', 'kb-antora-importer'),
|
||||
],
|
||||
'public' => false,
|
||||
'show_ui' => true,
|
||||
'show_in_rest' => true,
|
||||
'hierarchical' => false,
|
||||
'rewrite' => false,
|
||||
]);
|
||||
|
||||
register_taxonomy('kb_component', ['kb_doc_page'], [
|
||||
'labels' => [
|
||||
'name' => __('Components', 'kb-antora-importer'),
|
||||
'singular_name' => __('Component', 'kb-antora-importer'),
|
||||
],
|
||||
'public' => false,
|
||||
'show_ui' => true,
|
||||
'show_in_rest' => true,
|
||||
'hierarchical' => false,
|
||||
'rewrite' => false,
|
||||
]);
|
||||
}
|
||||
|
||||
public function registerAdminPages(): void
|
||||
{
|
||||
add_menu_page(
|
||||
__('Knowledgebase', 'kb-antora-importer'),
|
||||
__('Knowledgebase', 'kb-antora-importer'),
|
||||
'manage_kb_docs',
|
||||
'kb-antora-importer',
|
||||
[StatusPage::class, 'render'],
|
||||
'dashicons-welcome-learn-more',
|
||||
58
|
||||
);
|
||||
|
||||
add_submenu_page('kb-antora-importer', __('Overview', 'kb-antora-importer'), __('Overview', 'kb-antora-importer'), 'manage_kb_docs', 'kb-antora-importer', [StatusPage::class, 'render']);
|
||||
add_submenu_page('kb-antora-importer', __('Synchronization', 'kb-antora-importer'), __('Synchronization', 'kb-antora-importer'), 'sync_kb_docs', 'kb-antora-sync', [SyncPage::class, 'render']);
|
||||
add_submenu_page('kb-antora-importer', __('Settings', 'kb-antora-importer'), __('Settings', 'kb-antora-importer'), 'manage_kb_docs', 'kb-antora-settings', [SettingsPage::class, 'render']);
|
||||
}
|
||||
|
||||
public function registerRestRoutes(): void
|
||||
{
|
||||
register_rest_route('kb-antora/v1', '/status', [
|
||||
'methods' => 'GET',
|
||||
'callback' => [StatusPage::class, 'restStatus'],
|
||||
'permission_callback' => static fn (): bool => current_user_can('manage_kb_docs'),
|
||||
]);
|
||||
|
||||
register_rest_route('kb-antora/v1', '/sync', [
|
||||
'methods' => 'POST',
|
||||
'callback' => static fn (\WP_REST_Request $request): \WP_REST_Response => (new ImportManager())->syncAll((bool) $request->get_param('dry_run')),
|
||||
'permission_callback' => static fn (): bool => current_user_can('sync_kb_docs'),
|
||||
]);
|
||||
|
||||
register_rest_route('kb-antora/v1', '/sync/project', [
|
||||
'methods' => 'POST',
|
||||
'callback' => static fn (\WP_REST_Request $request): \WP_REST_Response => (new ImportManager())->syncProject((string) $request->get_param('project_id'), (bool) $request->get_param('dry_run')),
|
||||
'permission_callback' => static fn (): bool => current_user_can('sync_kb_docs'),
|
||||
]);
|
||||
|
||||
register_rest_route('kb-antora/v1', '/search', [
|
||||
'methods' => 'GET',
|
||||
'callback' => [SearchController::class, 'restSearch'],
|
||||
'permission_callback' => '__return_true',
|
||||
]);
|
||||
|
||||
register_rest_route('kb-antora/v1', '/gitlab-webhook', [
|
||||
'methods' => 'POST',
|
||||
'callback' => static fn (): \WP_REST_Response => new \WP_REST_Response(['queued' => false, 'message' => 'Webhook endpoint is reserved for a later event-driven sync implementation.']),
|
||||
'permission_callback' => static fn (): bool => current_user_can('sync_kb_docs'),
|
||||
]);
|
||||
}
|
||||
|
||||
public function registerShortcodes(): void
|
||||
{
|
||||
add_shortcode('kb_docs_index', [Router::class, 'shortcodeDocsIndex']);
|
||||
add_shortcode('kb_docs', [Router::class, 'shortcodeDocsApp']);
|
||||
add_shortcode('kb_product_index', [Router::class, 'shortcodeProductIndex']);
|
||||
add_shortcode('kb_search', [SearchController::class, 'shortcodeSearch']);
|
||||
}
|
||||
|
||||
public function addCronSchedules(array $schedules): array
|
||||
{
|
||||
$schedules['kb_antora_weekly'] = [
|
||||
'interval' => WEEK_IN_SECONDS,
|
||||
'display' => __('Weekly', 'kb-antora-importer'),
|
||||
];
|
||||
|
||||
return $schedules;
|
||||
}
|
||||
|
||||
public function runCronSync(): void
|
||||
{
|
||||
(new ImportManager())->syncAll(false);
|
||||
}
|
||||
|
||||
public function enqueueFrontendAssets(): void
|
||||
{
|
||||
wp_enqueue_style('kb-antora-frontend', KB_ANTORA_IMPORTER_URL . 'assets/css/frontend.css', [], KB_ANTORA_IMPORTER_VERSION);
|
||||
wp_enqueue_script('kb-antora-frontend', KB_ANTORA_IMPORTER_URL . 'assets/js/frontend.js', [], KB_ANTORA_IMPORTER_VERSION, true);
|
||||
}
|
||||
|
||||
public static function settings(): array
|
||||
{
|
||||
return wp_parse_args((array) get_option('kb_antora_importer_settings', []), Settings::defaults());
|
||||
}
|
||||
|
||||
public static function syncCronSchedule(?array $settings = null): void
|
||||
{
|
||||
$settings = $settings ?: self::settings();
|
||||
wp_clear_scheduled_hook('kb_antora_importer_cron_sync');
|
||||
|
||||
if ('disabled' === $settings['cron_interval']) {
|
||||
return;
|
||||
}
|
||||
|
||||
$schedule = match ($settings['cron_interval']) {
|
||||
'hourly' => 'hourly',
|
||||
'daily' => 'daily',
|
||||
'weekly' => 'kb_antora_weekly',
|
||||
default => '',
|
||||
};
|
||||
|
||||
if ($schedule && ! wp_next_scheduled('kb_antora_importer_cron_sync')) {
|
||||
wp_schedule_event(time() + HOUR_IN_SECONDS, $schedule, 'kb_antora_importer_cron_sync');
|
||||
}
|
||||
}
|
||||
|
||||
private static function ensureDefaultSettings(): void
|
||||
{
|
||||
if (false === get_option('kb_antora_importer_settings', false)) {
|
||||
add_option('kb_antora_importer_settings', Settings::defaults(), '', false);
|
||||
}
|
||||
}
|
||||
|
||||
private static function grantCapabilities(): void
|
||||
{
|
||||
$role = get_role('administrator');
|
||||
|
||||
if (! $role) {
|
||||
return;
|
||||
}
|
||||
|
||||
foreach (['manage_kb_docs', 'view_kb_docs', 'sync_kb_docs'] as $capability) {
|
||||
$role->add_cap($capability);
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user