2009-06-03 9 views
38

Sfondo
ho creato i servizi web ASMX in passato e sono stato in grado di accedere al servizio dal browser web e Ajax richieste GET utilizzando la convenzione indirizzo:
MyService.asmx/MyMethod?Param=xxxFare un WCF lavoro Web Service con GET richiede

Ho appena iniziato a utilizzare WCF e ho creato un nuovo servizio Web nel mio progetto ASP.NET. Crea un file con l'estensione .svc come MyService.svc.

situazione attuale
sono in grado di consumare il servizio utilizzando il WcfTestClient che viene fornito con VS2008. Sono anche in grado di creare il mio client WCF aggiungendo un riferimento al servizio in un altro progetto o utilizzando la riga di comando svcutil.exe per generare il proxy e il file di configurazione.

Il problema
Quando provo ad utilizzare il servizio da un browser utilizzando MyService.svc/MyMethod?MyParam=xxx, ottengo una pagina vuota senza errori.

Quello che ho cercato
Ho già aggiunto una basicHttpBinding al web.config e ne ha fatto HttpGetEnabled nella configurazione comportamento. Ho anche aggiunto l'attributo [WebGet(UriTemplate = "MyMethod?MyParam={MyParam}")] al mio contratto operativo.

Ho già seguito le informazioni contenute in questo altro problema di stack overflow:
REST/SOAP EndPoints for a WCF Service

Tuttavia, mi sia ottenere una pagina vuota o un errore HTTP 404 dopo aver seguito questi passaggi. Non c'è niente di speciale nel codice. Sto solo prendendo una stringa come parametro e restituendo "Hello xxx". Questa è una cosa tipo base "Hello WCF World" di tipo proof-of-concept.


AGGIORNAMENTO - Ecco il codice relativo

[ServiceContract] 
public interface IMyService 
{ 
    [WebGet(UriTemplate = "MyMethod/MyParam={MyParam}")] 
    [OperationContract] 
    string MyMethod(string MyParam); 
} 

Web.Config - system.serviceModel Sezione

<system.serviceModel>  
    <behaviors> 
     <serviceBehaviors>   
      <behavior name="MyServiceBehavior"> 
       <serviceMetadata httpGetEnabled="true" /> 
       <serviceDebug includeExceptionDetailInFaults="true"/> 
      </behavior> 
     </serviceBehaviors> 
    </behaviors> 
    <services> 
     <service behaviorConfiguration="MyServiceBehavior" name="MyService"> 
     <endpoint address="" 
         binding="wsHttpBinding" contract="IMyService" /> 
     <endpoint address="MyService.svc" 
         binding="basicHttpBinding" contract="IMyService" /> 
     <endpoint address="mex" 
         binding="mexHttpBinding" contract="IMetadataExchange"/> 
     </service> 
    </services>  
</system.serviceModel> 

risposta

43

Guardando la sezione servizioModel web.config, vedo che è necessario aggiungere un webHttpBinding e associare un endPointBehavior che include webHttpGet.

Il contratto di gestione è corretto. Ecco come dovrebbe apparire la tua sezione di configurazione system.serviceModel in modo che tu possa essere in grado di utilizzare il servizio da una richiesta HTTP GET.

<system.serviceModel>  
    <behaviors> 
     <serviceBehaviors> 
      <behavior name="MyServiceBehavior"> 
       <serviceMetadata httpGetEnabled="true" /> 
       <serviceDebug includeExceptionDetailInFaults="true"/>   
      </behavior> 
     </serviceBehaviors> 
     <endpointBehaviors> 
     <behavior name="WebBehavior"> 
      <webHttp /> 
     </behavior> 
     </endpointBehaviors> 
    </behaviors>  
    <services>  
     <service behaviorConfiguration="MyServiceBehavior" name="MyService"> 
     <endpoint address="ws" binding="wsHttpBinding" contract="IMyService"/> 
     <endpoint address="" behaviorConfiguration="WebBehavior" 
        binding="webHttpBinding" 
        contract="IMyService"> 
     </endpoint> 
     <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange"/> 
     </service> 
    </services>  
</system.serviceModel> 

Assicurarsi di assegnare un indirizzo diverso al vostro endpoint wsHttpBinding, altrimenti si otterrà un errore che dice che ci sono due punti finali di ascolto sulla stessa URI.

Un'altra opzione è lasciare vuoto l'indirizzo in wsHttpBinding, ma assegnare un indirizzo diverso al servizio webHttpBinding. Tuttavia, cambierà anche il tuo indirizzo GET.

Ad esempio, se si assegna l'indirizzo "asmx", si chiamerà il servizio con l'indirizzo "MyService.svc/asmx/MyMethod?MyParam=xxxx".

+0

Suppongo che tutto ciò di cui avevo bisogno era aggiungere l'endPointBehavior. Ha funzionato come un fascino. Grazie. – ichiban

5

Le normali richieste WCF sono sempre richieste SOAP - non sarà in grado per farlo funzionare solo con il tuo browser, avrai bisogno del Testclient WCF per questo.

C'è un add-on per WCF chiamata WCF REST Starter Kit (che sarà anche incluso nella WCF 4.0 con NET 4.0), che consente di utilizzare GET/POST/PUT/DELETE comandi HTTP per interrogare i servizi WCF e tali . È necessario scrivere i servizi in modo specifico per REST, tuttavia non è possibile avere SOAP e REST sulla stessa chiamata di servizio.

Marc

4

Come marc_s says, la Starter Kit resto può aiutare, ma si dovrebbe anche essere consapevoli che .NET 3.5 ha il supporto per i servizi REST direttamente in esso. Non è abbastanza completo come quello che si può fare con il kit di partenza, ma è utile.

Il modo in cui funziona è che si mette un attributo [WebGet] sulle operazioni per indicare dove l'URL dei vari parametri devono provenire da:

[WebGet(UriTemplate = "helloworld/{name}")] 
string Helloworld(string name); 

Vedi this portal per le tonnellate di informazioni.

Nota: è possibile avere lo stesso servizio esposto sia SOAP che REST se si specificano più endpoint/collegamenti nella configurazione.

+0

Ho l'attributo WebGet nel mio Contratto operativo come menzionato nella mia domanda. Ho perso la parte di UriTemplate nella mia domanda, ma è così che ho nel mio codice. Hai provato tu stesso? – ichiban

+0

Sì, questo è il modo in cui costruiamo i nostri servizi REST. –

+0

l'UriTemplate funziona per me. – Cheeso