When you make a call to Keystone to get a token, you also get back the service catalog. While many of my scripts have used the $OS_AUTH_URL to make follow on calls, if the calls are administrative in nature, you should use the URL in service catalog.
This makes use of curl fetch the token and jq to parse the output.
This call will fetch a token and ignore it, but instead pull the identity admin URL out of the Token.
curl -s -d @token-request.json -H "Content-type: application/json" $OS_AUTH_URL/auth/tokens | jq '.token | .catalog [] | select(.type == "identity") | .endpoints[] | select(.interface == "admin") | .url '
"http://192.0.2.1:35357/v2.0"
Say you want to talk to Nova? That would be the compute API on the public endpoint:
curl -s -d @token-request.json -H "Content-type: application/json" $OS_AUTH_URL/auth/tokens | jq '.token | .catalog [] | select(.type == "compute") | .endpoints[] | select(.interface == "public") | .url '
"https://192.0.2.2:13774/v2.1"