Skip to content

Properties

A resource is configured with protected properties; methods with the same names can be overridden for computed or translated values.

final class OrderItemResource extends Resource
{
protected string $model = OrderItemModel::class;
protected ?string $slug = 'order-items';
protected ?string $label = 'Order item';
protected ?string $pluralLabel = 'Order items';
protected string $recordTitleAttribute = 'product';
protected string $navigationIcon = 'basket';
protected ?string $navigationGroup = 'Sales';
protected int $navigationSort = 20;
protected bool $registerNavigation = false; // only reachable as relation
}
Property Default Purpose
$model – (required) model class, must extend Anvil\Data\Model (LogicException otherwise)
$slug plural kebab case of the class without Resource: OrderItemResource → order-items URI segment and prefix of the permissions
$label humanized class name: “Order item” singular, e.g. “New order item”
$pluralLabel humanized plural: “Order items” navigation, list heading, breadcrumbs
$recordTitleAttribute name attribute shown as title of a record: detail heading, breadcrumbs, cards, global search; the label when empty

Translated names: override the methods.

public function label(): string { return lang('Sales.orderItem'); }
public function pluralLabel(): string { return lang('Sales.orderItems'); }
public function recordTitle(array|object $record): string { return $record->number . ' – ' . $record->product; }

The slug is part of URLs, permissions, component ids and saved views: choose it once.

Property Default Purpose
$navigationIcon folder Bootstrap Icons name
$navigationGroup none group in the sidebar; override navigationGroup() for a translated name
$navigationSort 0 order within the group
$registerNavigation true false hides the entry; the pages stay reachable, e.g. from a relation

navigationBadge() and navigationBadgeColor() add a badge, e.g. the number of open records, see Badges. The entry is only shown to users with <slug>.view.

Property Default Enables
$globalSearch [] columns of the global search
$exportable false exports of the list for users with <slug>.export, see Exports
$attachments false files on the detail page, see Attachments
$relationTabs false related records as tabs instead of sections, see As tabs
$api [] operations for API clients: list, show, create, update, delete, actions, transitions, see API
$workflows [] workflow classes of the records, see Workflows
Method Purpose Details
form(Form $form) the form (required) Forms
collection(Collection $collection) the list (required) Tables
relations() related records on the detail page Related records
actions(), bulkActions() actions Actions
detailComponents() own sections on the detail page Detail page
listWidgets() widgets above the list Widgets above the list
scopeQuery(), formValues(), createRecord(), updateRecord(), deleteRecord(), afterSave() loading and saving Loading and saving
canViewAny(), canView(), canCreate(), canUpdate(), canDelete(), canExport(), canViewHistory() permissions Permissions
showsHistory() false hides the history History
globalSearchDescription() second line of a search hit Global search
apiRepresentation(), apiRepresentationSchema() JSON of a record in the API API
fileOwner() owner of the files of the records (default: the class) Files
Method Returns
panel() the panel the resource belongs to
model() a new model instance (no scope)
query() a new model with scopeQuery() applied
findRecord($uuid) the record by UUID within the scope, or null
recordKey($record) the internal primary key – never send it to the browser
recordUuid($record) the UUID
recordTitle($record) the title
url($page, $uuid), path($page, $uuid) URL or path of index, create, view, edit
getForm(), getCollection() the built form and collection
permission('view') <slug>.view