在这里,或在这里查看完整版本,您可以找到适用于 Unity 的示例 GRPC“Hello World”项目。只有为 Unity 构建并包装在 DLL 中的第一个版本在 Unity IDE 和Standalone build中运行良好。Raw Grpc.Core 文件在 IDE 中正确引用了所有内容,但它们存在编组问题。
不幸的是,它无法为带有 IL2CPP 后端的 UWP 构建。Unity 构建项目并创建一个 .sln 项目。但是 Visual Studio 总是在最终编译时为 GRPC 属性提供 LNK2001。
这是第一个错误代码:
LNK2001 unresolved external _grpccsharp_init@0
LNK2001 unresolved external _grpccsharp_shutdonw@0
LNK2001 unresolved external _grpccsharp_version_string@0
...
好的,感谢@Sunius,我更深入地研究了它。有几点,我要补充一下问题:
在 GRPC C# 包中引用外部方法有两种方法。它们被命名为静态和共享库。
internal class DllImportsFromStaticLib
{
private const string ImportName = "__Internal";
[DllImport(ImportName)]
public static extern void grpcsharp_init();
[DllImport(ImportName)]
public static extern void grpcsharp_shutdown();
...
}
和
internal class DllImportsFromSharedLib
{
private const string ImportName = "grpc_csharp_ext";
[DllImport(ImportName)]
public static extern void grpcsharp_init();
[DllImport(ImportName)]
public static extern void grpcsharp_shutdown();
...
}
我尝试使用共享文件对其进行测试,但我得到了另一个链接错误文件,它有点不同。
LNK2001 unresolved external _dlopen@8
LNK2001 unresolved external _dlsym@8
...
在两个单独的方法中,外部方法连接到内部接口:
public NativeMethods(DllImportsFromStaticLib unusedInstance)
{
this.grpccsharp_init = DllImportsFromStaticLib.grpccsharp_init;
this.grpccsharp_shutdown = DllImportsFromStaticLib.grpccsharp_shutdonw;
...
}
和
public NativeMethods(DllImportsFromSharedLib unusedInstance)
{
this.grpccsharp_init = DllImportsFromSharedLib.grpccsharp_init;
this.grpccsharp_shutdown = DllImportsFromSharedLib.grpccsharp_shutdonw;
...
}
这里定义了调用哪个方法:
private static NativMethods LoadNativeMethodsUnity()
{
switch(PlatformApis.GetUnityRuntimePlatform())
{
case "IPhonePlayer":
return new NativeMethods(new NativeMethods.DllImportsFromStaticLib());
default:
return new NativeMethods(new NativeMethods.DllImportsFromSharedLib());
}
}
一些更新:
感谢@jsmouret,他的 Grpc Github中有 Stub.c 文件,其中包含虚假方法,因此 Linker 不再抱怨 Grpc_init 方法。
下一个错误:dlopen、dlsym、dlerror:
首先,我尝试使用相同的 Stub 技术,但在这种情况下它没有帮助,或者我做错了。
感谢@Sunius,我注释掉了所有“__Internal”dll 导入代码。所以我没有收到任何 dlopen、dlsym 和 dlerror 错误。
下一个错误:它发生在应用程序内部,而不是 Visual Studio 调试器。它告诉我:“异常:要编组托管方法,请在方法定义中添加一个名为 'MonoPInvokeCallback' 的属性。 ”
exception: error loading the embedded resource "Grpc.Core.roots.pem"
和
exception: To marshal a managed method, please add an attribute named 'MonoPInvokeCallback' to the method definition.
在我用谷歌搜索之后,我知道我的选择,但问题是,我应该使用哪种方法?!