我在openshift上运行dotnet core 2.2 Web api,我有一个返回FileResult的api方法。该文件是使用epplus生成的。但是,在对应用程序进行容器化之后,端点将返回以下错误。我相信如果使用system.drawing库,则会发生此异常,但是我没有使用任何system.drawing功能。
System.TypeInitializationException:“ Gdip”的类型初始值设定项引发了异常。---> System.DllNotFoundException:无法加载DLL'libgdiplus':找不到指定的模块。
public async Task<FileResult> GetPSACostCaseAndFeedData([FromQuery] int caseId, [FromQuery] int proposalId, [FromQuery] int equipmentId)
{
try
{
var queryParams = new Dictionary<string, string> { { "caseId", caseId.ToString() }, { "proposalId", proposalId.ToString() }, { "equipmentId", equipmentId.ToString() } };
var restObj = _restFactory.createRestRequest(Method.GET, "ProposalService/PSACostData/GetPSACostCaseAndFeedData", queryParams);
Console.WriteLine("Base URL - " + restObj.Item2.BaseUrl);
var response = await restObj.Item2.ExecuteTaskAsync(restObj.Item1);
if (response.StatusCode == HttpStatusCode.OK)
{
var result = JsonConvert.DeserializeObject<PSACostCaseDetailsResponse>(response.Content);
Console.WriteLine("result -" + response.Content.ToString());
Console.WriteLine("start writing file");
var excelPackage = await _iPSACostExcelHelper.PopulatePsaCostFile(result, Path.Combine(_hostingEnvironment.ContentRootPath, "App_data", "PSACOST_V9.2.2.xlsm"));
Console.WriteLine("finished writing file");
return await Task.FromResult(File(_excelHelper.ConvertWorkBookToByteArray(excelPackage), ContentTypeEnums.excel, result.customerInformationModel.ProposalNum + "_" + result.caseDataModel.CaseNm + ".xlsm"));
}
throw new Exception("There is no PSA cost data for this case");
}
“完成的写入文件”行确实被打印到标准输出,此后的行失败。有人可以帮助我了解这里出了什么问题吗?为什么FileResult类型的返回方法需要system.drawing?
下面也是我的dockerfile。
FROM mcr.microsoft.com/dotnet/core/aspnet:2.2.7-alpine3.10
LABEL pipelineName="PSACOST.API" \
pipelineKey="UMAOKJOH" \
offeringKey="KKWEECBH"
RUN apk upgrade -U
EXPOSE 5000
ENV ASPNETCORE_URLS=http://*:5000
WORKDIR /app
COPY . /app
USER guest
ENTRYPOINT ["dotnet", "PSACOST.API.Web.dll"]
System.Drawing
从生成QR码的库中使用时,我遇到了类似的情况。
问题似乎是DotNet Core docker映像(sdk或运行时)没有libgdiplus
。对于Linux来说这不是问题,因为您可以apt-get install -y libgdiplus
在容器中做类似的事情,或者使用DotNetCore运行时映像加上this来构建应用程序docker映像libgdiplus
。
这是一个烦人的问题。我不确定是否有任何解决方案都不需要弄乱官方docker镜像,但是到目前为止还没有运气。
目前,我可以看到一些解决方案选项。
选项A:如果您正在使用Linux的Docker DotNetCore映像,似乎可以使用apt安装缺少的运行时依赖项,例如,libgdiplus
因为它们不是docker映像的一部分。
选项B:找到具有所有这些依赖关系的良好Docker DotNetCore映像(SDK或运行时)
选项C:找一个不同的库以外epplus
,不依赖System.Drawing
的libgdiplus
。但我什至不知道那是否可能
更新1对于选项B,您可以尝试以下包含aspnet核心运行时+所需依赖项的docker镜像:lonwern/aspnetcore-libgdiplus:2.1
有关如何在选择选项A之后生成图像的更多信息,请参见此处的创建方式:https : //hub.docker.com/r/lonwern/aspnetcore-libgdiplus/dockerfile
更新2我创建了包含DotNet Core SDK和AspNet Core plus的公共Docker映像,libgdiplus
以便在运行System.Drawing
与SDK DotNet Core CLI一起使用的应用程序时可以使用它们(例如:dotnet vstest,dotnet test等)。或带有运行时。
https://hub.docker.com/repository/docker/sunnyatticsoftware/dotnet-core-sdk-libgdiplus
https://hub.docker.com/repository/docker/sunnyatticsoftware/dotnet-core-aspnet-libgdiplus
有关存储库本身的更多信息。
我在CI / CD管道和Web应用程序的最终Docker映像中使用它们,以避免这些运行时异常。
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句