SSD Nodes Learn Hosting plans →
Mga Gabay Matt ConnorNi Matt Connor · Na-update 2026-10-06

Paano patakbuhin ang Gemini CLI sa headless VPS

Patakbuhin ang Gemini CLI sa headless VPS gamit ang kasalukuyang Node, no-sudo global install, API key auth na walang browser, at tmux para sa SSH drops.

Ano ang ginagawa mo

Isang always-on Gemini CLI sa server na pagmamay-ari mo, naa-access sa pamamagitan ng SSH, at nagpapatakbo ng mahahabang agent task na nagpapatuloy kahit isara mo ang laptop. Tatlong command ang kailangan para sa installation. Ang mas matrabaho ay ang mga bahaging umaasa sa desktop: gustong magbukas ng browser ng CLI ng Google para mag-log in ka, pero walang browser ang server mo. Kaya karamihan ng gabay na ito ay tungkol sa headless na proseso, isang kasalukuyang bersyon ng Node na hindi ibibigay ng distro, isang global npm install na hindi nangangailangan ng root, browserless authentication gamit ang API key na hindi mo inilalagay sa shell history, at tmux upang hindi maputol ang tumatakbong task kapag na-disconnect ang SSH session.

Ang Gemini CLI ay isang open-source (Apache-2.0) na Node program (@google/gemini-cli) na kumokonekta sa mga Gemini model ng Google at maaaring magbasa at magsulat ng mga file, magpatakbo ng shell command, at gumamit ng mga tool sa working directory. Sa isang VPS, isa itong maliit at laging available na agent na maaari mong hayaang magpatuloy sa pagtatrabaho. Dahil dito, mas mahalaga kung saang account ito tumatakbo at kung anong credentials ang nakaimbak sa server kaysa sa alinmang indibidwal na setting dito.

Mga kailangan at mahahalagang limitasyon

  • Isang bagong Ubuntu 24.04 KVM VPS na may root o sudo. Gumagana ang anumang KVM plan; magaan lang ang CLI mismo at ilang daang MB ng RAM ang ginagamit nito kapag idle.
  • Node.js 20 o mas bago. Ito ang tanging mahigpit na minimum na bersyon, at mas luma rito ang distro package. Tingnan ang susunod na section.
  • Outbound HTTPS (port 443) papunta sa Google APIs. Walang inbound port na kailangan; client ito, hindi server, kaya hindi mo kailangang magbukas ng firewall hole para rito.
  • Paraan ng authentication na hindi nangangailangan ng browser sa server: alinman sa Gemini API key mula sa Google AI Studio, o SSH tunnel papunta sa browser sa sarili mong machine. Ang API-key path ang angkop para sa mga script at unattended run.
  • Docker o Podman, kung gusto mo lamang ang --sandbox isolation. Optional ito at tatalakayin malapit sa dulo.

Ang limitasyong madalas hindi napapansin: ang user-friendly na gemini first-run login flow ay ginawa para sa desktop. Sinusubukan nitong magbukas ng browser at, sa headless na machine, maaaring mabigo o magbigay ng link na hindi gumagana. Piliin ang auth path bago ka magsimula.

Node: masyadong luma ang distro package

Ang Ubuntu 24.04 ay nagre-release ng Node 18.19.1 sa sarili nitong repositories, kasama ang npm 9.2.0. Idinedeklara ng Gemini CLI ang engines: { node: ">=20" } sa package.json, at bilang default, hindi tuluyang pinipigilan ng npm ang hindi tugmang bersyon. Nag-i-install pa rin ito at nagpapakita ng warning na tinutukoy ang agwat:

npm WARN EBADENGINE Unsupported engine {
npm WARN EBADENGINE   package: '@google/gemini-cli@0.50.0',
npm WARN EBADENGINE   required: { node: '>=20' },
npm WARN EBADENGINE   current: { node: 'v18.19.1', npm: '9.2.0' }
npm WARN EBADENGINE }

Kapag binalewala mo ang warning na iyon, tatakbo ang CLI sa runtime na hindi suportado. Magkakaroon ito ng maling behavior o magka-crash sa sandaling gumamit ito ng Node 20+ API na inaasahan nitong umiiral. Umabot din sa end-of-life ang Node 18 noong April 2025, kaya dead end pa rin ito. Mag-install ng kasalukuyang LTS bago i-install ang CLI. Ang dalawang maayos na opsyon ay ang NodeSource, isang system-wide na may lagdang apt repo, o ang nvm, isang per-user na version manager. Pumili ng isa.

NodeSource, kung gusto mong available ang Node sa lahat ng user sa server:

sudo apt-get update
sudo apt-get install -y ca-certificates curl gnupg
curl -fsSL https://deb.nodesource.com/setup_24.x | sudo -E bash -
sudo apt-get install -y nodejs
node --version

node --version dapat mag-print ng v20.x o mas mataas; ang v24.x ang kasalukuyang active LTS. Tingnan ang NodeSource page para sa kasalukuyang setup script; ang setup_24.x sa URL ang kailangang itaas kapag may bagong LTS na inilabas.

nvm, kung mas gusto mong panatilihin ang Node sa home directory ng isang user at huwag itong patakbuhin kailanman gamit ang sudo:

curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.40.1/install.sh | bash
source ~/.bashrc
nvm install --lts
node --version

Ang v0.40.1 sa URL na iyon ang kasalukuyang bersyon noong isinulat ito. Tingnan ang README ng nvm para sa pinakabagong release at palitan ang bersyon bago ito patakbuhin. May malaking bentahe ang nvm para sa gawaing ito: ini-install nito ang Node at ang mga global package nito sa ilalim ng ~/.nvm. Kaya hindi kailanman nangyayari ang problema sa permission ng global install na inilalarawan sa susunod na seksyon. Kung gagamitin mo ang nvm, maaari mong laktawan ang hakbang para sa npm prefix.

I-install ang CLI nang walang sudo npm -g

Nakakatuksong gamitin ang command na sudo npm install -g @google/gemini-cli. Huwag. Kapag root-owned ang global prefix, magkakaroon ng permission errors sa bawat susunod na install at magkakaroon ng root-owned files sa npm cache mo na magdudulot ng problema pagkalipas ng ilang buwan. Patakbuhin ang plain (walang sudo na) npm install -g laban sa system Node at lalabas naman ang ganitong error:

npm error code EACCES
npm error syscall mkdir
npm error path /usr/lib/node_modules/@google
npm error errno -13
npm error Error: EACCES: permission denied, mkdir '/usr/lib/node_modules/@google'

Sinusubukan ng npm na magsulat sa /usr/lib, na hindi maaaring sulatan ng user mo. Hindi sudo ang solusyon. Ituro ang global prefix ng npm sa home directory mo para mapunta ang global installs sa lokasyong pagmamay-ari mo:

mkdir -p ~/.npm-global
npm config set prefix ~/.npm-global
echo 'export PATH="$HOME/.npm-global/bin:$PATH"' >> ~/.bashrc
source ~/.bashrc
npm install -g @google/gemini-cli
gemini --version

Sinasadya ang ~/.bashrc, hindi ang ~/.profile: ang tmux, na paglalagyan mo ng CLI pagkalipas ng dalawang section, ay nagsisimula ng non-login shell na nagbabasa ng ~/.bashrc at nilalaktawan ang ~/.profile. Kaya kapag nasa maling file ang linyang PATH, mananatiling invisible ang gemini sa mismong lugar kung saan mo ito kailangan. Ang pag-print ng numero ng bersyon ng gemini --version ang buong test. Kung gemini: command not found ang makita mo, hindi na-apply ang PATH export mo; tingnan ang failure modes. Sa nvm, laktawan nang buo ang mga prefix line: awtomatiko na nitong ini-install ang globals sa ilalim ng home directory mo.

Kung nagpatakbo ka ng sudo npm kanina at nakikita mo na ngayon ang Your cache folder contains root-owned files, ayusin ito nang isang beses gamit ang sudo chown -R $(id -u):$(id -g) ~/.npm.

Ang problema sa headless auth at kung paano ito malalampasan

Patakbuhin nang interactive ang gemini sa unang pagkakataon. Bibigyan ka nito ng opsyong mag-log in gamit ang iyong Google account. Sa desktop, magbubukas ito ng browser tab. Sa headless VPS, walang browser, kaya maaaring mag-print ang flow ng localhost URL na kailangan mong buksan, o tuluyang mabigo at magpakita ng ganito:

Failed to open browser. Please visit the following URL to authorize:
https://accounts.google.com/o/oauth2/v2/auth?...&redirect_uri=http://localhost:PORT

Ang problema ay ang redirect_uri=http://localhost:PORT. Kahit buksan mo ang URL sa laptop mo at aprubahan ang login, magre-redirect si Google sa http://localhost:PORT, na localhost sa server. Wala itong port na maaabot ng laptop mo. Hindi makukumpleto ang login.

May dalawang tamang paraan para malampasan ito.

Ang unang paraan ay gumamit ng API key. Ito ang angkop na default para sa server. Gumawa ng key sa Google AI Studio (aistudio.google.com) at ipasa ito sa CLI bilang environment variable. Binabasa nito ang GEMINI_API_KEY at tuluyang nilalaktawan ang browser flow. Ngayon, tungkol sa pag-iwas na mapunta ito sa history at sa mga file na mababasa ng lahat: huwag i-type ang export GEMINI_API_KEY=AIza... sa prompt. Mapupunta ito nang malinaw na text sa ~/.bash_history. Huwag din itong ilagay sa file na mababasa ng ibang user. Isulat ito sa file na may mode 600 at sini-source ng shell sa pagsisimula:

umask 077
printf 'export GEMINI_API_KEY=%s\n' 'AIzaSyYOUR_KEY_HERE' > ~/.gemini_env
chmod 600 ~/.gemini_env
echo '[ -f ~/.gemini_env ] && . ~/.gemini_env' >> ~/.bashrc
source ~/.bashrc

Ibig sabihin ng chmod 600, ikaw lamang na user ang makakabasa sa file. Kumpirmahing napunta ang key sa environment gamit ang printenv GEMINI_API_KEY. Kung walang ma-print, babalik ang CLI sa browser flow at mabibigo. Nagbabasa rin ito ng .env file sa ~/.gemini/ kung mas gusto mo ang layout na iyon. Pareho pa rin ang tuntunin, kaya chmod 600 ~/.gemini/.env.

Ang ikalawang paraan ay panatilihin ang login gamit ang personal Google account at ang free tier nito sa pamamagitan ng pag-tunnel ng OAuth callback pabalik sa laptop mo. Ang problema, random ang port na bina-bind ng loopback server ng CLI sa bawat run. Walang stable na port na puwedeng i-forward maliban kung itakda mo muna ito gamit ang OAUTH_CALLBACK_PORT environment variable. Pagkatapos, i-forward ang eksaktong port na iyon:

# from your laptop, forward the callback port into the SSH session:
ssh -L 8085:localhost:8085 user@your-server
# then, on the server, pin the callback to the same port and start the CLI:
export OAUTH_CALLBACK_PORT=8085
gemini

Hindi makapagbukas ng browser ang CLI, kaya ipi-print nito ang auth URL. Buksan ito sa browser ng laptop mo at aprubahan ang login. Kapag nag-redirect si Google sa http://localhost:8085/..., dadalhin ng SSH forward ang request sa loopback server sa VPS at makukumpleto ang login. Kapag hindi mo itinakda ang port, bagong random port ang gagamitin sa bawat run. Walang ssh -L na na-set up nang maaga ang makakasalo rito. Gumagana ito, pero kailangan mong nasa harap ng browser. Kaya hindi ito angkop para sa mga script. Para sa anumang prosesong iiwan mong tumatakbo, gamitin ang API key.

Para sa Vertex AI o Google Cloud project sa halip na AI Studio, itakda ang GOOGLE_API_KEY kasama ng GOOGLE_GENAI_USE_VERTEXAI=true, o ang GOOGLE_CLOUD_PROJECT para sa Code Assist licence. Panatilihin ang parehong disiplina sa environment variable at gamitin ang parehong mode-600 file.

Patakbuhin ito sa loob ng tmux upang hindi ito mapatay ng naputol na SSH session

Ang prosesong gemini na direktang inilunsad mula sa iyong SSH shell ay child process ng shell na iyon. Kapag nawala ang koneksyon dahil isinara ang laptop, naputol ang Wi-Fi, o nag-time out dahil walang aktibidad, winawasak ng sshd ang pseudo-terminal, tumatanggap ang shell ng SIGHUP, at ipinapasa naman nito ang hang-up sa CLI. Kasama nitong namamatay ang task na sampung minuto nang nag-e-edit ng mga file, at kapag muli kang kumonekta, wala nang prosesong mare-recover.

Inaayos ito ng tmux sa pamamagitan ng pagmamay-ari sa shell sa halip na sshd ang magmay-ari rito. Kapareho ito ng pattern sa pagpapatakbo ng AI coding agent sa remote VPS sa loob ng tmux, at pareho rin ang paggana nito rito:

sudo apt install -y tmux
tmux new -A -s gemini
# inside the session:
gemini
# detach with Ctrl-b then d — the task keeps running
# reconnect later from any machine:
tmux attach -t gemini

Ina-attach ng tmux new -A -s gemini ang session na pinangalanang gemini kung mayroon na ito, at ginagawa ito kung wala pa, kaya ito ang isang command na dapat patakbuhin kaagad pagkatapos ng bawat login. Ang shell sa loob nito ay pagmamay-ari ng detached tmux server, hindi ng iyong SSH session, kaya patuloy na gumagana ang CLI kapag naputol ang koneksyon. Kumonekta muli, mag-attach, at babalik ka sa parehong scrollback. Kung magpapatakbo ka ng maraming agent session sa isang server, tig-isa sa bawat tmux session, wala silang paraan upang mag-usap sa isa’t isa rito, hindi tulad sa Claude Code, kung saan maaaring magpasa ng text ang isang session sa isa pang session sa parehong VPS, kaya panatilihing independent ang bawat Gemini job o pag-ugnayin ang mga ito gamit ang mga file sa disk.

Para sa non-interactive at scripted na mga run, may headless mode ang Gemini CLI: nagpi-print ng sagot ang gemini -p "summarise the failing tests in this repo" at nag-e-exit, habang nagbibigay ang --output-format json ng machine-readable output na maaaring i-pipe sa ibang command. Ang headless mode na may API key ang eksaktong kailangan sa loob ng tmux session na nagpapatakbo ng matagal na batch job, o kapag inilulunsad mula sa cron entry, ngunit may isang mahalagang kondisyon: walang sine-source na login file ang cron job, kaya maglagay ang crontab line ng sarili nitong GEMINI_API_KEY (o ipa-source sa command ang ~/.gemini_env), kung hindi ay babalik ang CLI sa browser flow at mabibigo.

Sandboxing at mga permission sa server na nagpapatakbo rin ng production

Ang agent na may shell access ay may shell access. Maaaring magpatakbo ng commands ang Gemini CLI. Bilang default, nagtatanong ito bago ang bawat mapanganib na command. Ngunit ginagamit ng mga tao ang --yolo (awtomatikong pag-apruba sa bawat tool call). Maaari nitong burahin ang mga file, mag-push sa git, o kumonekta sa internal services gamit ang buong authority ng user account na pinapatakbo nito. Kung nagpapatakbo rin ng production ang server, tunay ang blast radius nito. Hindi ito hypothetical.

Tatlong control, ayon sa laki ng pakinabang ng mga ito:

  • Patakbuhin ito gamit ang dedicated, unprivileged user. Huwag itong patakbuhin bilang root o bilang miyembro ng sudo. Gumawa ng agent user na may sariling home directory. I-install doon ang Node at ang CLI. Sa ganitong paraan, mananatili sa account na iyon ang mga epekto ng maling interpretasyon sa isang instruction. Ito ang pinakamahalagang desisyon.
  • Huwag ilagay sa server ang production credentials. Huwag maglagay ng prod ~/.aws/credentials, huwag kumopya ng .env mula sa production, at huwag gumamit ng database password na may write access sa anumang mahalagang resource. Bigyan ito ng staging credential o read-only credential.
  • Gamitin ang built-in sandbox. Kapag naka-install ang Docker o Podman, pinapatakbo ng gemini --sandbox (o GEMINI_SANDBOX=docker) ang tool calls ng agent sa loob ng container na hiwalay sa filesystem at network ng host. Hindi nito pinapalitan ang unprivileged user. Ngunit isa itong matibay na second layer kapag ginagamit din ng parehong VPS ang production workloads.

Kung pinapatakbo mo ang Gemini CLI katabi ng iba pang self-hosted tooling, halimbawa ay isang MCP server na naglalantad ng mga tool sa agent sa parehong VPS, ituring ang bawat idinadagdag na capability bilang karagdagang surface na maaabot ng agent. Limitahan ang mga token na ibinibigay dito sa eksaktong isang gawain.

Quota, gastos, at kung aling auth path ang pinili mo

Tinutukoy ng auth path kung paano ka sisingilin. Ang personal na Google account (ang OAuth path) ay gumagamit ng libreng Gemini Code Assist tier, na may aktuwal na limit sa bawat minuto at bawat araw; kapag lumampas ka rito, magbabalik ng rate-limit error ang mga request hanggang sa mag-reset ang window. Ang API key mula sa AI Studio ay maaaring nasa free tier o may billing, depende sa project. Kapag billed ang key, tataas ang mga limit at sisingilin ka batay sa token. Ang auth gamit ang Vertex at Cloud project ay sinisingil sa pamamagitan ng Google Cloud.

Dalawang praktikal na paalala. Mabilis makakakonsumo ng quota ang unattended agent na paulit-ulit na tumatakbo, kaya i-monitor ito sa unang ilang paggamit bago mo ito pagkatiwalaang patakbuhin bilang cron job. At kung privacy o unmetered inference ang dahilan mo sa paggamit ng server-side model, sa halip na hosted model ng Google, ibang tool iyon: ang pagse-self-host ng open LLM gamit ang Ollama sa isang VPS ay nagpapanatili ng weights at prompts sa sarili mong server, kapalit ng pagpapatakbo ng mas maliit na model kaysa sa Gemini.

Panatilihin itong updated

Madalas mag-release ng bagong bersyon ang Gemini CLI. Dahil ini-install mo ito sa prefix na pagmamay-ari ng user, hindi kailanman kailangan ng sudo para sa mga update:

npm install -g @google/gemini-cli@latest
gemini --version

May mga release channel: stable ang @latest, weekly preview ang @preview, at bleeding edge ang @nightly. I-pin sa @latest ang anumang kritikal na ginagamit mo. Sa nvm, nasa ilalim ng aktibong Node version ang mga global package. Kaya pagkatapos ng nvm use para lumipat ng Node, maaaring kailangan mong i-reinstall ang CLI. Basahin ang release notes sa halip na habulin ang bawat patch.

Mga failure mode, kasama ang eksaktong string

npm WARN EBADENGINE Unsupported engine ... required: { node: '>=20' }, at nagka-crash ang CLI habang tumatakbo. Luma na ang Node; ang bersyon ng distro ay 18.19.1, na lampas na rin sa end-of-life. Mag-install ng Node 20+ mula sa NodeSource o nvm, kumpirmahin gamit ang node --version, at kung marami kang naka-install na Node, tiyaking ang which node ay tumuturo sa bago at hindi sa /usr/bin/node.

npm error code EACCES / permission denied, mkdir '/usr/lib/node_modules/...'. Global install ito sa prefix na pagmamay-ari ng root. Huwag itong patakbuhin gamit ang sudo, itakda ang npm config set prefix ~/.npm-global, idagdag ang ~/.npm-global/bin sa PATH, at i-install muli bilang normal na user. Kung may naiwang cache file na pagmamay-ari ng root mula sa naunang sudo npm (Your cache folder contains root-owned files), patakbuhin ang sudo chown -R $(id -u):$(id -g) ~/.npm.

Failed to open browser, nagha-hang ang login, o may redirect_uri=http://localhost:PORT na hindi mo maabot. Nangangailangan ang OAuth flow ng browser na wala sa server, at ang localhost callback nito ay tumuturo sa server, hindi sa laptop mo. Gamitin ang API-key path (GEMINI_API_KEY), o i-pin ang OAUTH_CALLBACK_PORT, i-forward ito sa SSH gamit ang ssh -L, at buksan ang URL nang lokal.

Nawala ang process nang maputol ang SSH. Direktang pinatakbo mo ang gemini mula sa SSH shell, kaya naging child ito ng shell na iyon at namatay kasama ng pty nang ma-disconnect. Wala nang kailangang i-recover. Simulan ang bawat session gamit ang tmux new -A -s gemini at patakbuhin ang CLI sa loob nito.

Patuloy na nagfa-fail ang auth kahit nakatakda ang key, bumabalik ang CLI sa auth picker nito, o nagbabalik ang isang request ng API key not valid na may HTTP 400. Wala ang key sa environment na nakikita ng CLI. Kumpirmahin gamit ang printenv GEMINI_API_KEY; kung walang output, hindi na-source ang ~/.gemini_env mo. Tingnan kung nasa ~/.bashrc ang line; binabasa ito ng interactive shells, kasama ang tmux, ngunit hindi ng cron at iba pang non-interactive shells. Ang sobrang space o quote sa loob ng key value ay nagdudulot din ng API key not valid.

429 / RESOURCE_EXHAUSTED / mensahe tungkol sa rate limit. Naabot mo ang quota para sa tier na ginagamit ng iyong auth. Hintaying mag-reset ang window, pabagalin ang agent, o lumipat sa billed API key. Patuloy na tatamaan nito ang agent na na-stuck sa retry loop; ihinto ito at tingnan kung ano ang ginagawa nito.

FAQ

Paano ko ia-authenticate ang Gemini CLI sa isang headless server?

Gumamit ng API key, hindi ng browser login. Gumawa ng key sa Google AI Studio, ilagay ito sa file na may mode-600 na sini-source ng shell (export GEMINI_API_KEY=...), at ganap na lalaktawan ng CLI ang OAuth browser flow. Kung partikular mong gusto ang libreng tier para sa personal account, i-pin ang loopback port gamit ang OAUTH_CALLBACK_PORT=8085, i-forward ito pabalik sa iyong laptop gamit ang ssh -L 8085:localhost:8085 user@server, at buksan nang lokal ang naka-print na URL. Gayunman, kailangan mong nasa harap ng browser, kaya hindi ito angkop para sa mga script.

Bakit nangangailangan ng sudo ang npm global install, at paano ko ito maiiwasan?

Dahil ang default global prefix ng npm ay /usr/lib/node_modules at hindi ito maaaring sulatan ng iyong user, kaya mabibigo ang simpleng npm install -g gamit ang EACCES. Maling solusyon ang sudo npm -g dahil nag-iiwan ito ng mga file na pagmamay-ari ng root at nagdudulot ng problema sa mga susunod na install. Ang tamang solusyon ay ituro ang prefix sa iyong home (npm config set prefix ~/.npm-global) at idagdag ang bin nito sa PATH, o gumamit ng nvm, na awtomatikong nag-i-install ng mga global package sa iyong home.

Paano ko mapananatiling tumatakbo ang Gemini CLI pagkatapos kong mag-disconnect?

Patakbuhin ito sa loob ng tmux. Mamamatay ang prosesong sinimulan mula sa iyong SSH shell kapag naputol ang koneksyon dahil child ito ng shell na iyon. Pinapatakbo ng tmux ang shell sa ilalim ng detached server na nananatili kahit mag-disconnect ka. Gamitin ang tmux new -A -s gemini, patakbuhin ang gemini sa loob nito, mag-detach gamit ang Ctrl-b d, at muling mag-attach sa ibang pagkakataon gamit ang tmux attach -t gemini.

Ligtas bang patakbuhin ang Gemini CLI sa production box?

Ligtas lamang ito kung maingat ang configuration, dahil kayang gawin ng agent na may shell access ang anumang kaya ng user na siyang nagpapatakbo rito. Patakbuhin ito bilang dedicated unprivileged user na walang sudo, huwag maglagay ng production credentials sa machine, iwasan ang --yolo auto-approval, at gamitin ang --sandbox (Docker o Podman) upang ihiwalay ang mga tool call sa host. Mas mahalaga ang account na ginagamit nito kaysa sa anumang iisang flag na itinakda mo.

Kailangan ko bang magbukas ng anumang firewall port para sa Gemini CLI?

Hindi. Isa itong client na gumagawa ng outbound HTTPS calls sa mga API ng Google, kaya kailangan nito ang outbound port 443 ngunit walang inbound port. Kung gagamitin mo ang OAuth tunnel, ang naka-pin na callback port (halimbawa, 8085) ay nasa localhost at naaabot sa pamamagitan ng SSH forward, hindi sa pamamagitan ng bukas na inbound port. Panatilihing mahigpit ang mga inbound connection.

#gemini-cli#node#tmux#headless#ai#vps