# Delete and Restore

Projects and dataset versions deleted through the Python SDK are moved to the workspace **Trash** and retained for 30 days before being permanently cleaned up. Within the retention window you can restore them back to the workspace.

Any in-flight training jobs for a project or version are cancelled automatically when it is moved to Trash, so you don't continue spending credits.

## Delete a Project

```python
import roboflow

rf = roboflow.Roboflow(api_key="YOUR_API_KEY")
project = rf.workspace().project("my-detector")

project.delete()
```

The project is immediately hidden from the workspace project list and appears in the Trash view under Settings → Trash.

## Restore a Project

If you still have a reference to the `Project` object, call `restore()` on it:

```python
project.restore()
```

The SDK looks up the project in the workspace Trash by its slug and restores it. `RuntimeError` is raised if the project isn't currently in Trash.

## Delete a Version

Move a single dataset version to Trash. Any in-flight training on the version is cancelled.

```python
import roboflow

rf = roboflow.Roboflow(api_key="YOUR_API_KEY")
project = rf.workspace().project("my-detector")
version = project.version(3)

version.delete()
```

## Restore a Version

```python
version.restore()
```

The parent project must still be active (not itself in Trash) to restore a version. Restore the project first if necessary.

## List Items in Trash

Use `Workspace.trash()` to see what's currently in the workspace Trash:

```python
import roboflow

rf = roboflow.Roboflow(api_key="YOUR_API_KEY")
ws = rf.workspace()

trash = ws.trash()
for item in trash["items"]:
    print(item["type"], item["name"], "cleanup:", item["scheduledCleanupAt"])
```

`trash["sections"]` groups the same items by `projects`, `versions`, and `workflows` for convenience.

## Restore by ID

If you don't already have a `Project` or `Version` handle (for example, you're restoring something that was deleted in a previous session), use `Workspace.restore_from_trash()` with the id returned by `trash()`:

```python
trash = ws.trash()
project_in_trash = trash["sections"]["projects"][0]

ws.restore_from_trash("project", project_in_trash["id"])
```

For versions, pass the parent project id:

```python
version_in_trash = trash["sections"]["versions"][0]
ws.restore_from_trash(
    "version",
    version_in_trash["id"],
    parent_id=version_in_trash["parentId"],
)
```

## Workflows

The SDK doesn't currently expose a `Workflow` object, but you can soft-delete a workflow via the low-level `rfapi` helper and restore it with `Workspace.restore_from_trash("workflow", ...)`:

```python
from roboflow.adapters import rfapi

# Soft-delete — moves the workflow to Trash for 30 days.
rfapi.delete_workflow(api_key, ws.url, "slow-webhooks")

# Restore — look up the workflow's id in Trash first.
trash = ws.trash()
wf = next(w for w in trash["sections"]["workflows"] if w["url"] == "slow-webhooks")
ws.restore_from_trash("workflow", wf["id"])
```

## Permanent Deletion

Permanent deletion is intentionally not available from the SDK — the actions to empty Trash and to immediately delete a single Trash item destroy data irrecoverably, and we don't want a stray script to be able to trigger them. These actions are available only through the Trash view in the Roboflow web app, which has an explicit confirmation dialog.

Items left in Trash are cleaned up automatically after the 30-day retention window, so you rarely need to act on them manually.


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.roboflow.com/developer/python-sdk/delete-and-restore.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
