在Phalanger中使用System.Reflection和资源



我需要使用 phalanger 将一些资源嵌入到 php 编写的纯编译 dll 中。这些是我在视觉工作室中设置为"嵌入式资源"的txt文件。

我的问题是我无法使用程序集类通过GetManifestResourceStream获取资源。

我尝试了这样的代码: 使用系统\反射\程序集

$asm = Assembly::GetExecutingAssembly(); //this gives me mscorlib instead of my dll
$str = $asm->GetManifestResourceStream("name");

我的问题是:我如何访问 phalanger 中的嵌入式资源?非常感谢

我不确定为什么Assembly::GetExecutingAssembly()返回不正确的值。无论如何,若要解决$asm值,请使用以下代码:

$MyType = CLRTypeOf MyProgram;
$asm = $MyType->Assembly;

然后,您可以在发布时访问嵌入的资源

$asm->GetManifestResourceStream("TextFile1.txt");

或者,您可以将标准资源文件 (.resx) 包含在项目中,并使用 \System\Resources\ResourceManager

$this->manager = new SystemResourcesResourceManager("",$asm);
$this->manager->GetObject("String1",null);

请注意,目前Phalanger项目中只能有一个.resx

这个问题很旧,但Phalanger代码(Php.Core.Emit.AddResourceFile()方法)中负责这个问题的部分自从被问到以来没有改变。我遇到了同样的问题,并以(几乎)非黑客的方式解决了它。您必须提供替代名称(/res:/path/to/filename,alternative-name)才能正常工作。

$asm = clr_typeof('self')->Assembly;
$resourceStream = $asm->GetManifestResourceStream("filename");
$reader = new SystemResourcesResourceReader($resourceStream);
$type = $data = null;
$reader->GetResourceData("alternative-name", $type, $data);
// and still there are 4 excess bytes
// representing the length of the resource
$data = substr($data, 4);
$stream  = new IOMemoryStream($data);
// after this $stream is usable as you would expect

简单的GetManifestResourceStream()(如Jakub建议的那样)不起作用,因为Phalanger不使用System.Reflection.Emit.ModuleBuilder.DefineManifestResource()(就像我认为在提供无法识别的文件格式时应该使用的那样)。它使用返回ResourceWriterModuleBuilder.DefineResource(),只真正适合.resources文件。这就是当您需要读取资源时需要使用ResourceReader的要求。

注意:此答案适用于撰写本文时的Phalanger主分支以及大约自2011年以来的先前版本。注意,因为它看起来像一个错误(特别是需要使用原始名称和替代名称)。

相关内容

  • 没有找到相关文章

最新更新