我无法理解如何处理使用 Docker 运行的 WebApi 应用程序中的数据。
在我的应用程序中,用户可以上传存储如下的文件:
~\App_Data\accounts\user123\files\<sha256>.bin
在不配置任何卷的情况下,带有我的应用程序镜像的 Docker 容器似乎工作正常并且写入文件没有任何问题。
现在我想进行配置,以便文件最终位于我可以明确指定的位置,而不是位于默认的 docker 卷文件夹内。
我假设我需要创建卷映射?
我尝试创建一个文件夹并将其映射到“/App_Data”。它仍然像以前一样工作,但我仍然没有在该文件夹中看到任何文件。
此文件夹的写入权限是否有问题?如果没有访问权限,Docker 会回退并写入默认卷吗?
什么用户/组应该具有此文件夹的写入权限?是否有“docker”用户?
我在 Synology NAS 上运行此程序,因此我仅使用带有“添加文件夹”按钮的标准 Docker UI。
这是我尝试过的文件夹:
最佳答案
现在可以使用了!
问题出在这一行:
var appDataPath = env.ContentRootPath + @"\App_Data";
在 Docker 中运行时会转换为 @"/app\App_Data"
。
首先,我使用的是 Windows 目录分隔符 '\'
,我认为它不适用于 Linux。另外,我认为该路径不能包含 "/app"
因为它是相对于该文件夹的。当在 Windows 中的 Docker 之外运行它时,我得到了一个效果更好的根路径:@"c:\wwwroot\app\App_Data"
无论如何,通过更改为它,它开始按预期工作:
var appDataPath = @"/App_Data";
更新
有后续问题。我希望该路径既能在 Linux 上的 Docker 中工作,又能在普通的 Windows 托管中工作,但我不能只使用 /App_Data
作为路径,因为这会转换为 c:\App_Data
在 Windows 上。因此,我尝试使用此路径:./AppData
,它在 Windows 中运行良好,结果为 c:\wwwroot\app\App_Data
。但不幸的是,这在 Docker 中仍然不起作用。但不明白为什么。 Maybee Docker 对路径匹配非常挑剔,只接受完全匹配,即 /App_Data
因为这是我在容器配置中映射到的路径。
无论如何,这真是一个令人头疼的问题,我已经花了 6 个小时来解决这个问题。这是我想出的方法,可以在 Linux 和 Windows 上使用。看起来不太好,但它有效:
Path.Combine(Directory.GetCurrentDirectory().StartsWith("/") ? "/": ".", "App_Data");
如果您能想出更好看的方法,请随时告诉我。
更新2
好的,我想我现在明白了。我认为。在 Docker 中运行此命令时,每个路径都必须以“/”为根。不允许使用相对路径。我的应用程序文件被复制到容器路径“/app”,并且我已将数据映射到“/data”。当前目录设置为“/app”,但要访问数据,我显然必须指向“/data”而不是“/app/data”。我错误地认为所有路径都是相对于“/app”而不是“/”。原因很可能是因为当我在标准 Windows 托管中运行此程序时,我的数据文件位于应用程序文件夹中(在任何情况下这可能都不是一个好主意)。然而,这让我很困惑,认为这同样适用于我的 Docker 环境。
现在我意识到了这一点,它变得更加清晰了。我必须使用“/data”,而不是“./data”或“/app/data”,甚至“data”(这也是相对的)等。
在相对路径可以使用的标准 Windows 托管中,我仍然可以使用“./data”或任何其他相对路径,这些路径将相对于 ContentRootPath/CurrentDir 进行解析。但是,像“/data”这样的绝对根路径将不起作用,因为它将解析为“c:\data”(相对于当前驱动器的根目录)。
关于docker - 如何在 Docker .NET Core Web 应用程序中保存数据?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44508456/