2011-01-19 3 views
3

이 질문은이 질문과 비슷합니다. Win32Exception @ ServiceHost.Open() for WCF service.WCF slow ServiceHost.Open() 호출

아래의 ServiceHost.Open 호출에서 매우 느린 컴퓨터가 있습니다. 매번 서비스를 열 때까지 항상 7 초 정도 걸립니다. 이 기계는 내 고향 상자이며 이 아니고 도메인의 일부입니다.

도메인의 일부이고 서비스 호스트는 첫 번째 호출에서 약 3-4 초 만에 열리는 다른 상자 (내 작업 상자)에서 동일한 코드를 실행할 수 있지만 프로그램을 다시 실행하면 서비스 호스트가 약 1 초 이내에 열립니다.

나는이 문제에 대해 MS 지원팀에서 작업했으며 추적 로그를 생성했으며 걸려있는 부분은 도메인이 아닌 컴퓨터에서도 도메인에 연결을 시도하는 곳입니다. 그리고 그것은 "지정된 도메인이 존재하지 않거나 접촉 할 수 없습니다."라는 메시지가 나타납니다. 예외 추적 로그에, 그리고 그 모든 시간을 먹는지고있다.

하지만 정말 이상한 점은 내 작업 컴퓨터에서도 도메인에 연결되어 있지 않으면 (내 직장 네트워크에없고 집에서 뛰는 것처럼) 여전히 하지 않음 get 지연.

Windows 7 64 비트를 사용하여 컴퓨터를 재구성했으며 Windows 7이 문제를 해결하지 못했을 때 복원 한 XP SP3을 실행하는 동일한 문제가 발생합니다.

나는 누군가가 이것을 일으킬 수있는 아이디어가 있는지 궁금해했습니다. 그런데 "Microsoft 네트워크 용 클라이언트"를 비활성화하면 ServiceHost를 여는 데 4 초 정도 걸리지 만 여전히이 컴퓨터가 서비스를 열 수있을만큼 빠르지는 않습니다. 어쨌든, 그것이 도메인이나 뭔가의 일부라고 생각합니다. 여기

static void RunServiceWithinEXE() 
    { 
     Uri baseAddress = new Uri("http://localhost:11111/Demo"); 
     ServiceHost serviceHost = new ServiceHost(typeof(CalculatorService), baseAddress); 

     try 
     { 
      // Add a service endpoint 
      serviceHost.AddServiceEndpoint(
       typeof(ICalculator), 
       new WSHttpBinding(), 
       "CalculatorService"); 

      // Enable metadata exchange 
      ServiceMetadataBehavior smb = new ServiceMetadataBehavior(); 
      smb.HttpGetEnabled = true; 
      serviceHost.Description.Behaviors.Add(smb); 
      serviceHost.Opening += new EventHandler(serviceHost_Opening); 
      serviceHost.Opened += new EventHandler(serviceHost_Opened); 
      serviceHost.Open(); 
      Console.WriteLine("The service is ready."); 

      // Close the ServiceHostBase to shutdown the service. 
      serviceHost.Close(); 
     } 
     catch (CommunicationException ce) 
     { 
      Console.WriteLine("An exception occured: {0}", ce.Message); 
      serviceHost.Abort(); 
     } 
    } 

    static void serviceHost_Opened(object sender, EventArgs e) 
    { 
     TimeSpan timeToOpen = DateTime.Now - shOpening; 
     Console.WriteLine("Time To Open: :" + timeToOpen.Seconds); 
    } 

    static void serviceHost_Opening(object sender, EventArgs e) 
    { 
     shOpening = DateTime.Now; 
    } 

내의 app.config,하지만 난 거기에 서비스에 대한 특별한 보안 구성 설정을하지 않아도, 일부 진단 설정은 WCF 추적을 활성화합니다.

<?xml version="1.0" encoding="utf-8" ?> 
<configuration> 
    <system.serviceModel> 
     <diagnostics> 
      <messageLogging maxMessagesToLog="30000" 
        logEntireMessage="true" 
        logMessagesAtServiceLevel="false" 
        logMalformedMessages="true" 
        logMessagesAtTransportLevel="true"> 
       <filters> 
        <clear/> 
       </filters> 
      </messageLogging> 
     </diagnostics> 
    </system.serviceModel> 

    <system.diagnostics> 
     <sources> 
      <source name="System.ServiceModel" switchValue="Warning, ActivityTracing" propagateActivity="true" > 
       <listeners> 
        <add name="xml" /> 
       </listeners> 
      </source> 
      <source name="System.ServiceModel.MessageLogging" switchValue="Warning"> 
       <listeners> 
        <add name="xml" /> 
       </listeners> 
      </source> 
     </sources> 
     <sharedListeners> 
      <add name="xml" type="System.Diagnostics.XmlWriterTraceListener" initializeData="C:\Temp\Server.svclog" /> 
     </sharedListeners> 
     <trace autoflush="true" indentsize="4"> 
      <listeners> 
       <remove name="Default" /> 
       <add name="ScottsConsoleListener" type="System.Diagnostics.ConsoleTraceListener" /> 
       <add name="ScottsTextListener" type="System.Diagnostics.TextWriterTraceListener" initializeData="C:\Temp\DebugLog.txt" /> 
      </listeners> 
     </trace> 
    </system.diagnostics> 
</configuration> 

내 서비스 정의에는 SessionMode가 필요합니다 (아래 참조). SessionMode 요구 사항을 제거하면 지연이 발생하지 않습니다.

using System; 
using System.ServiceModel; 
using System.ServiceModel.Description; 

namespace Microsoft.ServiceModel.Samples 
{ 
    // Define a service contract. 
    [ServiceContract(Namespace = "http://Microsoft.ServiceModel.Samples", SessionMode = SessionMode.Required)] 
    public interface ICalculator 
    { 
     [OperationContract] 
     double Add(double n1, double n2); 

     [OperationContract] 
     double Subtract(double n1, double n2); 

     [OperationContract] 
     double Multiply(double n1, double n2); 

     [OperationContract] 
     double Divide(double n1, double n2); 

     [OperationContract] 
     string PrintName(string firstName, string lastName); 

     [OperationContract] 
     Point MakePoint(double x, double y); 

    } 
} 
+0

해당 컴퓨터에 바이러스 스캐너/방화벽/보안 제품군이 설치되어 있습니까? – CaptainPlanet

+0

@CaptainPlanet - 예.하지만 제거한 후에도 여전히 느립니다. 바이러스 스캐너가 설치되지 않은 채로 시도했지만 Windows 방화벽이 꺼졌습니다. 생각에 감사드립니다. – dcp

+0

서비스 ** 설정 **, 특히 보안 설정을 보여줄 수 있습니까 ?? 도메인에 연결하려고한다는 사실은 ServiceHost가 Windows 도메인에 대한 링크를 설정하여 사용자 자격 증명을 확인하려고하는 Windows 자격 증명을 기본값으로 사용하거나 사용자 지정 인증 메커니즘을 시도하고 있거나 Active Directory 도메인에 연결할 수 있습니다. –

답변

3

네트워크 연결에서 netbios를 비활성화하면 ServiceHost.Open 호출에 지연이 발생하지 않습니다. 왜 그런지 모르겠지만 문제를 해결하는 것처럼 보였습니다.

이상한 점은 XP를 새로 설치할 때 Netbios가 활성화되어 있어도 지연이 없었기 때문에 기존 설치에서 왜 이런 일이 발생하는지 전혀 알지 못합니다. 동일한 컴퓨터에서 실행 한 다음이 테스트를 실행하기 위해 이미지에서 백업을 복원했습니다.

+0

+1 나를 위해 일했습니다. –

4

좋아, 내 의심은 Windows 자격 증명을 사용하여 호출자를 인증 기본값 당신이 구체적으로하지에 얘기하지 않는 한 바인딩 (WsHttpBinding)를 사용하는 사실이다.

서비스 호스팅 코드에서 기본값 WsHttpBinding 인스턴스를 인스턴스화하는 것만으로 기본 보안 동작을 변경하는 구성이나 코드의 설정이 없습니다.

그냥 테스트 목적 :

// Add a service endpoint 
serviceHost.AddServiceEndpoint(
      typeof(ICalculator), 
      new WSHttpBinding(SecurityMode.None), // pass in SecurityMode.None 
      "CalculatorService"); 

이 효과적으로 상쇄 모든 보안 설정, 예 : 코드를 호스팅 서비스를 변경하려고 ServiceHost은 발신자를 인증하기 위해 더 이상 Windows 도메인을 찾지 않아야합니다.

관측치가 변경 되었습니까?

+0

아니요. "System.InvalidOperationException 예외가 발생합니다. 세션에 세션이 필요하지만 'WSHttpBinding'이 바인딩을 지원하지 않거나 올바르게 지원하도록 구성되지 않았습니다." 하지만 제안에 감사 드리며, 감사드립니다. 나는 당신이 그것을 가지고 놀고 싶다면 전체 프로그램과 솔루션 파일을 담고있는 zip 파일을 이메일로 보냈다. – dcp

+0

@dcp : 이것을 시도하십시오 : 생성자에서'SecurityMode.None'을 사용하고 서비스 계약에서'SessionMode.Required'를 제거하십시오 - 이제'ServiceHost'가 en 눈 깜박임 (1 초 미만) . 세션 모드와 그 모든 것들을 설정하는 것은 오버 헤드를 운반합니다 .... 그렇다면 왜 SessionMode가 필요할 것입니까? 이와 같은 서비스에서 필요합니까 ?? –

+0

그래, 나는 SessionMode를 제거하는 것이 오버 헤드를 제거하고 서비스가 빨리 열리게된다는 것을 이미 알고 있었다. 그러나 문제는 SessionMode.Required가있을 때 시스템이 도메인의 일부가 아닌 것을 알기 위해 7 초가 걸리는 이유는 무엇입니까? SessionMode.Required가 필요한 이유는이 짧은 예제가 아니지만 내 실제 WCF 서비스에서는 많은 트랜잭션을 사용하며 때로는 끝점 사이에 세션이 필요합니다. 어쨌든 귀하의 제안에 다시 한 번 감사드립니다. – dcp

0

같은 문제가있는 것 같다. 예외로 인해 발생하는 긴 통화 지속 기간입니다. Wcf 서비스에 대한 보안 설정 구성에 대해 봤습니다. 의 Web.config 파일 위치에 다음과 같은 항목

<wsHttpBinding> 요소 아래 :

<security mode="None" /> 

가 클라이언트에 서비스 참조를 업데이트해야합니다 나를 위해 일한 다음과 같은 해결책을 발견!