Terraform's remote-exec provisioner fails immediately if any command in a script exists with a non-zero exit code. This makes building polling loops a bit more involved than it normally is. So, here is an example loop that checks if a URL can be reached:
while true; do curl -k https://puppet:8140/puppet-ca/v1 && break || sleep 3 done
When the URL is unreachable, the "||" will ensure that "sleep" gets run, which returns 0. If the URL is reachable, curl itself will return 0 and "&&" ensures that we break out of the loop.