Icoryx
Icoryx

Reputation: 96

Loop through array to assign dynamic variable with results from 'find'

I'm trying to assign the results of find to a dynamic variable using the entries of an array both as the variable name and search string.

databases=(ABC DEF GHI JKL)
for i in "${databases[@]}"
do
    schema_$i=$(find '/hana/shared/backup_service/backup_shr/Schema' -type d -iname ${i} -mtime 0)
done

The result should be 0 to 4 variables that look something like this (depending on how many folders were found):

schema_ABC=/hana/shared/backup_service/backup_shr/Schema/ABC

However when I try this I get 'No such file or directory' as an error.

./find_schema.sh: line 4: schema_ABC=/hana/shared/backup_service/backup_shr/Schema/ABC: No such file or directory
./find_schema.sh: line 4: schema_DEF=/hana/shared/backup_service/backup_shr/Schema/DEF: No such file or directory
./find_schema.sh: line 4: schema_GHI=: command not found
./find_schema.sh: line 4: schema_JKL=/hana/shared/backup_service/backup_shr/Schema/JKL: No such file or directory

The folder structure looks like this:

Server:/hana/shared/backup_service/backup_shr/Schema # ll
total 0
drwxr-xr-x 2 root root 0 Sep 29  2020 Test
drwxr-xr-x 2 root root 0 Jan 24 21:15 ABC
drwxr-xr-x 2 root root 0 Jan 24 21:30 DEF
drwxr-xr-x 2 root root 0 Jan 12 22:00 GHI
drwxr-xr-x 2 root root 0 Jan 24 21:45 JKL

I believe that I'm not declaring that variable correctly but I can't make out what's wrong.

Upvotes: 1

Views: 90

Answers (2)

William Pursell
William Pursell

Reputation: 212514

Consider:

schema_$i=$(cmd)

When bash parses that line, it first checks for variable assignments. Since $ is not a valid character in a variable name, it does not see any variable assignments. Then it expands the string schema_$i to the string schema_ABC (or whatever the current value of $i is). Then it executes cmd to get some output, and then it attempts to execute the command schema_ABC=foo, but fails to find a command that matches that name. Intuitively, you are trying to make bash evaluate the string schema_ABC=foo, in which case you would need to tell it to do so explicitly with eval "schema_$i=$(find ...)". But you really don't want to go down that rabbit hole.

Instead, you could use an associative array and do something like:

declare -A schema
databases=(ABC DEF GHI JKL)
for i in "${databases[@]}"
do
    schema[$i]=$(...) 
done

Upvotes: 2

Fravadona
Fravadona

Reputation: 17208

One way to declare dynamic variable names is to use declare:

#!/bin/bash

databases=(ABC DEF GHI JKL)
for i in "${databases[@]}"
do
    declare "schema_$i"="$(find '/hana/shared/backup_service/backup_shr/Schema' -type d -iname "$i" -mtime 0)"
done

remark: The find command doesn't seem right; it will only list directories whose name is "$i"

Upvotes: 1

Related Questions