Dell EMC PowerStore Snapshots
Tasks for managing Dell EMC PowerStore volume snapshots: create, list, delete, and restore.
Manage Dell EMC storage systems from Kestra, starting with PowerStore: volumes, snapshots, replication, and array/alert monitoring.
Manage Dell EMC storage systems from Kestra. This first release covers Dell EMC PowerStore via its REST API (https://{host}/api/rest): volumes, snapshots, replication, and array/alert monitoring.
Every task authenticates with HTTP Basic Auth exchanged for a session: GET /api/rest/login_session is called with an Authorization: Basic header built from username/password; the appliance responds with a session cookie (Set-Cookie) and a DELL-EMC-TOKEN CSRF value. Every subsequent request sends the Authorization header and the session cookie; write requests (POST/PATCH/DELETE) additionally send DELL-EMC-TOKEN. If a write is rejected with HTTP 403 (a stale or missing CSRF token), the task re-authenticates once and retries before failing.
Required connection properties on every task:
| Property | Description |
|---|---|
host |
Management IP or hostname, optionally including a port (for example: powerstore.example.com or 192.168.1.20: 8443) |
username |
PowerStore local or LDAP account username |
password |
Password — store as a secret and reference via {{ secret('POWERSTORE_PASSWORD') }} |
Optional:
| Property | Description |
|---|---|
skipTlsVerification |
When true, accepts the appliance's TLS certificate without validation. Defaults to false. PowerStore management interfaces are commonly deployed with a self-signed certificate; intended for lab/non-production use only. |
Use plugin defaults to avoid repeating connection properties across tasks:
pluginDefaults:
- type: io.kestra.plugin.ee.dellemc.powerstore
values:
host: "{{ secret('POWERSTORE_HOST') }}"
username: "{{ secret('POWERSTORE_USERNAME') }}"
password: "{{ secret('POWERSTORE_PASSWORD') }}"
io.kestra.plugin.ee.dellemc.powerstore.volumes)| Task | API endpoint | Key properties |
|---|---|---|
List |
GET /api/rest/volume |
pageSize, fetchType |
Get |
GET /api/rest/volume/{id} |
volumeId |
Create |
POST /api/rest/volume |
name, sizeBytes, wait, waitTimeout |
Resize |
PATCH /api/rest/volume/{id} |
volumeId, sizeBytes, wait, waitTimeout |
Delete |
DELETE /api/rest/volume/{id} |
volumeId |
List supports a fetchType property (default STORE): STORE writes results to Kestra internal storage and returns a URI (recommended for large appliances), FETCH returns all rows inline, FETCH_ONE returns a single row, and NONE returns only the total count. Pagination uses PowerStore's limit/offset convention.
Create and Resize may be accepted asynchronously by the appliance (HTTP 202 with a job reference) and both expose the job ID via a jobId output while pending. When wait is true (default), the task polls GET /api/rest/job/{id} until completion, bounded by waitTimeout (default PT10M, capped at PT30M); a job failure fails the task with the job's error detail, while a client-side wait timeout returns successfully without confirmed completion instead of failing. Polling blocks the worker thread for the duration of the wait — size the worker pool accordingly if many job-aware tasks run concurrently. PowerStore exposes no job-cancellation endpoint: killing the execution stops the task from polling immediately, but the array-side operation itself keeps running to completion regardless.
io.kestra.plugin.ee.dellemc.powerstore.snapshots)| Task | API endpoint | Key properties |
|---|---|---|
Create |
POST /api/rest/volume/{volumeId}/snapshot |
volumeId, name |
List |
GET /api/rest/volume?type=eq.Snapshot&protection_data->>source_id=eq.{volumeId} |
volumeId, pageSize, fetchType |
Delete |
DELETE /api/rest/volume/{snapshotId} |
snapshotId |
Restore |
POST /api/rest/volume/{volumeId}/restore with body {"from_snap_id": "<snapshotId>"} |
volumeId, snapshotId, wait, waitTimeout |
A snapshot is a volume resource under the hood in PowerStore, so Delete reuses the same /volume/{id} endpoint as a regular volume, and List has no dedicated sub-collection — it filters /volume by type=Snapshot and protection_data.source_id. Restore targets the parent volume (volumeId), restoring it in place to the state captured by snapshotId; any data written after the snapshot was taken is lost, and the source snapshot itself is left untouched. Like volumes.Resize/replication.Failover, Restore may be accepted asynchronously (HTTP 202 + job) and exposes the job ID via a jobId output while pending; see wait/waitTimeout.
io.kestra.plugin.ee.dellemc.powerstore.replication)| Task | API endpoint | Key properties |
|---|---|---|
CreateRule |
POST /api/rest/replication_rule |
name, rpo (one of Five_Minutes, Fifteen_Minutes, Thirty_Minutes, One_Hour, Six_Hours, Twelve_Hours, One_Day, Zero), remoteSystemId |
GetSessionStatus |
GET /api/rest/replication_session/{id} |
sessionId |
Failover |
POST /api/rest/replication_session/{id}/failover |
sessionId, wait, waitTimeout |
Synchronize |
POST /api/rest/replication_session/{id}/sync |
sessionId, wait, waitTimeout |
Failover and Synchronize follow the same asynchronous job semantics as volumes.Create/Resize (see above): wait/waitTimeout control whether and how long the task polls for completion before returning.
io.kestra.plugin.ee.dellemc.powerstore.arrays)| Task | API endpoint | Key properties |
|---|---|---|
ListAlerts |
GET /api/rest/alert |
acknowledgedOnly (default false), pageSize, fetchType |
GetMetrics |
POST /api/rest/metrics/generate |
entityType, entityId, interval, fetchType |
ListAlerts returns every alert by default; set acknowledgedOnly: true to restrict results to already-acknowledged alerts. Both tasks support fetchType (default STORE, same semantics as the volumes/snapshots List tasks: STORE writes results to internal storage and returns a uri, FETCH returns all rows inline, FETCH_ONE returns one row, NONE returns only the count). The total output reflects the appliance-reported count regardless of fetchType, and an empty result set returns a 0 count rather than an error. GetMetrics's underlying /metrics/generate endpoint is not paginated, so the full data point set is always received and parsed in memory before fetchType is applied — STORE keeps data points out of the execution's output but does not reduce that parse-time memory peak.
OnAlertCreated (io.kestra.plugin.ee.dellemc.powerstore.arrays)Polls GET /api/rest/alert at interval, filtered server-side to unacknowledged alerts only (so poll cost scales with the open-alert backlog rather than the full alert history). Each poll emits at most one execution: when one or more new, unacknowledged alerts at or above minSeverity (NONE < INFO < MINOR < MAJOR < CRITICAL, default MINOR) are discovered, the output describes the newest one and lists every new alert from that poll cycle in alerts, so a burst of several new alerts is never reduced to just the newest. An alert reporting a severity string outside this set is logged and treated as not meeting the threshold, rather than crashing the poll cycle.
Key properties: host, username, password, minSeverity, interval (default PT1M).
On the very first poll, all pre-existing matching alerts are recorded without triggering executions. If the appliance is unreachable, the trigger logs a warning and waits for the next cycle. Two alerts raised in the same millisecond are each fired exactly once thanks to an ID-based boundary tracked alongside the timestamp baseline.
Trigger outputs available as {{ trigger.alertId }}, {{ trigger.description }}, {{ trigger.severity }}, {{ trigger.raisedTimestamp }}, {{ trigger.newAlertCount }}, {{ trigger.alerts }} (the newest alert plus the full list of new alerts detected in the poll cycle).