Connecting to a Memorystore Redis from your local machine
Published August 15, 2026
A Memorystore instance has no public address. It exists only inside a VPC, and the only way to connect from a local machine is through a VM that lives on that network. An IAP tunnel alone is not enough: it can only target a port on the VM itself, never a third host. The real path to a Memorystore Redis takes two hops, in a single command.
Why is there no public address?
It is not an oversight. Google only builds authenticated public gateways, like the Cloud SQL proxy or the Cloud Run one, in front of protocols that can carry real authentication. Redis is not one of them: its AUTH is a plain, optional password, so Google chose network isolation as the only security. The instance answers machines on its authorized network, and nothing else reaches it.
Hopping through a VM on that network is therefore not a workaround: it is the method Google intends for a workstation. The Memorystore documentation, read on 17 August 2026, documents exactly this port forwarding through a VM of the authorized network.
What can the IAP tunnel do, and where does it stop?
IAP is Google's door for reaching a VM that has no public address: gcloud compute start-iap-tunnel opens a local port that lands on a port of the VM. Its limit is sharp: it can only target a port of the VM itself, never a third host on the network. A Redis lives at another address of the VPC, so the IAP tunnel alone stops one hop short.
The answer is not to drop IAP but to compose it with an ssh -L: IAP carries the SSH session to the VM, and the VM carries the second hop, from its network to the private address of the Redis.
The two-hop command, piece by piece
You need the private address of the instance first. The listing gives it in the host field, along with the authorized network, authorizedNetwork, which will matter below; --region=- is the API's wildcard, every region at once:
gcloud redis instances list --region=- --format=json
Then the full command, worth keeping exactly as is:
gcloud compute ssh <jump-vm> --zone <zone> --project <project> \
--tunnel-through-iap -- -N -L 127.0.0.1:6379:<redis-ip>:6379
gcloud compute ssh opens an SSH session to the VM and handles identity for you: no key to create, none to install. --tunnel-through-iap routes that session through IAP, and that is the first hop: no public address needed anywhere, on the VM or elsewhere. Everything after -- goes to the ssh client: -N opens no shell, and -L 127.0.0.1:6379:<redis-ip>:6379 asks the VM for the second hop, from its network to the private address of the Redis. While the command runs, your Redis client talks to 127.0.0.1:6379 as if the instance listened on your machine.
The three errors it produces, and what they mean
| The error | Where it comes from | The move |
|---|---|---|
| The command fails before the local port opens | IAP refuses the first hop: the IAP-secured Tunnel User role, roles/iap.tunnelResourceAccessor, is missing, or the project firewall does not let IAP's range in, 35.235.240.0/20 | Both are fixed on the project side: the IAP documentation, read on 17 August 2026, gives the exact firewall rule |
channel 2: open failed: connect failed: Connection refused | The first hop is open; the second one failed: wrong address, or a VM that is not on the instance's authorized network | Compare the <redis-ip> in the command with the host field of the listing, and the VM's network with authorizedNetwork |
bind: Address already in use | Local port 6379 is already taken: a Redis installed locally, or a forgotten earlier tunnel | Change the left-hand side of the -L, 127.0.0.1:16379 for instance, and point your client there |
The second row is the misleading one: the message comes from the SSH server, not from your machine, and the article devoted to it explains how to read it. The third one has its own article too, because a forgotten tunnel still holding its port is the most ordinary failure of the family.
Kestro does this double hop as a single toggle: it lists your Redis instances, guesses the jump VM inside the authorized network, and assembles exactly this command, the way it already assembles the Cloud SQL proxy one. And the command above is enough if you would rather not add a tool: kept in an alias, it is the same path.
What remains
The tunnel lives as long as the command does: close the terminal or let the machine sleep, and the path is gone, sometimes with nothing to show for it. A project with no VM at all offers no jump host; creating one for this purpose is an infrastructure decision, not a troubleshooting trick, and it is not covered here. If the instance enforces AUTH or in-transit encryption, the network door spares you neither the password nor the TLS setup: both have their own sections in the documentation cited above. Memcached, finally, shares the same topology; the same path applies, with a different port.