Mechanics
Create a Subscription
You can create a subscription by submitting a full subscription request to the following endpoint:
POST https://api.planet.com/subscriptions/v1/<subscription_id>
A basic subscription must include a name
and source
block. Subscriptions also support select tools
and a delivery
block for specifying cloud storage and hosting. A subscription request will be rejected if the geometry specified in the geometry
attribute or the clip tool exceeds 1,500 vertices.
A subscription processes and delivers items as soon as all item filter criteria are met, and all requested asset types have been published and are available for delivery.
Subscriptions API supports various different data products with nuanced properties within the source
block. Data products that belong to the Planet scene catalogs (For example, PSScene, SkySatScene, TanagerScene, etc.) can be subscribed to using the catalog
source block, and all other data products Subscriptions API supports (For example, Planetary Variables, Analysis-Ready PlanetScope) can be subscribed to using the subscription source
block. These different source blocks are described in more detail in the subscription sources section.
Time series data is available via the results endpoint for all subscriptions after they are created. Planetary Variable and Analysis-Ready PlanetScope subscriptions can be created as results only subscriptions by omitting the delivery
parameter. A results only subscription will not deliver any data products to cloud storage. Catalog subscriptions cannot be created as results-only subscriptions.
Example: PSScene Subscription Request
This example creates a subscription that will deliver imagery to a Google Cloud Storage bucket.
- CURL
- Python SDK
- CLI
curl -X POST "https://api.planet.com/subscriptions/v1" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "Example PSScene Subscription",
"source": {
"type": "catalog",
"parameters": {
"item_types": ["PSScene"],
"asset_types": ["ortho_analytic_4b"],
"start_time": "2025-01-15T00:00:00.0Z",
"end_time": "2025-01-15T00:00:01.0Z",
"time_range_type": "acquired",
"geometry": {
"coordinates": [
[
[139.56481933, 35.42374884],
[140.10314941, 35.42374884],
[140.10314941, 35.77102915],
[139.56481933, 35.77102915],
[139.56481933, 35.42374884]
]
],
"type": "Polygon"
}
}
},
"delivery": {
"type": "google_cloud_storage",
"parameters": {
"bucket": $GCS_BUCKET,
"credentials": $GCS_CREDENTIALS
}
}
}'
from datetime import datetime
from planet import Planet
from planet.subscription_request import (
build_request,
catalog_source,
google_cloud_storage,
)
pl = Planet()
def create_psscene_subscription(gcs_bucket, gcs_credentials):
psscene_subscription = build_request(
name="Example PSScene Subscription",
source=catalog_source(
item_types=["PSScene"],
asset_types=["ortho_analytic_4b"],
start_time=datetime.fromisoformat("2025-01-15T00:00:00.0Z"),
end_time=datetime.fromisoformat("2025-01-15T00:00:01.0Z"),
time_range_type="acquired",
geometry={
"coordinates": [
[
[139.56481933, 35.42374884],
[140.10314941, 35.42374884],
[140.10314941, 35.77102915],
[139.56481933, 35.77102915],
[139.56481933, 35.42374884],
]
],
"type": "Polygon",
},
),
delivery=google_cloud_storage(
bucket=gcs_bucket,
credentials=gcs_credentials,
),
)
subscription = pl.subscriptions.create_subscription(psscene_subscription)
return subscription
geometry="{
\"coordinates\": [
[
[139.56481933, 35.42374884],
[140.10314941, 35.42374884],
[140.10314941, 35.77102915],
[139.56481933, 35.77102915],
[139.56481933, 35.42374884]
]
],
\"type\": \"Polygon\"
}"
delivery="{
\"type\": \"google_cloud_storage\",
\"parameters\": {
\"bucket\": \"${GCS_BUCKET}\",
\"credentials\": \"${GCS_CREDENTIALS}\"
}
}"
source=$(planet subscriptions request-catalog \
--item-types PSScene \
--asset-types ortho_analytic_4b \
--start-time 2025-01-15T00:00:00.0Z \
--end-time 2025-01-15T00:00:01.0Z \
--time-range-type acquired \
--geometry "$geometry"
)
planet subscriptions request \
--name "Example PSScene Subscription" \
--source "$source" \
--delivery "$delivery" \
| planet subscriptions create -
Example: Planetary Variable Subscription Request
Here is an example of a JSON payload for SWC-AMSR2-X_V5.0_1000
results only subscription over San Francisco using a Feature Reference ID. Note that this example omits the delivery
parameter.
- CURL
- Python SDK
- CLI
curl -X POST "https://api.planet.com/subscriptions/v1" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "Example Soil Moisture Subscription",
"source": {
"type": "soil_water_content",
"parameters": {
"id": "SWC-AMSR2-X_V5.0_1000",
"start_time": "2025-01-15T00:00:00.0Z",
"end_time": "2025-01-15T00:00:01.0Z",
"geometry": {
"content": "pl:features/my/feature_collection-2q26z0q/mX9dB1o",
"type": "ref"
}
}
}
}'
from datetime import datetime
from planet import Planet
from planet.subscription_request import build_request, planetary_variable_source
pl = Planet()
def create_swc_subscription():
swc_subscription = build_request(
name="Example Soil Moisture Subscription",
source=planetary_variable_source(
var_type="soil_water_content",
var_id="SWC-AMSR2-X_V5.0_1000",
start_time=datetime.fromisoformat("2025-01-15T00:00:00.0Z"),
end_time=datetime.fromisoformat("2025-01-15T00:00:01.0Z"),
geometry="pl:features/open/sandbox-zx0JO2n/mendoza-argentina-PAXyMXz",
),
)
subscription = pl.subscriptions.create_subscription(swc_subscription)
return subscription
source=$(planet subscriptions request-pv \
--var-type soil_water_content \
--var-id SWC-AMSR2-X_V5.0_1000 \
--start-time 2025-01-15T00:00:00.0Z \
--end-time 2025-01-15T00:00:01.0Z \
--geometry pl:features/my/feature_collection-2q26z0q/mX9dB1o
)
planet subscriptions request \
--name "Example Soil Moisture Subscription" \
--source "$source" \
| planet subscriptions create -
Example: Analysis-Ready PlanetScope Subscription Request
This example creates a subscription that will deliver Analysis-Ready PlanetScope imagery. Please note that Analysis-Ready PlanetScope does not support any tools at this time.
- CURL
- Python SDK
- CLI
curl -X POST "https://api.planet.com/subscriptions/v1" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "Example Analysis-Ready PlanetScope Subscription",
"source": {
"type": "analysis_ready_ps",
"parameters": {
"id": "PS_ARD_SR_DAILY",
"start_time": "2025-01-15T00:00:00.0Z",
"end_time": "2025-01-15T00:00:01.0Z",
"geometry": {
"coordinates": [
[
[-122.39334886, 37.79508572],
[-122.41963198, 37.79508572],
[-122.41963198, 37.77362268],
[-122.39334886, 37.77362268],
[-122.39334886, 37.79508572]
]
],
"type": "Polygon"
}
}
},
"hosting": {
"type": "sentinel_hub"
}
}'
from datetime import datetime
from planet import Planet
from planet.subscription_request import (
build_request,
planetary_variable_source,
sentinel_hub,
)
pl = Planet()
def create_arps_subscription():
arps_subscription = build_request(
name="Example Analysis-Ready PlanetScope Subscription",
source=planetary_variable_source(
var_type="analysis_ready_ps",
var_id="PS_ARD_SR_DAILY",
start_time=datetime.fromisoformat("2025-01-15T00:00:00.0Z"),
end_time=datetime.fromisoformat("2025-01-15T00:00:01.0Z"),
geometry={
"coordinates": [
[
[-122.39334886, 37.79508572],
[-122.41963198, 37.79508572],
[-122.41963198, 37.77362268],
[-122.39334886, 37.77362268],
[-122.39334886, 37.79508572],
]
],
"type": "Polygon",
},
),
hosting=sentinel_hub(None),
)
subscription = pl.subscriptions.create_subscription(arps_subscription)
return subscription
geometry="{
\"coordinates\": [
[
[-122.39334886, 37.79508572],
[-122.41963198, 37.79508572],
[-122.41963198, 37.77362268],
[-122.39334886, 37.77362268],
[-122.39334886, 37.79508572]
]
],
\"type\": \"Polygon\"
}"
source=$(planet subscriptions request-pv \
--var-type analysis_ready_ps \
--var-id PS_ARD_SR_DAILY \
--start-time 2025-01-15T00:00:00.0Z \
--end-time 2025-01-15T00:00:01.0Z \
--geometry "$geometry"
)
planet subscriptions request \
--name "Example Analysis-Ready PlanetScope Subscription" \
--source "$source" \
| planet subscriptions create -
Update a Subscription
You can update a subscription by submitting a full subscription request to the following endpoint:
PUT https://api.planet.com/subscriptions/v1/<subscription_id>
A subscription may be updated when it is in a pending
or running
state, with certain constraints:
source.start_time
: Cannot be updated if the start time is in the past.source.item_type
: Cannot be modified.notifications
: Cannot be modified.
All other elements may be updated as long as the subscription does not surpass the limit on expected items delivered daily:
name
: May be modified.source.start_time
: May be modified if the start time is in the future.source.end_time
: May be modified if the subscription has not expired.source.geometry
: May be modified only for thecatalog
source type.source.rrule
: May be modified. Not supported for Analysis-Ready PlanetScope.delivery
: May be modified.
Importantly, the update will only apply to future item publications and deliveries. No items will be redelivered. If you need to reorder archive items based on an updated filter or tool specifications, you can search for and order archive items with the Data API and Orders API.
Example: Update a Subscription
- CURL
- Python SDK
- CLI
curl -X PUT "https://api.planet.com/subscriptions/v1/${SUBSCRIPTION_ID}" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "Updated Subscription",
"source": {
"type": "catalog",
"parameters": {
"item_types": ["PSScene"],
"asset_types": ["ortho_analytic_4b"],
"start_time": "2025-01-15T00:00:00.0Z",
"end_time": "2025-01-15T00:00:01.0Z",
"time_range_type": "acquired",
"geometry": {
"coordinates": [
[
[139.56481933, 35.42374884],
[140.10314941, 35.42374884],
[140.10314941, 35.77102915],
[139.56481933, 35.77102915],
[139.56481933, 35.42374884]
]
],
"type": "Polygon"
}
}
},
"delivery": {
"type": "google_cloud_storage",
"parameters": {
"bucket": $GCS_BUCKET,
"credentials": $GCS_CREDENTIALS
}
}
}'
from planet import Planet
pl = Planet()
def update_subscription(subscription, gcs_bucket, gcs_credentials):
subscription_id = subscription.get("id")
source_params = subscription.get("source").get("parameters")
update = pl.subscriptions.update_subscription(
subscription_id,
{
"name": "Update Subscription",
"source": {
"type": subscription.get("source").get("type"),
"parameters": {
"item_types": source_params.get("item_types"),
"asset_types": source_params.get("asset_types"),
"start_time": source_params.get("start_time"),
"end_time": source_params.get("end_time"),
"time_range_type": source_params.get("time_range_type"),
"geometry": source_params.get("geometry"),
},
},
"delivery": {
"type": "google_cloud_storage",
"parameters": {
"bucket": gcs_bucket,
"credentials": gcs_credentials,
},
},
},
)
return update
geometry="{
\"coordinates\": [
[
[139.56481933, 35.42374884],
[140.10314941, 35.42374884],
[140.10314941, 35.77102915],
[139.56481933, 35.77102915],
[139.56481933, 35.42374884]
]
],
\"type\": \"Polygon\"
}"
delivery="{
\"type\": \"google_cloud_storage\",
\"parameters\": {
\"bucket\": \"${GCS_BUCKET}\",
\"credentials\": \"${GCS_CREDENTIALS}\"
}
}"
source=$(planet subscriptions request-catalog \
--item-types PSScene \
--asset-types ortho_analytic_4b \
--start-time 2025-01-15T00:00:00.0Z \
--end-time 2025-01-20T00:00:00.0Z \
--time-range-type acquired \
--geometry "$geometry"
)
planet subscriptions request \
--name "Update Subscription" \
--source "$source" \
--delivery "$delivery" \
| planet subscriptions update ${SUBSCRIPTION_ID} -
Patch a Subscription
You can patch specific subscription properties by submitting a PATCH
request:
PATCH https://api.planet.com/subscriptions/v1/<subscription_id>
Not all properties can be edited this way, but they are subject to fewer restrictions than PUT
requests. Importantly, the full subscription request body is not required and such requests are accepted regardless of a subscription state.
See the API reference for the full list of supported properties.
Example: Patch a Subscription
- CURL
- Python SDK
- CLI
curl -X PATCH "https://api.planet.com/subscriptions/v1/${SUBSCRIPTION_ID}" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "Patch Subscription"
}'
from planet import Planet
pl = Planet()
def patch_subscription(subscription, name):
patch = pl.subscriptions.patch_subscription(
subscription.get("id"),
{"name": name},
)
return patch
planet subscriptions patch ${SUBSCRIPTION_ID} "{\"name\": \"Patch Subscription\"}"
Cancel a Subscription
You can cancel a subscription with the following request:
POST https://api.planet.com/subscriptions/v1/<subscription_id>/cancel
After a subscription is canceled, no additional items will be delivered (except for any items in processing or delivery). A canceled subscription cannot be transitioned to running
state. canceled
subscriptions will continue to be returned in the GET
subscriptions response.
Example: Cancel a Subscription
- CURL
- Python SDK
- CLI
curl -X POST "https://api.planet.com/subscriptions/v1/${SUBSCRIPTION_ID}/cancel" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json"
from planet import Planet
pl = Planet()
def cancel_subscription(subscription_id):
cancel = pl.subscriptions.cancel_subscription(subscription_id)
return cancel
planet subscriptions cancel ${SUBSCRIPTION_ID}
Get a Subscription
You can get details on a single subscription with the following request:
GET https://api.planet.com/subscriptions/v1/<subscription_id>
The response will include the original request, pagination links, a results link, and system generated properties like status
, created
timestamp, and updated
timestamp.
Example: Get a Subscription
- CURL
- Python SDK
- CLI
curl -X GET "https://api.planet.com/subscriptions/v1/${SUBSCRIPTION_ID}" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json"
from planet import Planet
pl = Planet()
def get_subscription(subscription_id):
subscription = pl.subscriptions.get_subscription(subscription_id)
return subscription
planet subscriptions get ${SUBSCRIPTION_ID}
List Subscriptions
You can list all subscriptions with the following request:
GET https://api.planet.com/subscriptions/v1
- CURL
- Python SDK
- CLI
curl -X GET "https://api.planet.com/subscriptions/v1" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json"
from planet import Planet
pl = Planet()
def list_subscriptions():
subscriptions = pl.subscriptions.list_subscriptions()
for subscription in subscriptions:
yield subscription
planet subscriptions list
This access pattern supports query parameters for filtering:
status
source_type
user_id
Example: List Subscriptions By Status
- CURL
- Python SDK
- CLI
curl -X GET "https://api.planet.com/subscriptions/v1?status=running" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json"
from planet import Planet
pl = Planet()
def list_subscriptions_by_status(status):
subscriptions = pl.subscriptions.list_subscriptions(status=status)
for subscription in subscriptions:
yield subscription
planet subscriptions list --status running
Example: List Subscriptions By Source Type
- CURL
curl -X GET "https://api.planet.com/subscriptions/v1?source_type=catalog" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json"
Example: List Subscriptions By User ID
- CURL
curl -X GET "https://api.planet.com/subscriptions/v1?user_id=123" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json"
List Subscription Results
The response will include a paginated list of all of the subscription's results that were created within the last 30 days. A result for the catalog
source type subscription represents an attempt to process and deliver an item that matches your subscription criteria. Results for at least the past 30 days of deliveries will be returned. The response schema will include:
Property | Description |
---|---|
id | The unique ID of the subscription result. |
status | The delivery status of the result's item. Result status can be either created , queued , processing , success , or failed . See the section on subscription states and statuses for more details. |
properties | Time series data for the subscription. See Catalog properties and Planetary Variable/Analysis-Ready PlanetScope properties tables for details. |
created | The time the result was generated. For a catalog source type subscription, this will be when the subscription acknowledges the newly published item. |
updated | The time that the result was last updated. |
completed | The time the result reached an end status of success or failed . |
errors | Information on result failure, including a reason and array of details . |
output | The directories of the final output files. |
Catalog subscription results
Property | Description |
---|---|
item_id | The item_id of the result. |
item_types | The item_type of the result. |
Planetary Variable and Analysis-Ready PlanetScope results
Property | Description |
---|---|
item_id | The item_id of the result. |
local_solar_time | Time based on the position of the Sun in the sky when the asset was captured. |
source_id | The specific product ID for the subscription. |
statistics[].asset | The data product that the statistic is calculated from. |
statistics[].band | The specific range of wavelengths in the electromagnetic spectrum that the statistic is calculated from. |
statistics[].name | The name of the statistic: valid_percent (integer from 0 - 100), mean (floating point with two fractional digits). |
statistics[].type | The data type of the statistic, e.g. number . |
statistics[].value | The value of the statistic. |
You can filter subscriptions results by status
(For example, ?status=processing
) and by created
, updated
, or completed
timestamps, using STAC API timestamp and interval conventions:
- A datetime:
2020-09-01T00:00:00Z
- A closed interval:
2020-09-01T00:00:00Z/2020-09-30T23:59:59Z
- Open intervals:
2020-09-01T00:00:00Z/..
or../2020-09-01T00:00:00Z
As an organization administrator, you also have the ability to get subscription results for any subscription created in your organization by including the user_id=all
query parameter.
Example: List Subscription Results
- CURL
- Python SDK
- CLI
curl -X GET "https://api.planet.com/subscriptions/v1/${SUBSCRIPTION_ID}/results" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json"
from planet import Planet
pl = Planet()
def list_subscription_results(subscription_id):
results = pl.subscriptions.get_results(subscription_id)
for result in results:
yield result
planet subscriptions results ${SUBSCRIPTION_ID}
Get a Summary
You can get a summary of all the subscriptions you have created by status with the following request:
GET https://api.planet.com/subscriptions/v1/summary
The response will include a count of subscriptions by status.
Example: Get Summary
- CURL
- Python SDK
- CLI
curl -X GET "https://api.planet.com/subscriptions/v1/summary" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json"
from planet import Planet
pl = Planet()
def get_summary():
summary = pl.subscriptions.get_summary()
return summary
planet subscriptions summarize
If you are an organization administrator, you can get a summary of all subscriptions created in your organization by including the user_id=all
query parameter.
Example: Get Summary as Org Admin
- CURL
curl -X GET "https://api.planet.com/subscriptions/v1/summary?user_id=all" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json"
Get a Subscription Summary
You can get a summary of result statuses for a single subscription with the following request:
GET https://api.planet.com/subscriptions/v1/<subscription_id>/summary
The response will include a count of results by status, as well as the subscription status.
Example: Get Subscription Summary
- CURL
- Python SDK
- CLI
curl -X GET "https://api.planet.com/subscriptions/v1/${SUBSCRIPTION_ID}/summary" \
--include \
-H "Authorization: api-key $PL_API_KEY" \
-H "Content-Type: application/json"
from planet import Planet
pl = Planet()
def get_subscription_summary(subscription_id):
sub_summary = pl.subscriptions.get_subscription_summary(subscription_id)
return sub_summary
planet subscriptions summarize --subscription-id=${SUBSCRIPTION_ID}
Org admins may get summaries of any subscription within the organization. No extra parameters are required.
Links
Most Planet API responses contain a _links
object that contains a list of hyperlinks to itself and related data. You are encouraged to rely on these links rather than constructing the links yourself.
The most common _link
is _self
, which is a self reference. When an API response is paginated, _links
will contain _next
and _prev
references.
Pagination
The Planet API paginates responses to limit the results, making them easier to work with. The first GET request will yield the first page along with _links
representing the location of the _next
page. Following the _next
link will return another page of results. This process may be repeated until the _next
link is no longer returned, which indicates the last page of the results.
The following _links
are provided in the response to facilitate pagination:
_self
- The canonical location of the current page._first
- The initial page._next
- The page that logically follows the current page._prev
- The page that logically precedes the current page.