Merge pull request #11848 from filamentphp/feature/section-save

feature: Section save
This commit is contained in:
Dan Harrin
2024-03-14 10:51:02 +00:00
committed by GitHub
3 changed files with 80 additions and 6 deletions
+6 -6
View File
@@ -69,15 +69,15 @@ use Filament\Forms\Components\Actions\Action;
use Filament\Forms\Components\Section;
Section::make('Rate limiting')
->schema([
// ...
])
->footerActions([
Action::make('test')
->action(function () {
// ...
}),
])
->schema([
// ...
])
```
<AutoScreenshot name="forms/layout/section/footer/actions" alt="Section with footer actions" version="3.x" />
@@ -94,6 +94,9 @@ use Filament\Forms\Components\Section;
use Filament\Support\Enums\Alignment;
Section::make('Rate limiting')
->schema([
// ...
])
->footerActions([
Action::make('test')
->action(function () {
@@ -101,9 +104,6 @@ Section::make('Rate limiting')
}),
])
->footerActionsAlignment(Alignment::End)
->schema([
// ...
])
```
### Adding actions to a section without heading
@@ -178,6 +178,37 @@ class EditUser extends EditRecord
Alternatively, if you're editing records in a modal action, check out the [Actions documentation](../../actions/prebuilt-actions/edit#lifecycle-hooks).
## Saving a part of the form independently
You may want to allow the user to save a part of the form independently of the rest of the form. One way to do this is with a [section action in the header or footer](../../forms/layout/section#adding-actions-to-the-sections-header-or-footer). From the `action()` method, you can call `saveFormComponentOnly()`, passing in the `Section` component that you want to save:
```php
use Filament\Forms\Components\Actions\Action;
use Filament\Forms\Components\Section;
use Filament\Notifications\Notification;
use Filament\Resources\Pages\EditRecord;
Section::make('Rate limiting')
->schema([
// ...
])
->footerActions([
fn (string $operation): Action => Action::make('save')
->action(function (Section $component, EditRecord $livewire) {
$livewire->saveFormComponentOnly($component);
Notification::make()
->title('Rate limiting saved')
->body('The rate limiting settings have been saved successfully.')
->success()
->send();
})
->visible($operation === 'edit'),
])
```
The `$operation` helper is available, to ensure that the action is only visible when the form is being edited.
## Halting the saving process
At any time, you may call `$this->halt()` from inside a lifecycle hook or mutation method, which will halt the entire saving process:
@@ -9,6 +9,8 @@ use Filament\Actions\ForceDeleteAction;
use Filament\Actions\ReplicateAction;
use Filament\Actions\RestoreAction;
use Filament\Actions\ViewAction;
use Filament\Forms\ComponentContainer;
use Filament\Forms\Components\Component;
use Filament\Forms\Form;
use Filament\Infolists\Infolist;
use Filament\Notifications\Notification;
@@ -172,6 +174,47 @@ class EditRecord extends Page
}
}
public function saveFormComponentOnly(Component $component): void
{
$this->authorizeAccess();
try {
$this->beginDatabaseTransaction();
$this->callHook('beforeValidate');
$data = ComponentContainer::make($component->getLivewire())
->schema([$component])
->model($component->getRecord())
->statePath($this->getFormStatePath())
->getState();
$this->callHook('afterValidate');
$data = $this->mutateFormDataBeforeSave($data);
$this->callHook('beforeSave');
$this->handleRecordUpdate($this->getRecord(), $data);
$this->callHook('afterSave');
$this->commitDatabaseTransaction();
} catch (Halt $exception) {
$exception->shouldRollbackDatabaseTransaction() ?
$this->rollBackDatabaseTransaction() :
$this->commitDatabaseTransaction();
return;
} catch (Throwable $exception) {
$this->rollBackDatabaseTransaction();
throw $exception;
}
$this->rememberData();
}
protected function getSavedNotification(): ?Notification
{
$title = $this->getSavedNotificationTitle();