Skip to content

Commit bebe1da

Browse files
authored
Looping over comma-separated values in Bash
1 parent 067ac0e commit bebe1da

File tree

1 file changed

+59
-0
lines changed

1 file changed

+59
-0
lines changed

bash/loop-over-csv.md

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
# Looping over comma-separated values in Bash
2+
3+
Given a file (or a process) that produces comma separated values, here's how to split those into separate variables and use them in a bash script.
4+
5+
The trick is to set the Bash `IFS` to a delimiter, then use `my_array=($my_string)` to split on that delimiter.
6+
7+
Create a text file called `data.txt` containing this:
8+
```
9+
first,1
10+
second,2
11+
```
12+
You can create that by doing:
13+
```bash
14+
echo 'first,1
15+
second,2' > /tmp/data.txt
16+
```
17+
To loop over that file and print each line:
18+
```bash
19+
for line in $(cat /tmp/data.txt);
20+
do
21+
echo $line
22+
done
23+
```
24+
To split each line into two separate variables in the loop, do this:
25+
```bash
26+
for line in $(cat /tmp/data.txt);
27+
do
28+
IFS=$','; split=($line); unset IFS;
29+
# $split is now a bash array
30+
echo "Column 1: ${split[0]}"
31+
echo "Column 2: ${split[1]}"
32+
done
33+
```
34+
Outputs:
35+
```
36+
Column 1: first
37+
Column 2: 1
38+
Column 1: second
39+
Column 2: 2
40+
```
41+
Here's a script I wrote using this technique for the TIL [Use labels on Cloud Run services for a billing breakdown](https://til.simonwillison.net/til/til/cloudrun_use-labels-for-billing-breakdown.md):
42+
```bash
43+
#!/bin/bash
44+
for line in $(
45+
gcloud run services list --platform=managed \
46+
--format="csv(SERVICE,REGION)" \
47+
--filter "NOT metadata.labels.service:*" \
48+
| tail -n +2)
49+
do
50+
IFS=$','; service_and_region=($line); unset IFS;
51+
service=${service_and_region[0]}
52+
region=${service_and_region[1]}
53+
echo "service: $service region: $region"
54+
gcloud run services update $service \
55+
--region=$region --platform=managed \
56+
--update-labels service=$service
57+
echo
58+
done
59+
```

0 commit comments

Comments
 (0)