Sandboxing Gemini CLI and Playwright MCP
2025-12-12Since the hype around claude code and others has subsided a bit, I figured its time to give one of these tools a try and gemini-cli being free, I decided to use that for a bit.
Installation is merely an npm install or npx call away. Once gemini is launched, use /auth
and login with your personal google account - easy.
Things went well and I had it extend an existing little app of mine but soon enough I realized it could only fix compile errors but not layout or styling issues or runtime errors. So, we need a way to give gemini-cli a browser and eyes and it seems playwright is the go-to tool for that.
Playwright also is just an npm install or npx call away from running but since starting to dabble
with gemini and now, just before wanting to install playwright,
a little thing with some mildly popular npm packages happended
and once again refreshed my weariness regarding installing random npm packages
(and potentially running equally random postinstall scripts) - stuff like this really
puts a damper on the joy of developing software.
Since I’ve been running gemini with --sandbox anyway, I decided, I wanted playwright
to run in isolation too. Being new to all this MCP stuff, unless I missed something,
it took quite a bit of experimentation to get this all working the way I want it to.
Playwright Docker
When initially running playwright in docker using it via gemini I got weird errors,
that it had no permissions to access my $HOME directory - why would it want to do
that and how does this dockerized playwright know about my username anyways? I couldn’t
figure out why and how it knew about my home directory but --user root would at least
‘fix’ the permissions issue. Now, when taking a screenshot, it would unfortunately be saved
inside the docker container, in the same path as from where i started gemini, in a
subdirectory named .playwright-mcp. To solve that, I did a binding mount of
the project directory onto the same location inside the docker container. That would allow
playwright to run isolated yet on the outside everything would still look like it ran
directly and was able to access the .playwright-mcp directory directly.
run playwright
|
|
get ip of the playwright container
|
|
gemini config
The IP address below is the IP of the playwright container. Ideally, this IP would be read from a command and automatically update the gemini config.
|
|
Gemini Sandbox
Now, I run gemini --sandbox, which means I’m still running whatever random code
is included in google’s gemini distribution, which then eventually runs a docker
container for its actions - at least that’s my current understanding on how this works.
Improving the setup
Now manually managing IPs and ports and making sure the container is running and still has the correct IP written in the config gets old pretty quick, so i ended up throwing all of the above into a docker-compose with a few companion scripts that keep the gemini version up to date.
https://github.com/stackmagic/gemini-docker
So far it works and there’s probably still tons to improve. Also, docker isn’t really a security boundary so it’s not perfect protection anyway, but better than nothing.