【问题标题】:Difference between putting WCF namespace or not?是否放置 WCF 命名空间之间的区别?
【发布时间】:2014-04-17 14:40:23
【问题描述】:

我在关注这个tutorial,在完成上一个教程后也遇到了这个article

让我好奇的是[ServiceContractAttribute]。看到文章里的[ServiceContract]没有Namespace,但是教程有。

所以我继续将[ServiceContract(Namespace="SandwichServices")] 更改为[ServiceContract],但是当我运行应用程序并单击按钮时,出现异常:Uncaught ReferenceError: SandwichServices is not defined

所以我想知道,

  1. 除了还原更改之外,还有其他方法可以解决此错误吗?也许 Web.config 是答案,但我不确定我是否走在正确的轨道上。
  2. 两个[ServiceContractAttribute]有什么区别?从我的角度来看,接口似乎不需要Namespace,但我说的对吗?

Web.config 文件内容:

<system.serviceModel>
  <behaviors>
    <endpointBehaviors>
      <behavior name="SandwichServices.CostServiceAspNetAjaxBehavior">
        <enableWebScript />
      </behavior>
    </endpointBehaviors>
  </behaviors>

  <serviceHostingEnvironment
      aspNetCompatibilityEnabled="true" 
      multipleSiteBindingsEnabled="true" />

  <services>
    <service name="SandwichServices.CostService">
      <endpoint address="" 
          behaviorConfiguration="SandwichServices.CostServiceAspNetAjaxBehavior" 
          binding="webHttpBinding"
          contract="SandwichServices.CostService" />
    </service>
  </services>
</system.serviceModel>

【问题讨论】:

  • 要回答第一个问题,您能否将您的 web.config 添加到问题中,这可能是配置问题。
  • 您是否更新了您的服务参考?
  • @PeterB,抱歉,尝试添加部分 Web.config,但在格式化代码时遇到问题。

标签: c# asp.net wcf


【解决方案1】:

你是对的,ServiceContractAttribute 的命名空间属性在你的合约定义中不是必需的,但它默认为“http://tempuri.org”。这用于在 WSDL 中定义端口类型的名称空间。从您的问题中不清楚为什么会发生错误。

使用 urn 格式的非默认命名空间(例如 urn:companyname:servicename)是一种很好的做法(特别是对于面向外部的 API)。此外,您可以使用 Name 属性来进一步定义服务。

例子:

对于菜单服务

[ServiceContract(Name="menu", Namespace="urn:subway:sandwich")] 

订购服务

[ServiceContract(Name="order", Namespace="urn:subway:sandwich")]

等等

通常,您会将 WSDL 命名空间与代码中的 CLR 命名空间相匹配。

继续这个例子:

namespace Subway.Sandwich
{
   [ServiceContract(Name="menu", Namespace="urn:subway:sandwich")]
   public interface MenuService
   {

   }

   [ServiceContract(Name="order", Namespace="urn:subway:sandwich")]
   public interface OrderService
   {

   }
}

回答您的具体问题。

  1. 相关信息不足,无法了解(但可能与配置有关)。
  2. ServiceContract 和 ServiceContractAttribute 相同,不需要命名空间。

【讨论】:

  • 如果您承认自己无法回答问题,那么您应该先发表评论要求澄清。收集所需信息后,发布完整答案。
  • @BartoszKP 谢谢——我是新来的,会相应更新
  • 不用担心,这是一个非常好的答案——唯一的问题是它没有抓住重点。但是,只要 OP 将使用相关详细信息更新问题,并且您将为 OP 的问题添加特定的解决方案,就可以了 :)
【解决方案2】:

关于这个特定的教程,在我的情况下(在从 ServiceContractAttribute 中删除命名空间之后)更改行就足够了:

var service = new SandwichServices.CostService();

var service = new CostService();

在 Javascript 部分。一切都恢复正常了。

您可以在PeterB's answer找到更多解释。

【讨论】:

  • 这很奇怪。我试过你的方法,但它不起作用。单击按钮时仍然出现错误。
  • @TanJiaMing 你试过“重建”吗?我真的只是从字面上重复了你的步骤:1)教程中的版本(工作)2)删除命名空间(停止工作)3)修复JS(再次开始工作)
  • 是的,我什至尝试了“Clean”,并通过手动删除 DLL 更加极端,但仍然没有运气。
【解决方案3】:

我还倾向于认为您只是在更改命名空间后忘记更新客户端应用程序的服务引用。它的工作原理与 .NET 类几乎相同。让我们考虑一个例子。在命名空间MyProject.SuperClasses 中有一个名为SuperClass 的类。您已经在代码中的某处使用了该类,然后您去更改该类的命名空间。您很可能会遇到构建错误,并且必须为新命名空间添加 using 语句。

还有几个现实生活中为什么应该指定命名空间的例子:

1.

您应该始终指定数据合约的名称和命名空间 防止 .NET 类型的名称和命名空间暴露在 合同。这样,如果您以后决定更改 .NET 命名空间或类型名称,您的数据协定保持不变。

简单来说,指定命名空间后,如果您决定进行一些重构并重命名类或属性,就不会破坏现有客户端。

2.

命名空间通常用于对 WCF 服务进行版本控制。我什至会说使用命名空间对 WCF 服务进行版本控制是最佳实践。所以你应该仔细设计你的命名空间,并像这样在其中包含版本信息:

http://schemas.contoso.com/2005/05/21/PurchaseOrder

这将大大简化您日后想要更改合同并确保现有客户不会中断的事情。你可以阅读更多关于主题here的内容。

希望对你有帮助!

【讨论】:

  • 对不起,我对 WCF 还很陌生。我能知道我应该如何更新关于这个特殊案例的服务参考吗?
  • @Tan Jia Ming 进入客户端应用项目,展开服务引用文件夹,右键引用会出现更新引用的菜单项。
猜你喜欢
  • 2016-05-28
  • 2020-08-21
  • 2012-08-12
  • 2020-10-21
  • 1970-01-01
  • 2012-05-07
  • 1970-01-01
  • 2018-06-23
  • 2014-09-20
相关资源
最近更新 更多