【问题标题】:The requested Performance Counter is not a custom counter, it has to be initialized as ReadOnly." on RouteTable.Routes.MapHubs();请求的性能计数器不是自定义计数器,它必须初始化为只读。” 在 RouteTable.Routes.MapHubs();
【发布时间】:2021-02-03 00:24:32
【问题描述】:

我在 AspNet MVC 4 应用程序中使用 SignalR 1.1.2 版本和 Windsor Castle。 我的问题是,自从我迁移到较新的 SignalR 版本后,此错误消息就出现了。

"The requested Performance Counter is not a custom counter, it has to be initialized as ReadOnly."

在行中

    RouteTable.Routes.MapHubs();

这是 RegisterHubs 类

public static class RegisterHubs
{
    public static void Start()
    {
        var signalrDependencyContainer = new WindsorContainer().Install(new HubsInstaller());
        var signalrDependency = new SignalrDependencyResolver(signalrDependencyContainer.Kernel);
        GlobalHost.DependencyResolver = signalrDependency;
        RouteTable.Routes.MapHubs();
    }
}

我已经尝试了一些我在互联网上找到的东西,例如:

lodctr /R
cd C:\Windows\Inf\.NETFramework
lodctr corperfmonsymbols.ini

但我仍然收到相同的错误消息。有任何想法吗?

我正在使用 dotnet 框架 4.5。

这是堆栈跟踪

at System.Diagnostics.PerformanceCounter.InitializeImpl()

谢谢!

更新 我正在添加 Drew 要求的屏幕截图。

【问题讨论】:

  • 你能提供整个堆栈跟踪,而不仅仅是最底部的条目吗?这将有助于确定 SignalR 中哪里出了问题。
  • 这就是它所拥有的一切,没有别的了。
  • 那是不可能的。你能截取你正在看的任何东西吗?根据您到目前为止告诉我们的内容,我认为您在 SignalR 尝试连接其性能计数器时看到了第一次机会异常。如果您查看 SignalR 源代码,它在其中初始化性能计数器,您将看到初始化可能失败的许多原因以及 SignalR 如何优雅地处理这些。 github.com/SignalR/SignalR/blob/master/src/…
  • @DrewMarsh 截图已添加到问题中。

标签: c# asp.net signalr signalr-hub


【解决方案1】:

因此,根据您提供的信息,很明显,这些是 SignalR 尝试创建性能计数器但无权使用进程正在运行的身份这样做时抛出的第一次机会异常在下面。您可以放心地忽略这些异常,但您显然不会获得性能计数器数据。

如果您想创建性能计数器,您需要确保应用程序的身份在运行时属于 Performance Counter Users 组。要么,要么您需要使用Microsoft ASP.NET SignalR Utilities NuGet package 中提供的实用程序应用程序,它允许您创建带外计数器。只需安装包并运行命令:

signalr ipc

【讨论】:

  • 成功了!!我不知道那个包,非常感谢德鲁!
  • 这对我不起作用,直到我指定了“signalR.exe”的完整路径。只需点击 Windows 按钮并键入“signalr.exe”即可找到它...在我的情况下,它是“C:\SVN\trunk\TestSln\packages\Microsoft.AspNet.SignalR.Utils.2.4.1\tools\net40\ signalr.exe" 然后我可以安装性能计数器: PM> C:\SVN\trunk\TestSln\packages\Microsoft.AspNet.SignalR.Utils.2.4.1\tools\net40\signalr.exe ipc
【解决方案2】:

Drew Marsh's response,也为我解决了这个问题。以下是描述如何运行signalr 命令的其他详细信息:


使用包管理器安装 SignalR Utils:

  1. 在 VS 中:工具 -> 库包管理器 -> 包管理器 控制台
  2. 在命令行中输入:

    下午>Install-Package Microsoft.AspNet.SignalR.Utils

  3. 以管理员身份运行 IDE,运行:

    下午>signalr ipc

需要管理员权限才能运行性能计数器安装命令 (signalr ipc) - 不这样做运行会导致此错误:

错误:System.Security.SecurityException:请求的注册表访问 不被允许。 在 Microsoft.Win32.RegistryKey.OpenSubKey(字符串名称,布尔可写) 在 System.Diagnostics.PerformanceCounterLib.CreateRegistryEntry(字符串 categoryName、PerformanceCounterCategoryType categoryType、CounterCreationDataCollec 化创建数据,布尔值和 iniRegistered) 在 System.Diagnostics.PerformanceCounterLib.RegisterCategory(字符串 类别 Name, PerformanceCounterCategoryType categoryType, String categoryHelp, Counter CreationDataCollection creationData) 在 System.Diagnostics.PerformanceCounterCategory.Create(字符串类别名称, 字符串 categoryHelp、PerformanceCounterCategoryType categoryType、 CounterCreationDataCollection counterData) 在 Microsoft.AspNet.SignalR.Utils.PerformanceCounterInstaller.InstallCounters()

   at Microsoft.AspNet.SignalR.Utils.InstallPerformanceCountersCommand.Execute(
String[] args)
   at Microsoft.AspNet.SignalR.Utils.Program.Main(String[] args)
The Zone of the assembly that failed was:
MyComputer

【讨论】:

  • “术语 'signalr' 未被识别为 cmdlet、函数、脚本文件或可运行程序的名称。”成功安装包后。
  • @UserControl 安装信号器似乎有问题。 Install-Package 命令的结果是什么?您可能想看看这里记录的关于软件包安装选项的一些案例:stackoverflow.com/questions/13056329/…
  • 包安装成功。由于某种原因,IDE 找不到该命令。我必须找到它的位置目录并从那里运行signalr ipc
  • 对于那些搜索:安装软件包后,您必须重新启动 Visual Studio 并通过右键单击 VS 图标并单击“以管理员身份运行”以管理员身份运行它。然后您可以从包管理器控制台运行“signalr ipc”命令。
【解决方案3】:

请注意,如果您遵循上述(正确)建议并调用“signalr ipc”来安装 SignalR 的自定义计数器,则在使用调试器运行时,您的应用程序可能会莫名其妙地完全停止工作。 问题是 CLR 在初始化时如何处理 CultureInfo 的错误。该问题至少存在于 SignalR 2.2.0 中。 此处讨论了完整的解释和一些解决方法:https://github.com/SignalR/SignalR/issues/3414

【讨论】:

    【解决方案4】:

    这是为无法使用管理员权限运行的开发者提供的解决方案。创建下面的类并将其添加到 DependencyResolver 中,如下所示:

    // Stop exception being thrown when trying to access performance counters
    var dummyPerformanceCounterManager = new DummyPerformanceCounterManager();
    GlobalHost.DependencyResolver.Register(
        typeof(IPerformanceCounterManager), 
        () =>dummyPerformanceCounterManager);
    

    这是替换 PerformanceCounterManager 的类

    public class DummyPerformanceCounterManager : IPerformanceCounterManager
    {
      private readonly static PropertyInfo[] _counterProperties = GetCounterPropertyInfo();
      private readonly static IPerformanceCounter _noOpCounter = new NoOpPerformanceCounter();
    
      public DummyPerformanceCounterManager()
      {
        foreach (var property in _counterProperties)
        {
          property.SetValue(this, new NoOpPerformanceCounter(), null);
        }
      }
    
      public void Initialize(string instanceName, CancellationToken hostShutdownToken)
      {
      }
    
      public IPerformanceCounter LoadCounter(string categoryName, string counterName, string instanceName, bool isReadOnly)
      {
        return _noOpCounter;
      }
    
      internal static PropertyInfo[] GetCounterPropertyInfo()
      {
        return typeof(DummyPerformanceCounterManager)
            .GetProperties()
            .Where(p => p.PropertyType == typeof(IPerformanceCounter))
            .ToArray();
      }
      public IPerformanceCounter ConnectionsConnected { get; set; }
      public IPerformanceCounter ConnectionsReconnected { get; set; }
      public IPerformanceCounter ConnectionsDisconnected { get; set; }
      public IPerformanceCounter ConnectionsCurrentForeverFrame { get; private set; }
      public IPerformanceCounter ConnectionsCurrentLongPolling { get; private set; }
      public IPerformanceCounter ConnectionsCurrentServerSentEvents { get; private set; }
      public IPerformanceCounter ConnectionsCurrentWebSockets { get; private set; }
      public IPerformanceCounter ConnectionsCurrent { get; private set; }
      public IPerformanceCounter ConnectionMessagesReceivedTotal { get; private set; }
      public IPerformanceCounter ConnectionMessagesSentTotal { get; private set; }
      public IPerformanceCounter ConnectionMessagesReceivedPerSec { get; private set; }
      public IPerformanceCounter ConnectionMessagesSentPerSec { get; private set; }
      public IPerformanceCounter MessageBusMessagesReceivedTotal { get; private set; }
      public IPerformanceCounter MessageBusMessagesReceivedPerSec { get; private set; }
      public IPerformanceCounter ScaleoutMessageBusMessagesReceivedPerSec { get; private set; }
      public IPerformanceCounter MessageBusMessagesPublishedTotal { get; private set; }
      public IPerformanceCounter MessageBusMessagesPublishedPerSec { get; private set; }
      public IPerformanceCounter MessageBusSubscribersCurrent { get; private set; }
      public IPerformanceCounter MessageBusSubscribersTotal { get; private set; }
      public IPerformanceCounter MessageBusSubscribersPerSec { get; private set; }
      public IPerformanceCounter MessageBusAllocatedWorkers { get; private set; }
      public IPerformanceCounter MessageBusBusyWorkers { get; private set; }
      public IPerformanceCounter MessageBusTopicsCurrent { get; private set; }
      public IPerformanceCounter ErrorsAllTotal { get; private set; }
      public IPerformanceCounter ErrorsAllPerSec { get; private set; }
      public IPerformanceCounter ErrorsHubResolutionTotal { get; private set; }
      public IPerformanceCounter ErrorsHubResolutionPerSec { get; private set; }
      public IPerformanceCounter ErrorsHubInvocationTotal { get; private set; }
      public IPerformanceCounter ErrorsHubInvocationPerSec { get; private set; }
      public IPerformanceCounter ErrorsTransportTotal { get; private set; }
      public IPerformanceCounter ErrorsTransportPerSec { get; private set; }
      public IPerformanceCounter ScaleoutStreamCountTotal { get; private set; }
      public IPerformanceCounter ScaleoutStreamCountOpen { get; private set; }
      public IPerformanceCounter ScaleoutStreamCountBuffering { get; private set; }
      public IPerformanceCounter ScaleoutErrorsTotal { get; private set; }
      public IPerformanceCounter ScaleoutErrorsPerSec { get; private set; }
      public IPerformanceCounter ScaleoutSendQueueLength { get; private set; }
    }
    
    internal class NoOpPerformanceCounter : IPerformanceCounter
    {
      public string CounterName => GetType().Name;
      public long Decrement() => 0;
      public long Increment() => 0;
      public long IncrementBy(long value) => 0;
      public long RawValue { get; set; } = 0;
      public void Close() { }
      public void RemoveInstance() { }
      CounterSample IPerformanceCounter.NextSample() => CounterSample.Empty;
    }
    

    【讨论】:

    • 对于DependencyResolver注册:using Microsoft.AspNet.SignalR; using Microsoft.AspNet.SignalR.Infrastructure;对于类:using Microsoft.AspNet.SignalR.Infrastructure; using System.Diagnostics; using System.Linq; using System.Reflection; using System.Threading;
    【解决方案5】:

    解决了这个问题。在我的测试或生产服务器中,我没有安装像 Visual Studio 这样的 IDE。所以我坚持同样的错误。最后我简单地做了以下步骤:

    请在安装了 VS 的服务器上执行以下步骤

    • 在 VS 中:工具 -> NuGet 包管理器 -> 包管理器控制台 在命令行中输入:

    • 下午>Install-Package Microsoft.AspNet.SignalR.Utils

    • 转到包 -> Microsoft.AspNet.SignalR.Utils.2.2.3 -> 工具

    • 复制signalr.exe

    请在测试或生产服务器中执行以下步骤

    • 将signalr.exe粘贴到bin->debug文件夹下并复制路径
    • 以管理员模式打开命令提示符并将目录更改为复制的路径
    • 键入并运行命令signalr.exe ipc

    成功运行上述命令后,我启动了应用程序,它运行良好。如果他们在测试环境中需要它,我只是将其发布给其他人。

    【讨论】:

      【解决方案6】:

      如果您不想完全使用性能计数器,那么当您的解析器在被要求提供IPerformanceCounterManager 时返回“null”是完全可以的。

      https://github.com/SignalR/SignalR/blob/master/src/Microsoft.AspNet.SignalR.Core/Hosting/HostDependencyResolverExtensions.cs

          private static void InitializePerformanceCounters(this IDependencyResolver resolver, string instanceName, CancellationToken hostShutdownToken)
          {
              var counters = resolver.Resolve<IPerformanceCounterManager>();
              if (counters != null)
              {
                  counters.Initialize(instanceName, hostShutdownToken);
              }
          }
      

      我刚刚遇到了这个问题,因为 ninject 在请求未配置的依赖项时抛出。

      【讨论】:

        猜你喜欢
        • 2011-01-04
        • 2013-06-02
        • 2013-02-28
        • 2012-12-13
        • 2013-01-03
        • 2021-10-06
        • 2018-03-13
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多