跑發布好的版本
用 version 宣告的服務,會用它的名字跑發布好的映像,不用 build:箱子怎麼拉取與啟動、env 裡的額外變數,以及怎麼看進度與換版本。
宣告時帶 version 的服務,會用它的名字跑一顆已發布的 image,不用 build,也不用你自己 docker run:
sandbox_start { "name": "web 接退款改版的 billing", "goal": "讓 web 前端接已發布的退款版 billing;在瀏覽器裡下的退款被那個 billing 記下來就算完成", "environment": "dev", "services": [{ "name": "billing.acme.internal", "port": 8080, "version": "refund-a1b2c3d" }] }
sandbox_wire { "id": "<id>", "service": "billing.acme.internal", "port": 8080, "version": "refund-a1b2c3d" }
version是sandbox_versions列出的標籤或versionId。同一個標籤有好幾個服務都發布過時,挑服務名跟這個名字一樣、或跟它的第一段 DNS 標籤一樣的那個(billing.acme.internal就是billing);還分不出來就回 400,列出service/label → versionId,這時改給versionId。找不到的回 400no published version with label or id "…"; sandbox_versions lists them。- 開箱時 control 就解析版本並挑
targetPort:用port本身,除非它是 80、9095,或已經被箱子裡別的服務用了,那就從 20000 往上挑第一個沒用的。也可以自己給targetPort。sandbox_start立刻回;容器跑起來之後,箱子裡的程式與容器用name:port就連得到它。 - 箱子 ready 之後,control 用一個背景命令(note 是
start published <服務>@<標籤>)先docker pull,再docker run -d --restart unless-stopped --name psbx-svc-<名字> -p <targetPort>:<容器的 port> [--env-file /work/.sbx/env/<服務>.env] [-e NAME=value …] -e SBX_BOX_ID <image>,並最多等 120 秒到容器開始聽。<服務>是這個版本發布時登記的服務;箱子的環境有它的設定檔才會帶。除了env(下一項),其他什麼都不會帶進去。箱子有externalBaseUrl時,會先把這個名字切成box。 env(只能跟version一起)是給容器的額外環境變數,一組字串對字串,例如{ "SENTRY_ENVIRONMENT": "psbx", "WORKERS_ENABLED": "false" }。它們接在設定檔後面,同名的以env為準,而且原樣帶進去,引號與$(…)都只是字串。名字照 shell 變數的規則(字母、數字與_,不以數字開頭);不能設SBX_BOX_ID;最多 64 個、每個值 4 KB、合計 32 KB。值會出現在sandbox_status,所以不要放秘密。再 wire 一次這個版本,會用你這次給的env整組換掉。沒有version卻帶env會失敗:sandbox_start回services[<i>] (<name>): env goes with version, the published version to run; for your own process pass -e to docker run(400),sandbox_wire回同一句,只是前面沒有services[<i>] (<name>):。- 容器的 port:有給
containerPort就用它,否則用 image 唯一一個 EXPOSE 的 TCP port,都沒有就用port。image EXPOSE 了好幾個 TCP port 時要給containerPort,不然啟動會失敗:the image exposes several TCP ports (…); declare the service with containerPort。 sandbox_status→services[].run看結果:state(not_started、starting、running、exited、failed,問不到箱子時是unknown)、image、versionId、label、container、logPath(啟動命令的 log)與error(失敗時附那份 log 的最後幾行)。訊息有docker pull failed for <image>(registry 裡沒有那顆 image:pull 會說not found)、the container exited before it listened on port N (restarts: M)與the container did not start listening on port N within 120 s,後面接容器最後幾行 log。- 一個箱子只會起一次:boxd 重啟時容器照樣在跑,容器結束的話 Docker 會把它重新拉起來(
--restart unless-stopped)。 - 要把正在跑版本的名字換成另一個版本,用同樣的
service與port加上新的version呼叫sandbox_wire。在sandbox_start用version宣告的名字也可以,環境的位址也一樣:容器psbx-svc-<名字>會被換掉,run從starting重新開始,名字的targetPort不變。我們試的箱子上,換成一個容器會當掉的版本時run.state是failed,再換回來就回到running。 - 規則:同一個服務不能既是 link 又是版本(400
a link cannot also run a published version; use either fromBox or version);containerPort要跟version一起給;跑著的箱子上給version時一定要給port;沒有take-over功能的箱子裡,已經是 link 的名字不能跑版本(409);你送來的image與run一律不收。 - 每個箱子都已經登入帳號的 registry;凍結 10 小時以上的箱子解凍時會先換一次登入,所以凍很久之後照樣拉得到。
- 在有
take-over功能的箱子上,sandbox_wire帶version也會接走開箱時沒宣告的環境位址,以及 link(接手 link 或環境位址)。比較舊的箱子不會:版本起來了、run.state也是running,但名字照樣連到連接器,容器只在127.0.0.1:<targetPort>上有回應;在那種箱子上,這種名字要在sandbox_start宣告。
所有工具與主題都列在工具參考。