Bash: How to retrieve a variable value inside a background while loop
This is due to the &
creating a new subshell for the first while loop.
I'm pretty certain you'll need to use some kind of IPC to solve this. Using a pipe or a named pipe to implement a producer/consumer setup would be reasonable.
A rough example:
#!/bin/bashmyvar=AAAwhile true;do sleep 3 myvar_piped=BBB echo $myvar_piped # this goes to the pipe. sleep 1done | # this connects the two loops.while true;do # if we consumed something (timeout=1) print it, else print our own variable. if read -t 1 myvar_piped # then echo "${myvar_piped}" else echo "${myvar}" fi done
Outputs:
AAAAAAAAABBBAAAAAAAAAAAABBB
Substantially, there is nothing you can do to read the variable directly in the parent shell.
The first loop is run in a sub-shell because of the &
; the sub-shell's memory is completely independent of the main shell's memory, and there's no way (short of doing ghastly things like running the debugger on the sub-shell) to access the child's memory from the parent shell.
If you can modify the sub-shell process to write its variable's value every second, then the parent might be able to detect that. Alternatively, if the sub-shell writes the variable to a file with a known name every time it changes the variable, then you can read the file as often as you want in the parent:
#!/bin/bashtmp=$(mktemp)trap "rm -f $tmp; exit 1" 0 1 2 3 13 15myvar=AAAecho $myvar > $tmpwhile true;do sleep 3 myvar=BBB echo $myvar > $tmp sleep 3 myvar=CCC echo $myvar > $tmpdone &while cat $tmpdo sleep 1donerm -f $tmptrap 0
The trappery ensures the temporary file is removed under most circumstances (signals HUP, INT, QUIT, PIPE and TERM).