ENV: GNU bash, 버전 4.2.46(2)-릴리스(x86_64-redhat-linux-gnu)(이전)
- 각 루프에 동일한 시간이 걸리기를 원합니다.
- 순환은 결코 멈추지 않는다
- 이
api_call
기능이 정상적으로 실행되기까지 약 1초~5초 정도 소요됩니다. - 네트워크 문제로 인해 60초 제한 시간이 초과될 때까지 API 호출이 중단되는 경우는 거의 없습니다.
내 스크립트 A
TIMEFORMAT=%R
while true; do
time=$(date +'%F %T')
api_result=$( { time api_call; } 2>api_runtime.txt )
api_runtime=$(cat api_runtime.txt)
echo "${time} ${api_result}"
sleep (( 10 - ${api_runtime} ))
done
나는 Scrit A가 어느 날 네트워크 속도가 느려지고 루프가 동기화되지 않을 때까지 작업을 수행할 것이라고 생각했습니다.
내 스크립트 B
TIMEFORMAT=%R
while true; do
time=$(date +'%F %T')
api_result=$( api_call & )
sleep 10
echo "${time} ${api_result:-No response}"
done
api_call
스크립트 B도 현재 작동하는 것 같지만 다음 루프가 10초 이상 걸릴 때 안전한지 확실하지 않습니다 .
어떻게 이를 달성할 수 있나요?
답변1
명령 대체 내에서 이를 사용하면 &
기본 스크립트와 동시에 백그라운드에서 명령이 실행되지 않고 명령 대체에서 다른 일만 발생합니다.
$ time str=$( (sleep 2; echo hello) & )
real 0m2.006s
user 0m0.000s
sys 0m0.003s
$ echo "$str"
hello
위 작업은 아래 작업과 마찬가지로 완료되기 전에 2초 동안 중단됩니다.
$ time str=$( echo hello & sleep 2; echo bye )
real 0m2.011s
user 0m0.000s
sys 0m0.006s
$ echo "$str"
hello
bye
sleep 10
이는 루프 본문의 실행 시간에 항상 10초를 추가할 필요가 없음을 의미합니다 . 왜냐하면 이전 행의 할당은 실행될 때까지 차단되고 api_call
종료 시 발생하기 때문입니다.
각 루프 반복에 60초가 걸리도록 하려면(언급한 제한 시간 길이):
while true; do
result=$( sleep 60 & api_call )
done
api_call
이렇게 하면 반환 시간이 그보다 짧 더라도 할당에 60초가 소요됩니다 .
또는,
while true; do
result=$( sleep 10 & timeout 10s api_call )
done
api_call
...TERM 신호가 명시적으로 전송되는 것보다 느린 경우 10초가 걸립니다.
오랫동안 실행되는 스크립트라면 점진적으로 표류할 것으로 예상할 수 있습니다. 한 가지 가능한 해결책은 cron 작업을 사용하여 주기적으로 일정을 변경하는 것입니다(실행 중인 스크립트를 종료하고 다시 실행).