RazorEngine在Azure函数中编译模板时抛出NotSupportedException

时间:2018-07-19 21:07:39

标签: azure caching azure-functions razorengine

我必须在azure函数中编译一个剃刀视图才能发送电子邮件,但是出了点问题。我收到一个NotSupportedException错误:The given path's format is not supported.

这是我的代码:

private IRazorEngineService _engine;

public MyCtor(bool isTestEnvironment)
{
    TemplateServiceConfiguration configuration = new TemplateServiceConfiguration();
    configuration.Debug = isTestEnvironment;

    this._engine = RazorEngineService.Create(configuration);
}

public string GetHtmlEmailBody(string templateFileName, object emailData, string layoutFileName)
{
    //Get data type of email data
    Type emailDataType = emailData.GetType();

    string layoutFullFileName = Path.Combine(this._layoutPath, layoutFileName);
    string layoutContentString = File.ReadAllText(layoutFullFileName);
    var layout = new LoadedTemplateSource(layoutContentString, layoutFullFileName);

    this._engine.AddTemplate("layoutName", layout);

    string templateFullFileName = Path.Combine(this._templatePath, templateFileName);
    string templateContentString = File.ReadAllText(templateFullFileName);
    var template = new LoadedTemplateSource(templateContentString, templateFullFileName);

    this._engine.AddTemplate("templateName", template);

    this._engine.Compile("templateName"); //<-- Here I get the exception
    string htmlEmailBody = this._engine.Run("templateName", emailDataType, emailData);

    return htmlEmailBody;
}

路径类似于D:\\...\\Emails\\Templates。。我正在本地测试,并且无法正常工作。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。明确我该如何解决问题。 我认为这个人写过here

时遇到了同样的问题

任何想法我该如何解决?我的工作有问题吗?

我正在使用RazorEngine 3.10.0 谢谢

1 个答案:

答案 0 :(得分:3)

我发现了问题,下载了代码并进行了逆向工程。 问题出在UseCurrentAssembliesReferenceResolver类的GetReferences方法中……这里引发异常的代码:

return CompilerServicesUtility
           .GetLoadedAssemblies()
           .Where(a => !a.IsDynamic && File.Exists(a.Location) && !a.Location.Contains(CompilerServiceBase.DynamicTemplateNamespace))
           .GroupBy(a => a.GetName().Name).Select(grp => grp.First(y => y.GetName().Version == grp.Max(x => x.GetName().Version))) // only select distinct assemblies based on FullName to avoid loading duplicate assemblies
           .Select(a => CompilerReference.From(a))
           .Concat(includeAssemblies ?? Enumerable.Empty<CompilerReference>());

恰好引发异常的语句是File.Exists(a.Location) && !a.Location.Contains(CompilerServiceBase.DynamicTemplateNamespace))。问题在于,在Azure函数中,某些程序集受到保护,因此无法检索到有关它们的信息...(当然,我必须研究Azure函数)...

此刻,我解决了编写自定义ReferenceResolver的问题。我从UseCurrentAssembliesReferenceResolver复制了完全相同的代码,而只是更改了Where的条件。

所以

.Where(a => !a.IsDynamic && File.Exists(a.Location) && !a.Location.Contains(CompilerServiceBase.DynamicTemplateNamespace))

成为

.Where(a => !a.IsDynamic && !a.FullName.Contains("Version=0.0.0.0") && File.Exists(a.Location) && !a.Location.Contains("CompiledRazorTemplates.Dynamic"))

我几乎可以肯定这不是解决问题的最佳方法...但是现在我解决了,两天后我的工作被封锁了,我需要继续...我希望这可以对某人有所帮助。 ..