Udostępnij za pośrednictwem


Niestandardowy bezpieczny punkt końcowy metadanych

W przykładzie CustomMexEndpoint pokazano, jak zaimplementować usługę z bezpiecznym punktem końcowym metadanych, który używa jednego z powiązań wymiany nienależących do metadanych oraz jak skonfigurować narzędzie ServiceModel Metadata Utility Tool (Svcutil.exe) lub klientów w celu pobrania metadanych z takiego punktu końcowego metadanych. Dostępne są dwa powiązania dostarczone przez system na potrzeby uwidaczniania punktów końcowych metadanych: mexHttpBinding i mexHttpsBinding. mexHttpBinding służy do uwidaczniania punktu końcowego metadanych za pośrednictwem protokołu HTTP w sposób niezabezpieczony. mexHttpsBinding służy do uwidaczniania punktu końcowego metadanych za pośrednictwem protokołu HTTPS w bezpieczny sposób. W tym przykładzie pokazano, jak uwidocznić bezpieczny punkt końcowy metadanych przy użyciu elementu WSHttpBinding. Należy to zrobić, gdy chcesz zmienić ustawienia zabezpieczeń w powiązaniu, ale nie chcesz używać protokołu HTTPS. Jeśli używasz elementu mexHttpsBinding, punkt końcowy metadanych będzie bezpieczny, ale nie ma możliwości modyfikowania ustawień powiązania.

Uwaga

Procedura instalacji i instrukcje kompilacji dla tego przykładu znajdują się na końcu tego tematu.

Usługa

Usługa w tym przykładzie ma dwa punkty końcowe. Punkt końcowy aplikacji obsługuje ICalculator kontrakt z WSHttpBinding włączoną obsługą ReliableSession i Message zabezpieczeniami przy użyciu certyfikatów. Punkt końcowy metadanych używa również elementu WSHttpBindingz tymi samymi ustawieniami zabezpieczeń, ale bez ReliableSessionelementu . Oto odpowiednia konfiguracja:

<services>
    <service name="Microsoft.ServiceModel.Samples.CalculatorService"
             behaviorConfiguration="CalculatorServiceBehavior">
     <!-- use base address provided by host -->
     <endpoint address=""
       binding="wsHttpBinding"
       bindingConfiguration="Binding2"
       contract="Microsoft.ServiceModel.Samples.ICalculator" />
     <endpoint address="mex"
       binding="wsHttpBinding"
       bindingConfiguration="Binding1"
       contract="IMetadataExchange" />
     </service>
 </services>
 <bindings>
   <wsHttpBinding>
     <binding name="Binding1">
       <security mode="Message">
         <message clientCredentialType="Certificate" />
       </security>
     </binding>
     <binding name="Binding2">
       <reliableSession inactivityTimeout="00:01:00" enabled="true" />
       <security mode="Message">
         <message clientCredentialType="Certificate" />
       </security>
     </binding>
   </wsHttpBinding>
 </bindings>

W wielu innych przykładach punkt końcowy metadanych używa wartości domyślnej mexHttpBinding, która nie jest bezpieczna. W tym miejscu metadane są zabezpieczone przy użyciu WSHttpBinding zabezpieczeń Message . Aby klienci metadanych mogli pobierać te metadane, muszą być skonfigurowani z pasującym powiązaniem. W tym przykładzie pokazano dwóch takich klientów.

Pierwszy klient używa Svcutil.exe do pobierania metadanych i generowania kodu klienta i konfiguracji w czasie projektowania. Ponieważ usługa używa powiązania innego niż domyślne dla metadanych, narzędzie Svcutil.exe musi być specjalnie skonfigurowane, aby można było pobrać metadane z usługi przy użyciu tego powiązania.

Drugi klient używa elementu MetadataResolver , aby dynamicznie pobierać metadane dla znanego kontraktu, a następnie wywoływać operacje na dynamicznie generowanym kliencie.

Klient Svcutil

Jeśli używasz domyślnego powiązania do hostowania IMetadataExchange punktu końcowego, możesz uruchomić Svcutil.exe z adresem tego punktu końcowego:

svcutil http://localhost/servicemodelsamples/service.svc/mex

i to działa. Jednak w tym przykładzie serwer używa domyślnego punktu końcowego do hostowania metadanych. Dlatego Svcutil.exe należy poinstruować, aby użyć poprawnego powiązania. Można to zrobić przy użyciu pliku Svcutil.exe.config.

Plik Svcutil.exe.config wygląda jak normalny plik konfiguracji klienta. Jedynymi nietypowymi aspektami są nazwa i kontrakt punktu końcowego klienta:

<endpoint name="http"
          binding="wsHttpBinding"
          bindingConfiguration="Binding1"
          behaviorConfiguration="ClientCertificateBehavior"
          contract="IMetadataExchange" />

Nazwa punktu końcowego musi być nazwą schematu adresu, w którym są hostowane metadane, a kontrakt punktu końcowego musi mieć wartość IMetadataExchange. W związku z tym po uruchomieniu Svcutil.exe za pomocą wiersza polecenia, takiego jak:

svcutil http://localhost/servicemodelsamples/service.svc/mex

Szuka punktu końcowego o nazwie "http" i kontraktu IMetadataExchange , aby skonfigurować powiązanie i zachowanie wymiany komunikacji z punktem końcowym metadanych. Pozostała część pliku Svcutil.exe.config w przykładzie określa poświadczenia konfiguracji powiązania i zachowania zgodne z konfiguracją serwera punktu końcowego metadanych.

Aby Svcutil.exe pobrać konfigurację w pliku Svcutil.exe.config, Svcutil.exe musi znajdować się w tym samym katalogu co plik konfiguracji. W związku z tym należy skopiować Svcutil.exe z lokalizacji instalacji do katalogu zawierającego plik Svcutil.exe.config. Następnie z tego katalogu uruchom następujące polecenie:

.\svcutil.exe http://localhost/servicemodelsamples/service.svc/mex

Wiodący plik ".\" gwarantuje, że zostanie uruchomiona kopia Svcutil.exe w tym katalogu (taka, która ma odpowiedni Svcutil.exe.config).

Klient MetadataResolver

Jeśli klient zna kontrakt i jak komunikować się z metadanymi w czasie projektowania, klient może dynamicznie znaleźć powiązanie i adres punktów końcowych aplikacji przy użyciu elementu MetadataResolver. Ten przykładowy klient pokazuje, jak skonfigurować powiązanie i poświadczenia używane przez MetadataResolver utworzenie i skonfigurowanie elementu MetadataExchangeClient.

Te same informacje o powiązaniu i certyfikacie, które zostały wyświetlone w pliku Svcutil.exe.config, można określić imperatywne w pliku MetadataExchangeClient:

// Specify the Metadata Exchange binding and its security mode
WSHttpBinding mexBinding = new WSHttpBinding(SecurityMode.Message);
mexBinding.Security.Message.ClientCredentialType = MessageCredentialType.Certificate;

// Create a MetadataExchangeClient for retrieving metadata, and set the // certificate details
MetadataExchangeClient mexClient = new MetadataExchangeClient(mexBinding);
mexClient.SoapCredentials.ClientCertificate.SetCertificate(    StoreLocation.CurrentUser, StoreName.My,
    X509FindType.FindBySubjectName, "client.com");
mexClient.SoapCredentials.ServiceCertificate.Authentication.CertificateValidationMode = X509CertificateValidationMode.PeerOrChainTrust;
mexClient.SoapCredentials.ServiceCertificate.SetDefaultCertificate(    StoreLocation.CurrentUser, StoreName.TrustedPeople,
    X509FindType.FindBySubjectName, "localhost");

Po skonfigurowaniu mexClient możemy wyliczyć interesujące nas kontrakty i użyć MetadataResolver polecenia , aby pobrać listę punktów końcowych z tymi kontraktami:

// The contract we want to fetch metadata for
Collection<ContractDescription> contracts = new Collection<ContractDescription>();
ContractDescription contract = ContractDescription.GetContract(typeof(ICalculator));
contracts.Add(contract);
// Find endpoints for that contract
EndpointAddress mexAddress = new EndpointAddress(ConfigurationManager.AppSettings["mexAddress"]);
ServiceEndpointCollection endpoints = MetadataResolver.Resolve(contracts, mexAddress, mexClient);

Na koniec możemy użyć informacji z tych punktów końcowych, aby zainicjować powiązanie i adres używanego ChannelFactory do tworzenia kanałów do komunikowania się z punktami końcowymi aplikacji.

ChannelFactory<ICalculator> cf = new ChannelFactory<ICalculator>(endpoint.Binding, endpoint.Address);

Kluczowym punktem tego przykładowego klienta jest pokazanie, że jeśli używasz programu MetadataResolver, i należy określić niestandardowe powiązania lub zachowania dla komunikacji wymiany metadanych, można użyć elementu , MetadataExchangeClient aby określić te ustawienia niestandardowe.

Aby skonfigurować i skompilować przykład

  1. Upewnij się, że wykonano procedurę instalacji jednorazowej dla przykładów programu Windows Communication Foundation.

  2. Aby skompilować rozwiązanie, postępuj zgodnie z instrukcjami w temacie Building the Windows Communication Foundation Samples (Tworzenie przykładów programu Windows Communication Foundation).

Aby uruchomić przykład na tej samej maszynie

  1. Uruchom Setup.bat z folderu instalacji przykładowej. Spowoduje to zainstalowanie wszystkich certyfikatów wymaganych do uruchomienia przykładu. Należy pamiętać, że Setup.bat używa narzędzia FindPrivateKey.exe, które jest instalowane przez uruchomienie setupCertTool.bat z jednorazowej procedury instalacji dla przykładów programu Windows Communication Foundation.

  2. Uruchom aplikację klienta z folderu \MetadataResolverClient\bin lub \SvcutilClient\bin. Działanie klienta jest wyświetlane w aplikacji konsolowej klienta.

  3. Jeśli klient i usługa nie mogą się komunikować, zobacz Rozwiązywanie problemów Wskazówki dla przykładów programu WCF.

  4. Usuń certyfikaty, uruchamiając Cleanup.bat po zakończeniu pracy z przykładem. Inne przykłady zabezpieczeń używają tych samych certyfikatów.

Aby uruchomić przykład między maszynami

  1. Na serwerze uruchom polecenie setup.bat service. Uruchomienie setup.bat z argumentem service powoduje utworzenie certyfikatu usługi z w pełni kwalifikowaną nazwą domeny maszyny i eksportuje certyfikat usługi do pliku o nazwie Service.cer.

  2. Na serwerze zmodyfikuj plik Web.config, aby odzwierciedlić nową nazwę certyfikatu. Oznacza to, że zmień findValue atrybut w elemencie <serviceCertificate> na w pełni kwalifikowaną nazwę domeny maszyny.

  3. Skopiuj plik Service.cer z katalogu usługi do katalogu klienta na komputerze klienckim.

  4. Na kliencie uruchom polecenie setup.bat client. Uruchomienie setup.bat z argumentem client powoduje utworzenie certyfikatu klienta o nazwie Client.com i wyeksportowanie certyfikatu klienta do pliku o nazwie Client.cer.

  5. W pliku MetadataResolverClient App.config na komputerze klienckim zmień wartość adresu punktu końcowego mex, aby był zgodny z nowym adresem usługi. W tym celu należy zastąpić hosta lokalnego w pełni kwalifikowaną nazwą domeny serwera. Zmień również wystąpienie "localhost" w pliku metadataResolverClient.cs na nową nazwę certyfikatu usługi (w pełni kwalifikowaną nazwę domeny serwera). Wykonaj to samo w przypadku konfiguracji App.config projektu SvcutilClient.

  6. Skopiuj plik Client.cer z katalogu klienta do katalogu usługi na serwerze.

  7. Na kliencie uruchom polecenie ImportServiceCert.bat. Spowoduje to zaimportowanie certyfikatu usługi z pliku Service.cer do magazynu CurrentUser — Trusted Osoby.

  8. Na serwerze uruchom polecenie ImportClientCert.bat, spowoduje to zaimportowanie certyfikatu klienta z pliku Client.cer do magazynu LocalMachine — Trusted Osoby.

  9. Na maszynie usługi skompiluj projekt usługi w programie Visual Studio i wybierz stronę pomocy w przeglądarce internetowej, aby sprawdzić, czy jest uruchomiona.

  10. Na komputerze klienckim uruchom element MetadataResolverClient lub SvcutilClient z programu VS.

    1. Jeśli klient i usługa nie mogą się komunikować, zobacz Rozwiązywanie problemów Wskazówki dla przykładów programu WCF.

Aby wyczyścić po próbce

  • Uruchom Cleanup.bat w folderze samples po zakończeniu uruchamiania przykładu.

    Uwaga

    Ten skrypt nie usuwa certyfikatów usługi na kliencie podczas uruchamiania tego przykładu na maszynach. Jeśli uruchomiono przykłady programu Windows Communication Foundation (WCF), które korzystają z certyfikatów na maszynach, wyczyść certyfikaty usługi zainstalowane w magazynie CurrentUser — Trusted Osoby. W tym celu użyj następującego polecenia: certmgr -del -r CurrentUser -s TrustedPeople -c -n <Fully Qualified Server Machine Name>. Na przykład: certmgr -del -r CurrentUser -s TrustedPeople -c -n server1.contoso.com.