feat: Actions system — scheduled mutations on external services
Full-stack implementation of provider-scoped Actions with extensible executor architecture. First action type: Immich auto_organize (sort assets into albums by person, CLIP search, date range, favorites). Core: - ActionTypeDefinition registry + ActionExecutor ABC with execute/validate/dry-run - ImmichActionExecutor with multi-album support and client-side filtering - ImmichClient write methods: add/remove assets, create album, paginated search Server: - Action, ActionRule, ActionExecution DB models - Full CRUD API + manual execute + dry-run + execution history endpoints - APScheduler integration (interval + cron) for automated execution - Action type discovery API + provider people endpoint Frontend: - Actions page with CRUD, execute/dry-run buttons, inline rule editor - RuleEditor: person/album MultiEntitySelect pickers, criteria config - ExecutionHistory: expandable per-rule result details - MultiEntitySelect reusable component (searchable multi-pick palette) - Notification tracker album picker migrated to MultiEntitySelect - Fixed MdiIcon race condition (icons missing after cache-clearing reload)
This commit is contained in:
@@ -33,7 +33,9 @@
|
||||
"targetDiscord": "Discord",
|
||||
"targetSlack": "Slack",
|
||||
"targetNtfy": "ntfy",
|
||||
"targetMatrix": "Matrix"
|
||||
"targetMatrix": "Matrix",
|
||||
"automation": "Automation",
|
||||
"actions": "Actions"
|
||||
},
|
||||
"auth": {
|
||||
"signIn": "Sign in",
|
||||
@@ -138,6 +140,7 @@
|
||||
"server": "Provider",
|
||||
"selectServer": "Select provider...",
|
||||
"albums": "Albums",
|
||||
"selectAlbums": "Select albums...",
|
||||
"eventTypes": "Event Types",
|
||||
"notificationTargets": "Notification Targets",
|
||||
"scanInterval": "Scan Interval (seconds)",
|
||||
@@ -828,5 +831,59 @@
|
||||
"navigate": "navigate",
|
||||
"open": "open",
|
||||
"close": "close"
|
||||
},
|
||||
"actions": {
|
||||
"title": "Actions",
|
||||
"description": "Scheduled mutations on external services",
|
||||
"addAction": "Add Action",
|
||||
"noActions": "No actions configured yet.",
|
||||
"provider": "Provider",
|
||||
"selectProvider": "Select provider...",
|
||||
"actionType": "Action Type",
|
||||
"name": "Name",
|
||||
"schedule": "Schedule",
|
||||
"interval": "Interval",
|
||||
"seconds": "seconds",
|
||||
"cronHint": "Standard cron expression (e.g. 0 3 * * * for daily at 3 AM)",
|
||||
"enabled": "Enabled",
|
||||
"rules": "rules",
|
||||
"addRule": "Add Rule",
|
||||
"ruleName": "Rule Name",
|
||||
"ruleNamePlaceholder": "e.g. Alice → Family Album",
|
||||
"unnamedRule": "Unnamed rule",
|
||||
"noRules": "No rules yet. Add a rule to define what this action does.",
|
||||
"on": "ON",
|
||||
"off": "OFF",
|
||||
"criteria": "Criteria",
|
||||
"persons": "Persons",
|
||||
"addPerson": "Add person...",
|
||||
"searchQuery": "Smart Search Query",
|
||||
"searchQueryPlaceholder": "e.g. sunset, beach, birthday...",
|
||||
"assetType": "Asset type",
|
||||
"dateFrom": "From date",
|
||||
"dateTo": "To date",
|
||||
"favoritesOnly": "Favorites only",
|
||||
"targetAlbum": "Target Album",
|
||||
"selectAlbum": "Album",
|
||||
"selectAlbumPlaceholder": "— Select album —",
|
||||
"albumId": "Album ID",
|
||||
"createAlbumIfMissing": "Create album if it doesn't exist",
|
||||
"newAlbumName": "New album name",
|
||||
"execute": "Execute",
|
||||
"dryRun": "Dry Run",
|
||||
"history": "History",
|
||||
"affected": "affected",
|
||||
"executeResult": "Action executed: {affected} items affected",
|
||||
"dryRunResult": "Dry run: {affected} items would be affected",
|
||||
"saved": "Action saved",
|
||||
"deleted": "Action deleted",
|
||||
"ruleSaved": "Rule saved",
|
||||
"ruleDeleted": "Rule deleted",
|
||||
"confirmDelete": "Are you sure you want to delete this action? All rules and execution history will be lost.",
|
||||
"loadError": "Failed to load actions",
|
||||
"noExecutions": "No executions yet.",
|
||||
"triggerManual": "manual",
|
||||
"triggerDryRun": "dry-run",
|
||||
"triggerScheduled": "scheduled"
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user