使用服务结构时出现 System.Runtime.InteropServices.COMException
Posted
技术标签:
【中文标题】使用服务结构时出现 System.Runtime.InteropServices.COMException【英文标题】:System.Runtime.InteropServices.COMException while using service fabric 【发布时间】:2018-02-13 18:02:59 【问题描述】:我正在 Azure Service Fabric Web API 中创建应用程序,但遇到以下问题:
例外:
System.Runtime.InteropServices.COMException occurred
ErrorCode=-2146233628
HResult=-2146233628
Message=Field of ByRef type. (Exception from HRESULT: 0x801312E4)
Source=mscorlib
StackTrace:
at System.Reflection.Emit.TypeBuilder.TermCreateClass(RuntimeModule module, Int32 tk, ObjectHandleOnStack type)
at System.Reflection.Emit.TypeBuilder.CreateTypeNoLock()
at System.Reflection.Emit.TypeBuilder.CreateTypeInfo()
at Microsoft.ServiceFabric.Services.Remoting.Builder.MethodBodyTypesBuilder.BuildRequestBodyType(ICodeBuilderNames codeBuilderNames, CodeBuilderContext context, MethodDescription methodDescription)
at Microsoft.ServiceFabric.Services.Remoting.Builder.MethodBodyTypesBuilder.Build(ICodeBuilderNames codeBuilderNames, CodeBuilderContext context, MethodDescription methodDescription)
at Microsoft.ServiceFabric.Services.Remoting.Builder.MethodBodyTypesBuilder.Build(InterfaceDescription interfaceDescription)
at Microsoft.ServiceFabric.Services.Remoting.Builder.CodeBuilder.Microsoft.ServiceFabric.Services.Remoting.Builder.ICodeBuilder.GetOrBuildMethodBodyTypes(Type interfaceType)
at System.Linq.Enumerable.ToDictionary[TSource,TKey,TElement](IEnumerable`1 source, Func`2 keySelector, Func`2 elementSelector, IEqualityComparer`1 comparer)
at Microsoft.ServiceFabric.Services.Remoting.Builder.ProxyGeneratorBuilder`2.Build(Type proxyInterfaceType, IEnumerable`1 interfaceDescriptions)
at Microsoft.ServiceFabric.Services.Remoting.Builder.CodeBuilder.Microsoft.ServiceFabric.Services.Remoting.Builder.ICodeBuilder.GetOrBuildProxyGenerator(Type interfaceType)
at Microsoft.ServiceFabric.Services.Remoting.Builder.ServiceCodeBuilder.GetOrCreateProxyGenerator(Type serviceInterfaceType)
at Microsoft.ServiceFabric.Services.Remoting.Client.ServiceProxyFactory.CreateServiceProxy[TServiceInterface](Uri serviceUri, ServicePartitionKey partitionKey, TargetReplicaSelector targetReplicaSelector, String listenerName)
at Microsoft.ServiceFabric.Services.Remoting.Client.ServiceProxy.Create[TServiceInterface](Uri serviceUri, ServicePartitionKey partitionKey, TargetReplicaSelector targetReplicaSelector, String listenerName)
at WebService.Controllers.HomeController.<GetAsync>d__0.MoveNext() in C:\Users\shkulka\Documents\Visual Studio 2015\Projects\SortingApp\WebService\Controllers\HomeController.cs:line 17
InnerException:
发生异常的行:
IRequestManagerService proxy = ServiceProxy.Create<IRequestManagerService>(new Uri("fabric:/SortingApp/RequestManagerService"));
一些代码供参考:
namespace WebService.Controllers
[Route("api/[controller]")]
public class HomeController : Controller
[HttpGet]
public async Task<IActionResult> GetAsync(int opId, string sortType = "Quick", string guid="454", string commaSeperatedArray="1,2,3,4")
IRequestManagerService proxy = ServiceProxy.Create<IRequestManagerService>(new Uri("fabric:/SortingApp/RequestManagerService"));
//rest of the code continues . . .
当我点击以下 URL 时发生异常:
http://localhost:8792/api/home?opId=0&sortType=Quick&guid=12&commaSeperatedArray=1,2,3,4
我正在以管理员权限运行我的项目。整个解决方案的平台目标是 x64。
如何摆脱异常?
更新 1:
在点击 URL 之前,我可以观察以下有关服务结构的信息。
在服务结构资源管理器中:
在诊断事件窗口中:
"Timestamp": "2017-09-06T10:49:34.7442479+05:30",
"ProviderName": "Microsoft-ServiceFabric-Services",
"Id": 2,
"Message": "RunAsync has been cancelled for a stateful service replica. The cancellation will be considered 'slow' if RunAsync does not halt execution within 4000 milliseconds. Application Type Name: GettingStartedApplicationType, Application Name: fabric:/GettingStartedApplication, Service Type Name: MyActorServiceType, Service Name: fabric:/GettingStartedApplication/MyActorService, Partition Id: 097c837b-857e-4f10-8c3a-8a902c1f0bb6, Replica Id: 131491461074099453",
"ProcessId": 34840,
"Level": "Informational",
"Keywords": "0x0000F00000000000",
"EventName": "StatefulRunAsyncCancellation",
"ActivityID": null,
"RelatedActivityID": null,
"Payload":
"applicationTypeName": "GettingStartedApplicationType",
"applicationName": "fabric:/GettingStartedApplication",
"serviceTypeName": "MyActorServiceType",
"serviceName": "fabric:/GettingStartedApplication/MyActorService",
"partitionId": "097c837b-857e-4f10-8c3a-8a902c1f0bb6",
"replicaId": 131491461074099453,
"slowCancellationTimeMillis": 4000.0
"Timestamp": "2017-09-06T10:49:34.760793+05:30",
"ProviderName": "Microsoft-ServiceFabric-Services",
"Id": 2,
"Message": "RunAsync has been cancelled for a stateful service replica. The cancellation will be considered 'slow' if RunAsync does not halt execution within 4000 milliseconds. Application Type Name: GettingStartedApplicationType, Application Name: fabric:/GettingStartedApplication, Service Type Name: MyActorServiceType, Service Name: fabric:/GettingStartedApplication/MyActorService, Partition Id: 78f9a969-4f09-4d8b-932f-4962cce7f4cd, Replica Id: 131491461074094464",
"ProcessId": 27832,
"Level": "Informational",
"Keywords": "0x0000F00000000000",
"EventName": "StatefulRunAsyncCancellation",
"ActivityID": null,
"RelatedActivityID": null,
"Payload":
"applicationTypeName": "GettingStartedApplicationType",
"applicationName": "fabric:/GettingStartedApplication",
"serviceTypeName": "MyActorServiceType",
"serviceName": "fabric:/GettingStartedApplication/MyActorService",
"partitionId": "78f9a969-4f09-4d8b-932f-4962cce7f4cd",
"replicaId": 131491461074094464,
"slowCancellationTimeMillis": 4000.0
点击网址后:
更新 2:
界面:
namespace RequestManagerService.Interfaces
public interface IRequestManagerService : IService
Task submitSortRequest(string sortType, string guid, string commaSeperatedArray);
Task<bool> isSortingComplete(string guid);
Task<string> getSortedArray(string guid);
Task<bool> isSortRequested(string sortType, ref string commaSeperatedArray, ref string guid);
Task setSortResult(string sortType, string guid, string sortedArray);
接口实现:
namespace RequestManagerService
/// <summary>
/// An instance of this class is created for each service instance by the Service Fabric runtime.
/// </summary>
internal sealed class RequestManagerService : StatelessService, IRequestManagerService
// <guid,<sorttype, array, isSortComplete>>
Dictionary<string, Tuple<string, string, bool>> SortDictionary = new Dictionary<string, Tuple<string, string, bool>>();
public RequestManagerService(StatelessServiceContext context)
: base(context)
public async Task<string> getSortedArray(string guid)
Tuple<string, string, bool> tempTuple;
string sortedArray= "";
if (await isSortingComplete(guid))
SortDictionary.TryGetValue(guid, out tempTuple);
sortedArray = tempTuple.Item2;
else
sortedArray = "Either there no request with this guid or the sorting is not yet complete.";
return sortedArray;
public Task<bool> isSortingComplete(string guid)
bool isSortComplete = false;
Tuple<string, string, bool> tempTuple;
if (SortDictionary.ContainsKey(guid))
SortDictionary.TryGetValue(guid, out tempTuple);
isSortComplete = tempTuple.Item3;
return Task.FromResult(isSortComplete);
public Task<bool> isSortRequested(string sortType, ref string commaSeperatedArray, ref string guid)
bool requestFound = false;
foreach(KeyValuePair<string, Tuple<string, string, bool>> entry in SortDictionary)
if (entry.Value.Item1 == sortType && entry.Value.Item3 == false)
commaSeperatedArray = entry.Value.Item2;
guid = entry.Key;
requestFound = true;
break;
return Task.FromResult(requestFound);
public Task setSortResult(string sortType, string guid, string sortedArray)
if (SortDictionary.ContainsKey(guid))
Tuple<string, string, bool> updatedTuple = new Tuple<string, string, bool>(sortType, sortedArray, true);
SortDictionary[guid] = updatedTuple;
return Task.FromResult<object>(null);
public Task submitSortRequest(string sortType, string guid, string commaSeperatedArray)
Tuple<string, string, bool> tuple = new Tuple<string, string, bool>(sortType, commaSeperatedArray, false);
SortDictionary.Add(guid, tuple);
return Task.FromResult<object>(null);
/// <summary>
/// Optional override to create listeners (e.g., TCP, HTTP) for this service replica to handle client or user requests.
/// </summary>
/// <returns>A collection of listeners.</returns>
protected override IEnumerable<ServiceInstanceListener> CreateServiceInstanceListeners()
return new ServiceInstanceListener[1]
new ServiceInstanceListener(this.CreateServiceRemotingListener)
;
/// <summary>
/// This is the main entry point for your service instance.
/// </summary>
/// <param name="cancellationToken">Canceled when Service Fabric needs to shut down this service instance.</param>
protected override async Task RunAsync(CancellationToken cancellationToken)
// TODO: Replace the following sample code with your own logic
// or remove this RunAsync override if it's not needed in your service.
long iterations = 0;
while (true)
cancellationToken.ThrowIfCancellationRequested();
ServiceEventSource.Current.ServiceMessage(this.Context, "Working-0", ++iterations);
await Task.Delay(TimeSpan.FromSeconds(1), cancellationToken);
【问题讨论】:
您能否分享一下您尝试访问的服务的合同实现? @KirylZ:嘿,刚刚添加了接口及其实现。如果您有任何想法,请告诉我。 我想说这里的合约不支持 ref/out 参数。摆脱它们,然后重试。 我也想过。但是在控件到达包含ref
或out
的语句之前发生异常。但我会尝试不使用它们。
这会发生在方法调用之前,因为整个类型需要首先在内存中构建。
【参考方案1】:
我想说这里的合同不支持 ref/out 参数。理想情况下,您的服务联系人不应依赖于特定语言的工件。摆脱它们,一切都会正常。
【讨论】:
非常感谢!如果可能的话,请指出合同中不支持提及 ref/out 参数的一些资源。我很想阅读更多内容。 不客气。我记得整个 SF 文档中唯一的参考是https://docs.microsoft.com/en-us/azure/service-fabric/service-fabric-reliable-actors-get-started。您会在此处找到“Actor 接口方法不得具有 out、ref 或可选参数。”。 我知道在 WCF 中可以使用 ref 参数定义合约,但返回类型必须为“void”。由于使用 SF 远程侦听器,您的方法必须是返回任务的异步方法,这可能是阻止您使用 ref 参数的原因。 遗漏一些细节会浪费很多时间!非常感谢。以上是关于使用服务结构时出现 System.Runtime.InteropServices.COMException的主要内容,如果未能解决你的问题,请参考以下文章
WPF 拖动时出现 Invalid FORMATETC structure
无法加载文件或程序集“System.Runtime.CompilerServices.Unsafe”
使用谓词列表时出现 DataContract SerializationException