Awn Awn
Back to Awn
Documentation menu — Build a plugin
Build / Build a plugin
Version
1.0
Last verified
2026-08-09

Build plugins

plugins/PackageName/
├── plugin.json
├── PackageNamePlugin.php
├── Http/{Controllers,Requests}/
├── Models/
├── Policies/
├── database/migrations/
├── resources/views/{dashboard,admin,site,widgets}/
└── routes/web.php

Composer maps Awn\Plugins\ to plugins/.

interface SitePlugin
{
    public function key(): PluginKey;
    public function settingsRules(): array;
    public function normalizeSettings(array $settings): array;
    public function render(
        PluginSlot $slot,
        PluginRenderContext $context,
        array $settings,
    ): ?View;
}

Optional contracts are:

  • ContributesDashboard and ContributesDashboardWidgets for one organization's admin.
  • ContributesSuperAdminPages and ContributesSuperAdminWidgets for global platform operators.
  • ContributesPages and SitePlugin::render() for the public site and active theme.
  • SeedsPluginData for install-time package seeders.

None is mandatory. A storage-only plugin may implement no UI contribution; a theme add-on may render one slot; a business package may use every surface.

Registration

Add one PluginKey case plus driver/directory arms, matching manifest, driver, existing routes/web.php, first-party views, and package data assets. All plugin controller routes must use plugin.{slug}..

Keep settings and management URLs separate. /charity/{organization}/plugins/{slug} belongs to the platform settings controller; package dashboards should use /plugins/{slug}/manage/.... PluginDefinitionValidator rejects contributed dashboards that collide with the settings URL.

Match route availability to each contribution: requiresEnabled: true uses plugin.available:{slug}; requiresEnabled: false uses plugin.available:{slug},installed. Validation rejects mismatches.

Tenant tables need ownership FK and tenant-leading constraints; models use BelongsToOrganization and guard ownership.

Lifecycle

php artisan awn:plugin:install {slug}
php artisan awn:plugin:uninstall {slug}
php artisan awn:plugin:uninstall {slug} --purge

Install validates definitions, runs package migrations/declared seeders, synchronizes catalog, marks installed/active, and clears affected caches. Normal uninstall globally deactivates and preserves assignments/tables. Purge confirms, deletes all assignments, reverses package migrations, and marks installed/active false; it keeps the catalog row.

Organization configure is separate. Enable validates installation/activity, compatibility, and CMS collisions, then normalizes/stores settings. Disable preserves data and records disabled_at.

Choose the next guide

For a complex plugin, create tenant models and reversible migrations first, then add only the surfaces the product needs. Test cross-tenant IDs, private files, direct authorization, state transitions, preview/publication, global deactivation, and purge.