# How do I bulk delete completed stories

**URL:** <https://community.taiga.io/t/how-do-i-bulk-delete-completed-stories/1388>\
**Category:** Troubleshooting\
**Created:** [June 20, 2023, 11:58am UTC](https://community.taiga.io/t/how-do-i-bulk-delete-completed-stories/1388 "2023-06-20T11:58:00Z")\
**Posts on this page:** 4\
**Page:** 1

<div class="post-metadata">

**Author:** ![Ayman\_El\_Nigoumi](https://dub1.discourse-cdn.com/flex017/user_avatar/community.taiga.io/ayman_el_nigoumi/32/1169_2.png) [@Ayman\_El\_Nigoumi](https://community.taiga.io/u/Ayman_El_Nigoumi)\
**Post date:** [June 20, 2023, 11:58am UTC](https://community.taiga.io/t/how-do-i-bulk-delete-completed-stories/1388/1 "2023-06-20T11:58:00Z")

</div>

How do I bulk delete completed stories I have like 900 ☹ and deleting them one by one is a pain.  
Support replied that this is possible via API … Any help on how to do that?

---

<div class="post-metadata">

**Author:** ![Pablohn26](https://dub1.discourse-cdn.com/flex017/user_avatar/community.taiga.io/pablohn26/32/927_2.png) [@Pablohn26](https://community.taiga.io/u/Pablohn26)\
**Post date:** [June 20, 2023, 2:35pm UTC](https://community.taiga.io/t/how-do-i-bulk-delete-completed-stories/1388/2 "2023-06-20T14:35:35Z")

</div>

which is the reason why you want to delete them? Usually it is better to archive them than to delete and losing information  
 ![imagen](https://europe1.discourse-cdn.com/flex017/uploads/taiga/original/2X/c/cc5252c115362d3b15b56bee319ea185b95a33b5.png)

Regarding the API, [here is the documentation](https://docs.taiga.io/). You should authenticate and perform [user stories deletion](https://docs.taiga.io/api.html#user-stories-delete).

Here is a snippet that you can start with (it is not tested, be careful you know what you are doing):

```auto
#!/bin/bash

# Set the Taiga API URL
API_URL="http://localhost:8000/api/v1/userstories/"

# Set the Taiga API token
AUTH_TOKEN="YOUR_AUTH_TOKEN_HERE"

# Check if the file path is provided as an argument
if [$# -ne 1]; then
  echo "Please provide the file path containing user story IDs."
  exit 1
fi

# Read the file line by line
while IFS= read -r story_id; do
  # Delete the user story using cURL
  curl -X DELETE \
    -H "Content-Type: application/json" \
    -H "Authorization: Bearer $AUTH_TOKEN" \
    -s "$API_URL$story_id"

  echo "Deleted user story with ID: $story_id"
done < "$1"

```

---

<div class="post-metadata">

**Author:** ![Ayman\_El\_Nigoumi](https://dub1.discourse-cdn.com/flex017/user_avatar/community.taiga.io/ayman_el_nigoumi/32/1169_2.png) [@Ayman\_El\_Nigoumi](https://community.taiga.io/u/Ayman_El_Nigoumi)\
**Post date:** [June 20, 2023, 2:48pm UTC](https://community.taiga.io/t/how-do-i-bulk-delete-completed-stories/1388/4 "2023-06-20T14:48:39Z")

</div>

Thank you for your reply, I will be running out of space soon, that’s why I have to delete it. regarding the script, I’m really new at this I’m not sure how to run or use this script ☹ any help?

---

<div class="post-metadata">

**Author:** ![Pablohn26](https://dub1.discourse-cdn.com/flex017/user_avatar/community.taiga.io/pablohn26/32/927_2.png) [@Pablohn26](https://community.taiga.io/u/Pablohn26)\
**Post date:** [June 20, 2023, 8:30pm UTC](https://community.taiga.io/t/how-do-i-bulk-delete-completed-stories/1388/5 "2023-06-20T20:30:28Z")

</div>

To run API calls you can do it using bash (already installed in Linux and Mac, [available in Windows following these instructions](https://www.laptopmag.com/articles/use-bash-shell-windows-10)).

- **IMPORTANT** perform a [database backup](https://docs.taiga.io/backup-and-restore.html) before running the commands.

## Authentication and ids

You can use [the following snippet](https://docs.taiga.io/api.html#_authentication) to get your auth\_token. To do so, save the following content to a file named `get_token.sh`, then provide it execution permissions with `sudo chmod +x get_token.sh`, and the run it with `bash ./get_token.sh`. **If you are using self hosted taiga, change in each script `API_URL` by your taiga instance endpoint.**

### get\_token.sh

```auto
#!/bin/bash

# Set the Taiga API URL
API_URL="https://api.taiga.io/api/v1"

# Request username and password for connecting to Taiga
read -p "Username or email: " USERNAME
read -r -s -p "Password: " PASSWORD

DATA=$(jq --null-input \
        --arg username "$USERNAME" \
        --arg password "$PASSWORD" \
        '{ type: "normal", username: $username, password: $password }')

# Get AUTH_TOKEN
USER_AUTH_DETAIL=$( curl -X POST \
  -H "Content-Type: application/json" \
  -d "$DATA" \
  $API_URL/auth 2>/dev/null )

AUTH_TOKEN=$( echo ${USER_AUTH_DETAIL} | jq -r '.auth_token' )

# Exit if AUTH_TOKEN is not available
if [-z ${AUTH_TOKEN}]; then
    echo "Error: Incorrect username and/or password supplied"
    exit 1
else
    echo "auth_token is ${AUTH_TOKEN}"
fi

```

You will see something like this:

 ![imagen](https://europe1.discourse-cdn.com/flex017/uploads/taiga/original/2X/7/7d42af8bd5797a5af0e2729f3415f95637c6cec6.png)

Remember to change `api.taiga.io` by your URL if you are using self hosted taiga.  
Copy and save in a secure place the `auth_token`, you will need it.

### get\_project\_id.sh

```auto
#!/bin/bash

# Set the Taiga API URL
API_URL="https://api.taiga.io/api/v1"

read -r -s -p "Introduce auth_token: " AUTH_TOKEN
echo ""
read -p "Introduce project slug: " name

curl -X GET \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer $AUTH_TOKEN" \
  -s "$API_URL/projects/by_slug?slug=$name" | jq -r '.id'

```

Once you get the `auth_token`, you have to get the `project_id` of the project that contains the user stories you want to delete. Same steps again, copy the content to a file named `get_project_id.sh`, then provide it execution permissions with `sudo chmod +x get_project_id.sh`, and the run it with `bash get_project_id.sh`. Copy the `project_id` (`819462` in the example) a save it in a safe place.

 ![imagen](https://europe1.discourse-cdn.com/flex017/uploads/taiga/original/2X/4/48f6d544e11d1905df5cbf7ebecf1dadee5104ed.png)

# Reviewing what are you going to delete and perform bulk deletion

Once you have the `auth_token` and `project_id`, you have to get all the user stories that are closed in that project using `review_user_stories_closed.sh`, then with `get_user_stories_closed.sh` you will get a file named `bulk_delete.txt` with the ids that are going to be deleted and finally you will perform the deletion with `bulk_delete.sh`. Same steps: copy the content, provide execution permission and run.

### review\_user\_stories\_closed.sh

```auto
#!/bin/bash

# Set the Taiga API URL
API_URL="https://api.taiga.io/api/v1"

read -r -s -p "Introduce auth_token: " AUTH_TOKEN
echo ""
read -p "Introduce project id: " project_id

curl -X GET \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer $AUTH_TOKEN" \
  -s "$API_URL/userstories?project=$project_id&is_closed=true" | jq '.[] | {id, subject}'

```

 ![imagen](https://europe1.discourse-cdn.com/flex017/uploads/taiga/original/2X/1/1f74529edc2363ea50facc2818ce63bca8b16588.png)

Using this script you will be able to know the id and the subject of the user stories you are going to delete. Use this as reference to know the ids of each one (you may want to skip deletion of several issues).

### get\_user\_stories\_closed.sh

```auto
#!/bin/bash

# Set the Taiga API URL
API_URL="https://api.taiga.io/api/v1"

read -r -s -p "Introduce auth_token: " AUTH_TOKEN
echo ""
read -p "Introduce project id: " project_id

response=$(curl -X GET \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer $AUTH_TOKEN" \
  -s "$API_URL/userstories?project=$project_id&is_closed=true")
 
echo "$response" | jq -r '.[] | .id' > ./bulk_delete.txt

echo "bulk_delete.txt file generated"

```

 ![imagen](https://europe1.discourse-cdn.com/flex017/uploads/taiga/original/2X/6/6f39efbaca3eb59b33a93413d08e560f1057a8c6.png)

When you run properly this script, you will get a file named `bulk_delete.txt` that contains the ids of the closed issues that are going to be deleted. **EDIT this file if you do not want to delete all closed issues**. You must remove the ids of the user stories that you want to preserve (in the example I only want to bulk delete user story ids 4718043 and 4718709)

![Select user stories ids to delete](https://europe1.discourse-cdn.com/flex017/uploads/taiga/original/2X/5/5dc19097335c566b722f07237fd2cc1aab23ac2d.gif)

### bulk\_delete.sh

```auto
#!/bin/bash

# Set the Taiga API URL
API_URL="https://api.taiga.io/api/v1/userstories/"

read -r -s -p "Introduce auth_token: " AUTH_TOKEN
echo ""
read -p "Introduce project id: " project_id

# Read the file line by line
while IFS= read -r story_id; do
  # Delete the user story using cURL
  curl -X DELETE \
    -H "Content-Type: application/json" \
    -H "Authorization: Bearer $AUTH_TOKEN" \
    -s "$API_URL$story_id?project=$project_id"

  echo "Deleted user story with ID: $story_id"
done < "bulk_delete.txt"

```

 ![imagen](https://europe1.discourse-cdn.com/flex017/uploads/taiga/original/2X/0/01dbb70745b2e581de1d1525338a47854b27cae6.png)

So at this time, **you have performed a bulk deletion of closed user stories** that you have in `bulk_delete.txt` file. Check your taiga instance to review that.

## Summary

- You have to copy the content of the .sh scripts, give them permissions with `chmod` and then run them.
- The process is the following: use `get_token.sh` to get the `auth_token`, then use `get_project_id.sh` to get the id of the project that contains the user stories, then use `review_user_stories_closed.sh` to get a list of user stories and their subject, then use `get_project_id.sh` to get the `bulk_delete.txt` file that contains the ids of the user stories that are going to be bulk deleted, **edit that file if you want to preserve some closed issues** and finally perform the bulk deletion running `bulk_delete.sh`.
