diff --git a/async.zsh b/async.zsh index 1257029..8cd828e 100644 --- a/async.zsh +++ b/async.zsh @@ -36,7 +36,7 @@ _async_job() { read -r -k 1 -p tok || exit 1 # Return output ( ). - print -r -n - ${(q)1} $ret ${(q)stdout} $duration + print -r -n - $'\0'${(q)1} $ret ${(q)stdout} $duration } 2> >(stderr=$(cat) && print -r -n - " "${(q)stderr}$'\0') # Unlock mutex by inserting a token. @@ -245,13 +245,15 @@ async_process_results() { if (( $#items == 5 )); then items+=($has_next) $callback "${(@)items}" # Send all parsed items to the callback. + (( num_processed++ )) + elif [[ -z $items ]]; then + # Empty items occur between results due to double-null ($'\0\0') + # caused by commands being both pre and suffixed with null. else # In case of corrupt data, invoke callback with *async* as job # name, non-zero exit status and an error message on stderr. $callback "async" 1 "" 0 "$0:$LINENO: error: bad format, got ${#items} items (${(q)items})" $has_next fi - - (( num_processed++ )) done done diff --git a/async_test.zsh b/async_test.zsh index 0791fc7..ba55c58 100644 --- a/async_test.zsh +++ b/async_test.zsh @@ -7,8 +7,8 @@ test__async_job_print_hi() { local line local -a out line=$(_async_job print hi) - # Remove trailing null, parse, unquote and interpret as array. - line=$line[1,$#line-1] + # Remove leading/trailing null, parse, unquote and interpret as array. + line=$line[2,$#line-1] out=("${(@Q)${(z)line}}") coproc exit @@ -396,8 +396,10 @@ test_async_flush_jobs() { # TODO: Confirm that they no longer exist in the process tree. local output output="${(Q)$(ASYNC_DEBUG=1 async_flush_jobs test)}" - [[ $output = *'print_four 0 4'* ]] || { - t_error "want discarded output 'print_four 0 4' when ASYNC_DEBUG=1, got ${(Vq-)output}" + # NOTE(mafredri): First 'p' in print_four is lost when null-prefixing + # _async_job output. + [[ $output = *'rint_four 0 4'* ]] || { + t_error "want discarded output 'rint_four 0 4' when ASYNC_DEBUG=1, got ${(Vq-)output}" } # Check that the killed job did not produce output.