php小編子墨發(fā)現(xiàn),有一些開發(fā)者在使用Go語言編寫docker容器時遇到了一個問題,即無法為容器寫入有效的掛載路徑。這個問題可能導(dǎo)致在容器中進(jìn)行文件讀寫操作時出現(xiàn)錯誤或失敗。對于開發(fā)者來說,這無疑是一個令人沮喪的困擾。接下來,我們將探討這個問題的原因以及可能的解決方案,幫助開發(fā)者解決這個挑戰(zhàn)。
問題內(nèi)容
我正在嘗試啟動一個測試容器來測試我的數(shù)據(jù)庫。我正在使用測試容器。
這是我如何設(shè)置容器的一段代碼:
func createContainer(ctx context.Context) (testcontainers.Container, *pgxpool.Pool, string, error) { var env = map[string]string{ "POSTGRES_PASSWORD": DbPass, "POSTGRES_USER": DbUser, "POSTGRES_DB": DbName, } var port = "5432/tcp" // /Users/:/ path := `/c/Users/pizhlo21/Desktop/Folder/golang/TgBotReminder/internal/db/postgresql/migration:/usr/app` req := testcontainers.GenericContainerRequest{ ContainerRequest: testcontainers.ContainerRequest{ Image: "postgres:latest", ExposedPorts: []string{port}, Env: env, WaitingFor: wait.ForLog("database system is ready to accept connections"), VolumeMounts: map[string]string{"/docker-entrypoint-initdb.d": path}, SkipReaper: true, }, Started: true, } container, err := testcontainers.GenericContainer(ctx, req) if err != nil { return container, nil, "", fmt.Errorf("unable to start container: %v", err) } ...
登錄后復(fù)制
但我從 docker 收到錯誤: failed to setup testunable to start container: failed to create container: error response from daemon: create /docker-entrypoint-initdb.d: "/docker-entrypoint-initdb.d" 包括本地卷名稱的無效字符,僅允許“[a-za-z0-9][a-za-z0-9_.-]”。如果您打算傳遞主機(jī)目錄,請使用絕對路徑
。
有時此錯誤如下所示:無法設(shè)置測試無法啟動容器:無法創(chuàng)建容器:守護(hù)程序的錯誤響應(yīng):“卷”類型的安裝配置無效:安裝路徑無效:'“c” /desktop/folder/golang/tgbotreminder/internal/db/postgresql/migration/000001_init_schema.up"' 掛載路徑必須是絕對
我嘗試了許多不同的路徑,例如:
//c/用戶/...
c/用戶/...
/%cd%/桌面/...
$home/桌面/文件夾/...
但沒有任何幫助我。
如何正確執(zhí)行?
解決方法
tl;dr
替換
volumemounts: map[string]string{"/docker-entrypoint-initdb.d": path},
登錄后復(fù)制
與
bindmounts: map[string]string{"/docker-entrypoint-initdb.d": path},
登錄后復(fù)制
問題 1
“/docker-entrypoint-initdb.d”包含本地卷名稱的無效字符,僅允許“[a-za-z0-9][a-za-z0-9_.-]”。
重要的是要知道三種類型的掛載:
卷存儲在由 docker 管理的主機(jī)文件系統(tǒng)的一部分中(linux 上為 /var/lib/docker/volumes/
)。非 docker 進(jìn)程不應(yīng)修改文件系統(tǒng)的這一部分。卷是在 docker 中保存數(shù)據(jù)的最佳方式。
綁定安裝可以存儲在主機(jī)系統(tǒng)上的任何地方。它們甚至可能是重要的系統(tǒng)文件或目錄。 docker 主機(jī)或 docker 容器上的非 docker 進(jìn)程可以隨時修改它們。
tmpfs
掛載僅存儲在主機(jī)系統(tǒng)的內(nèi)存中,并且永遠(yuǎn)不會寫入主機(jī)系統(tǒng)的文件系統(tǒng)。
volumemounts
用于指定卷掛載。從 github.com/testcontainers/[email?protected]
的值volumemounts
中的條目存儲卷名稱,該條目僅允許 [a-za-z0-9][a-za-z0-9_.-]
,這就是您看到錯誤消息的原因。順便說一句,要看到上面的錯誤消息,您的代碼必須是這樣的(請注意 /docker-entrypoint-initdb.d
是值而不是鍵):
volumemounts: map[string]string{path: "/docker-entrypoint-initdb.d"},
登錄后復(fù)制
問題 2
類型“volume”的掛載配置無效:掛載路徑無效:“c/desktop/folder/golang/tgbotreminder/internal/db/postgresql/migration/000001_init_schema.up”掛載路徑必須是絕對的
要查看此錯誤消息,您的代碼必須如下所示:
volumemounts: map[string]string{`"/c/desktop/folder/golang/tgbotreminder/internal/db/postgresql/migration/000001_init_schema.up"`: "/docker-entrypoint-initdb.d"},
登錄后復(fù)制
作為github.com/testcontainers/
, volumemounts
中條目的鍵存儲掛載路徑。由于掛載路徑包含雙引號("
),因此它是無效的。docker 守護(hù)進(jìn)程首先驗證掛載路徑。這就是您看到錯誤消息的原因。
考慮升級 github.com/testcontainers/testcontainers-go
在版本v0.13.0中,containerrequest.bindmounts
和 containerrequest.volumemounts
替換為 containerrequest.mounts
。這是因為“基于映射的數(shù)據(jù)結(jié)構(gòu)在某種程度上令人困惑。此更改通過為所有組件引入專用類型以獲得 ide 和編譯器的幫助來避免混亂”。 (請參閱 pr#386)。
升級到 github.com/testcontainers/[電子郵件受保護(hù)]
后,可以使用以下方式指定綁定安裝:
Mounts: testcontainers.Mounts( testcontainers.BindMount(path, "/docker-entrypoint-initdb.d"), ),
登錄后復(fù)制