March 7, 2017 • 1 minute read
Using reserved ngrok subdomains in Laravel Valet
I ran into an interesting issue the other day while working on a Laravel project that handles inbound email using Amazon SES and SNS. Basically, I needed to be able to send a webhook from SNS to my application whenever an email was received in SES. As you may have experienced in the past, webhooks and local development environments don't exactly play nicely together - the webhook is expecting a public URL and your local machine is typically not going to be responding to requests over the Internet.
A great solution to this problem is to use ngrok. Luckily, Laravel Valet includes ngrok out of the box, and using it is a cinch:
$ valet share
This will route requests from a subdomain such as
ddcb9385.ngrok.io to the local copy of your application while ngrok is running, giving you a public URL for testing your webhooks. This is great, but every time you run ngrok you'll get a different subdomain, so you'll need to update the services that call your webhook if you want them to continue to work.
Luckily, ngrok offers a premium feature for just $5/month called reserved domains. This allows you to reserve a specific subdomain within a selected region such as
yourproject.us.ngrok.io. You can then tell ngrok to use this subdomain using the parameters
-subdomain=yourproject -region=us. Brilliant.
Except when you try to pass those flags through to Valet, you'll get a whole bunch of Failed to connect to 127.0.0.1 port 4040: Connection refused errors. If you scroll up, you'll see a message:
Tunnel session failed: Only paid plans may bind custom subdomains. Failed to bind the custom subdomain 'yourproject' for an unauthenticated client. Sign up at: https://ngrok.com/signup
Makes sense that you'd need to authenticate to use your custom subdomain. You can do this with the authtoken that's shown on your ngrok Dashboard when you login at ngrok.com. Unfortunately Valet doesn't have a command to pass through to ngrok to do this for you. Thankfully, we can do it manually, and you only need to do it once per machine:
$ ~/.composer/vendor/laravel/valet/bin/ngrok authtoken <YOUR_AUTHTOKEN>
This will output a message Authtoken saved to configuration file, and now you should be able to use your reserved domain with the command (replace
us with the appropriate values):
$ valet share -subdomain=yourproject -region=us
This is also really useful for projects that use Stripe billing, making it easy to accept incoming webhooks in your local environment.