2012-04-19 3 views
0

Je rencontre un problème avec un service WCF fonctionnant correctement. J'essaye de créer un service duplex mais chaque fois que j'essaye de renvoyer un type de données fait sur commande il casse le côté de client.Le service WCF rompt avec le type de données personnalisé

Si je supprime GetTestData tout fonctionne correctement. Quand je l'ajoute, tout se brise du côté du client. Il semble que je puisse le réparer en décochant "Réutiliser les types dans les assemblages référencés", mais je ne suis pas sûr qu'il y ait des effets secondaires négatifs.

Voici le code

ITestService.cs

namespace MyApp.Server 
{ 
    [ServiceContract(Namespace = "http://www.mysite.net", CallbackContract = typeof(IDuplexTestClient))] 
    public interface ITestService 
    { 
     [OperationContract] 
     string Hello(); 

     [OperationContract] 
     TestData GetTestData(); 
    } 

    public interface IDuplexTestClient 
    { 
     [OperationContract(IsOneWay = true)] 
     void TestCallback(string message); 
    } 
} 

TestService.cs

namespace MyApp.Server 
{ 
    [ServiceBehavior(Namespace = "http://www.mysite.net")] 
    public class TestService : ITestService, ICrossDomainPolicyResponder 
    { 
     public string Hello() 
     { 
      return "Hello"; 
     } 

     public TestData GetTestData() 
     { 
      return new TestData(); 
     } 

     #region ICrossDomainPolicyResponder Members 
     public Stream GetSilverlightPolicy() 
     { 
      string result = @"<?xml version=""1.0"" encoding=""utf-8""?> 
       <access-policy> 
        <cross-domain-access> 
         <policy> 
          <allow-from http-request-headers=""*""> 
           <domain uri=""*""/> 
          </allow-from> 
          <grant-to> 
           <resource path=""/"" include-subpaths=""true""/> 
          </grant-to> 
         </policy> 
        </cross-domain-access> 
       </access-policy>"; 
      return StringToStream(result); 

     } 

     public Stream GetFlashPolicy() 
     { 
      string result = @"<?xml version=""1.0""?> 
          <!DOCTYPE cross-domain-policy SYSTEM ""http://www.macromedia.com/xml/dtds/cross-domain-policy.dtd""> 
          <cross-domain-policy> 
           <allow-access-from domain=""*"" /> 
          </cross-domain-policy>"; 
      return StringToStream(result); 
     } 

     private Stream StringToStream(string result) 
     { 
      WebOperationContext.Current.OutgoingResponse.ContentType = "application/xml"; 
      return new MemoryStream(Encoding.UTF8.GetBytes(result)); 
     } 
     #endregion 
    } 
} 

TestData.cs

namespace MyApp.SDK 
{ 
    [DataContract(Namespace = "http://www.mysite.net")] 
    public class TestData 
    { 
     [DataMember] 
     public string TestString { get; set; } 
    } 
} 
+0

Si j'autorise la désactivation des types de réutilisation, j'obtiens deux copies de TestData car je dois l'utiliser dans le client. J'ai donc MyApp.TestServiceReference.TestData et MyApp.SDK.TestData. Sachant que ceux-ci seront identiques, y a-t-il un moyen simple de convertir le type de référence de service en type de SDK local? – thecaptain0220

Répondre

0

Je ne suis toujours pas sûr à 100% de ce qui se passe ici mais j'ai trouvé une solution qui fonctionne pour moi. Je suis capable d'utiliser les "Types de réutilisation dans les assemblages référencés spécifiés" pour obtenir la fonctionnalité dont j'ai besoin. Cela a résolu le problème mais me permet toujours de partager les classes MyApp.SDK entre le client et le serveur.

0

Votre type TestData est déclaré sur le serveur côté.

Pour que le client utilise le service qui renvoie TestData, il doit savoir à quoi ressemble TestData.

Ceci est configuré lorsque vous faites une référence de service d'ajout.

Il y a deux façons de le faire.

  • Le client a une référence à la dll contenant le TestData
  • Le Ajouter un service de référence génère types sur le client

Les « types de réutilisation dans les ensembles référencés », dit que vous voulez utiliser la première option.

Il n'y a pas de "bonne" façon de le faire. Si vous avez le contrôle sur le client et le serveur, vous pouvez réutiliser dll et donc pas besoin de mettre à jour les références de service lorsque les types changent.

+0

Le serveur est WPF et le client est Silverlight. Je pense que c'est le problème. En fait, ils ont tous les deux TestData mais ils sont séparés par des DLL, car l'un est compilé pour Silverlight et l'autre pour WPF. Y a-t-il un moyen de le partager entre les deux dans ce cas? – thecaptain0220

+0

Si elles étaient exactement les mêmes, cela fonctionnerait. Vous avez probablement différents espaces de noms. Dans VS, vous pouvez ajouter un projet existant à une solution –

+0

C'est pourquoi je suis confus. C'est la même classe dans l'espace de noms MyApp.SDK. Les solutions Silverlight et WPF ont simplement des projets différents pointant vers les mêmes fichiers. – thecaptain0220

Questions connexes