Đôi khi, thêm một tham chiếu dịch vụ WCF sẽ tạo ra một tham chiếu trống.


159

Đôi khi, việc thêm Tham chiếu dịch vụ WCF tạo ra một tham chiếu trống. Và tôi không thể tham chiếu dịch vụ ở bất cứ đâu trong dự án.

Có ai gặp phải điều này?

Câu trả lời:


377

Nói chung, tôi thấy rằng đó là một vấn đề về mã-gen và phần lớn là do tôi đã có một cuộc xung đột tên loại mà nó không thể giải quyết.

Nếu bạn nhấp chuột phải vào tham chiếu dịch vụ của bạn và nhấp vào cấu hình và bỏ chọn "Loại sử dụng lại trong các hội đồng tham chiếu", nó có thể sẽ giải quyết vấn đề.

Nếu bạn đang sử dụng một số khía cạnh của tính năng này, bạn có thể cần đảm bảo tên của mình được xóa sạch.


5
Khi nó xảy ra với tôi, tôi thấy rằng tôi cũng cần thay đổi Loại Bộ sưu tập từ ObjectModel.ObservableCollection thành Generic.List
Yossi Dahan

2
Đã xảy ra với tôi vì tôi đã thêm vào một phần lớp.
Makotosan

2
Tuy nhiên, nếu bạn muốn sử dụng các loại từ một hội đồng cụ thể, bạn có thể chọn chỉ tổ hợp đó và nó cũng hoạt động tốt (ít nhất là trong trường hợp của tôi), ta
Dead.Rabit

26
Tôi suy nghĩ rằng tôi nhận được trung bình 50 điểm mỗi tuần từ câu hỏi này thậm chí 6 năm sau đó. Thôi nào MS, sửa cái này đi. Ít nhất là cung cấp cho các nhà phát triển một số phản hồi khi điều này diễn ra kém thay vì khiến họ nhìn chằm chằm vào một tập tin trống.
Anderson Imes

1
9 năm sau và bạn vẫn đang giúp đỡ. Cảm ơn bạn!
tham số

38

Như câu trả lời được chấp nhận chỉ ra, một vấn đề tham chiếu loại khi sử dụng lại các loại có lẽ là thủ phạm. Tôi đã tìm thấy khi bạn không thể dễ dàng xác định sự cố sau đó sử dụng dòng lệnh svcutil.exe sẽ giúp bạn tiết lộ vấn đề tiềm ẩn (như John Saunders chỉ ra).

Như một sự cải tiến ở đây là một ví dụ nhanh về việc sử dụng svcutil.

svcutil /t:code https://secure.myserver.com/services/MyService.svc /d:test /r:"C:\MyCode\MyAssembly\bin\debug\MyAssembly.dll"

Ở đâu:

  • / t: code tạo mã từ url đã cho
  • / d: để chỉ định thư mục cho đầu ra
  • / r: để chỉ định một tham chiếu lắp ráp

Tham khảo dòng lệnh svcutil đầy đủ tại đây: http://msdn.microsoft.com/en-us/l Library / aa347733.aspx

Khi bạn chạy svcutil, bạn sẽ thấy ngoại lệ bị ném bởi quá trình nhập. Bạn có thể nhận được loại tin nhắn này về một trong các loại của bạn: "loại tham chiếu không thể được sử dụng vì nó không khớp với DataContract đã nhập".

Điều này có thể chỉ đơn giản là được chỉ định ở chỗ có sự khác biệt về một trong các loại trong tổ hợp được tham chiếu so với những gì được tạo trong DataContract cho dịch vụ. Trong trường hợp của tôi, dịch vụ tôi đang nhập có các loại mới hơn, được cập nhật từ những gì tôi có trong hội đồng chia sẻ. Điều này không dễ thấy vì loại được đề cập trong ngoại lệ có vẻ giống nhau. Điều khác biệt là một trong những loại phức tạp lồng nhau được sử dụng bởi loại.

Có những kịch bản phức tạp khác có thể kích hoạt loại ngoại lệ này và dẫn đến tham chiếu trống.cs. Đây là một ví dụ .

Nếu bạn đang gặp phải vấn đề này và bạn không sử dụng các loại chung trong hợp đồng dữ liệu cũng như bạn đang sử dụng IsReference = true, thì tôi khuyên bạn nên xác minh chắc chắn rằng các loại được chia sẻ của bạn giống hệt nhau trên máy khách và máy chủ của bạn. Nếu không, bạn có thể sẽ gặp phải vấn đề này.


Trong trường hợp của tôi, điều này xuất hiện sau khi tôi tham chiếu một hội đồng cũng tham chiếu dịch vụ WCF của tôi. Loại bỏ lắp ráp đó khỏi danh sách các hội đồng để chia sẻ các loại với cố định nó.
xr280xr

Tôi đã nhận được một thông báo lỗi vô nghĩa (chỉ là một không gian tên) khi thêm Tham chiếu dịch vụ và điều này đã chỉ ra vấn đề.
bcampolo 28/03/2016

12

Khi điều này xảy ra, hãy tìm trong cửa sổ Lỗi và cửa sổ Đầu ra để xem có thông báo lỗi nào không. Nếu không được, hãy thử chạy svcutil.exethủ công và xem có thông báo lỗi nào không.


@ Làm thế nào để chạy svcutil.exe? Bạn có thể giúp tôi được không ?
Arul Sidthan

@Arul: Sử dụng Google để tìm thông tin về svcutil.exe.
John Saunders

2
Không chắc Microsoft có đọc bài đăng này hay không nhưng thậm chí chỉ hiển thị hộp thông báo cho biết các lỗi và cảnh báo thay vì chỉ âm thầm đưa chúng vào cửa sổ Danh sách Lỗi (được thu nhỏ, trong trường hợp của tôi) sẽ khiến tôi không cần đến Google điều này. Ngoài ra, tôi đoán sẽ hữu ích khi tab hiển thị màu đỏ hoặc màu vàng khi có cảnh báo / lỗi mới?
ngày

12

Tôi đã vùi đầu cả ngày với vấn đề chính xác này. Tôi vừa sửa nó. Đây là cách ...

Dịch vụ phải chạy qua SSL (tức là tại https://mydomain.com/MyService.svc )

Thêm một tham chiếu dịch vụ vào dịch vụ WCF trên máy chủ phát triển hoạt động tốt.

Triển khai cùng một bản dựng chính xác của dịch vụ WCF trên máy chủ sản xuất trực tiếp, sau đó chuyển sang ứng dụng khách và định cấu hình tham chiếu dịch vụ để trỏ đến dịch vụ trực tiếp hiển thị không có lỗi nhưng ứng dụng sẽ không xây dựng: Hóa ra là tham chiếu dịch vụ Tệp Reference.cs hoàn toàn trống rỗng! Cập nhật tham chiếu dịch vụ không có sự khác biệt. Làm sạch các giải pháp đã không giúp đỡ. Khởi động lại VS2010 không có sự khác biệt. Tạo một giải pháp trống mới, bắt đầu một dự án giao diện điều khiển và thêm một tham chiếu dịch vụ vào dịch vụ trực tiếp thể hiện chính xác cùng một vấn đề.

Tôi không nghĩ đó là do các loại xung đột hay bất cứ điều gì, nhưng cái quái gì - tôi đã cấu hình lại tham chiếu dịch vụ WCF bằng cách bỏ chọn "Sử dụng lại các loại trong tất cả các cụm tham chiếu". Không có niềm vui; Tôi đặt dấu kiểm lại.

Bước tiếp theo là thử svcutil trên URL tham chiếu để xem liệu điều đó có giúp phát hiện ra vấn đề không. Đây là lệnh:

svcutil /t:code https://mydomain.com/MyService.svc /d:D:\test

Điều này tạo ra như sau:

Microsoft (R) Service Model Metadata Tool
[Microsoft (R) Windows (R) Communication Foundation, Version 4.0.30319.1]
Copyright (c) Microsoft Corporation.  All rights reserved.

Attempting to download metadata from 'https://mydomain.com/MyService.svc' using WS-Metadata Exchange or DISCO.
Error: Cannot import wsdl:portType
Detail: An exception was thrown while running a WSDL import extension: System.ServiceModel.Description.DataContractSerializerMessageContractImporter
Error: Schema with target namespace 'http://mynamespace.com//' could not be found.
XPath to Error Source: //wsdl:definitions[@targetNamespace='http://mynamespace.com//']/wsdl:portType[@name='IMyService']


Error: Cannot import wsdl:binding
Detail: There was an error importing a wsdl:portType that the wsdl:binding is dependent on.
XPath to wsdl:portType: //wsdl:definitions[@targetNamespace='http://mynamespace.com//']/wsdl:portType[@name='IMyService']
XPath to Error Source: //wsdl:definitions[@targetNamespace='http://tempuri.org/']/wsdl:binding[@name='WSHttpBinding_IMyService']


Error: Cannot import wsdl:port
Detail: There was an error importing a wsdl:binding that the wsdl:port is dependent on.
XPath to wsdl:binding: //wsdl:definitions[@targetNamespace='http://tempuri.org/']/wsdl:binding[@name='WSHttpBinding_IMyService']
XPath to Error Source: //wsdl:definitions[@targetNamespace='http://tempuri.org/']/wsdl:service[@name='MyService']/wsdl:port[@name='WSHttpBinding_IMyService']


Generating files...
Warning: No code was generated.
If you were trying to generate a client, this could be because the metadata documents did not contain any valid contracts or services
or because all contracts/services were discovered to exist in /reference assemblies. Verify that you passed all the metadata documents to the tool.

Warning: If you would like to generate data contracts from schemas make sure to use the /dataContractOnly option.

Điều đó đã làm tôi hoàn toàn bối rối. Mặc dù googling nặng và thực sự khá chéo, và xem xét lại một nghề nghiệp như một tài xế xe buýt, cuối cùng tôi đã xem xét lý do tại sao nó hoạt động tốt trên hộp phát triển. Nó có thể là một vấn đề cấu hình IIS?

Tôi đã từ chối đồng thời vào cả hộp phát triển và hộp trực tiếp và trên mỗi hộp tôi đã kích hoạt Trình quản lý IIS (chạy IIS 7.5). Tiếp theo, tôi đã đi qua từng cài đặt cấu hình trên mỗi hộp, so sánh các giá trị trên mỗi máy chủ.

Và có vấn đề: Trong "Cài đặt SSL" cho trang web, hãy đảm bảo "Yêu cầu SSL" đã được chọn và kiểm tra nút radio Chứng chỉ ứng dụng khách để biết "Chấp nhận". Vấn đề đã được sửa!


5

Tôi đã tìm thấy điều này xảy ra phổ biến bất cứ khi nào tôi thêm một tham chiếu, xóa nó và sau đó thêm lại một dịch vụ có cùng tên. Các xung đột loại dường như được gây ra bởi các tệp cũ còn lại ở đâu đó mà Visual Studio vẫn có thể nhìn thấy. Tất cả những gì tôi cần làm để sửa nó, là sạch trước khi thêm tài liệu tham khảo mới.

  1. Xóa tham chiếu dịch vụ có vấn đề.
  2. Nhấp vào tên dự án trong Solution Explorer để tô sáng dự án.
  3. Nhấp chuột phải vào tài liệu tham khảo dự án.
  4. Gần đầu danh sách ngữ cảnh, nhấp vào mục Clean .
  5. Thêm tài liệu tham khảo dịch vụ của bạn như bạn thường làm.

Hi vọng điêu nay co ich.


3

Tôi gặp vấn đề này với Silverlight 5 được nâng cấp từ phiên bản trước.

Ngay cả việc thêm lại tham chiếu dịch vụ vẫn cung cấp cho tôi một Reference.cs trống

Cuối cùng tôi đã phải tạo một dự án hoàn toàn mới và tạo lại tài liệu tham khảo dịch vụ. Đây là một cái gì đó để thử nếu bạn đã dành hơn nửa giờ cho việc này. Ngay cả khi bạn quyết tâm sửa chữa dự án ban đầu, bạn có thể muốn thử điều này chỉ để xem điều gì xảy ra và sau đó làm việc ngược lại để cố gắng khắc phục sự cố.

Tôi chưa bao giờ tìm ra chính xác vấn đề là gì - nhưng có thể một cái gì đó trong tệp .csproj không được nâng cấp hoặc một số cài đặt bị lỗi.


1
ok hóa ra tôi đã tham khảo một phiên bản cũ của System.Xml.Linq- vì vậy hãy kiểm tra các phiên bản của tất cả các DLL của bạn nếu bạn đã chuyển đổi phiên bản
Simon_Weaver

1

Nếu gần đây bạn đã thêm một bộ sưu tập vào dự án của mình khi điều này bắt đầu xảy ra, vấn đề có thể do hai bộ sưu tập có cùng thuộc tính CollectionDataContract :

[CollectionDataContract(Name="AItems", ItemName="A")]
public class CollectionA : List<A> { }

[CollectionDataContract(Name="AItems", ItemName="A")]  // Wrong
public class CollectionB : List<B> { }

Tôi đã sửa lỗi bằng cách quét qua dự án của mình và đảm bảo rằng mọi thuộc tính NameItemName là duy nhất:

[CollectionDataContract(Name="AItems", ItemName="A")]
public class CollectionA : List<A> { }

[CollectionDataContract(Name="BItems", ItemName="B")]  // Corrected
public class CollectionB : List<B> { }

Sau đó, tôi làm mới tài liệu tham khảo dịch vụ và mọi thứ hoạt động trở lại.



1

Kỹ thuật làm việc cho tôi trong trường hợp của tôi, sau khi đọc những câu trả lời này vô ích, chỉ đơn giản là nhận xét tất cả hợp đồng của tôi và các bit không ghi chú cho đến khi nó không hoạt động nữa, theo kiểu tìm kiếm nhị phân. Điều đó thu hẹp bit vi phạm.

Sau đó, bạn chỉ cần đoán những gì sai với mã đó.

Một số thông tin phản hồi lỗi trong công cụ sẽ có ích, tất nhiên.

Tôi đang viết một hợp đồng dịch vụ web. Tôi đã có một người giữ chỗ enum không có thành viên. Vậy là được rồi. Nhưng nếu tôi sử dụng nó trong một thuộc tính của một lớp khác và sử dụng lại dll hợp đồng trên máy khách, thì codegen sẽ phát nổ mà không có thông báo lỗi. Chạy svcutil.exe không giúp được gì, nó chỉ thất bại khi xuất tệp cs mà không đề cập đến lý do.


Nhận xét tất cả các hợp đồng hoạt động làm việc cho tôi. Tôi đã xem xét các phương pháp sai là thủ phạm. Cảm ơn đã trở lại cách tiếp cận cơ bản để khắc phục sự cố.
fizch

1

Sau đây không được liệt kê ở đây, và đây là giải pháp tôi đã thông qua (SvcUtils là hữu ích trong việc nhìn thấy các thông báo lỗi. Tuy nhiên, lỗi tôi nhận được wrapper type message cannot be projected as a data contract type since it has multiple namespaces. Ý nghĩa, tôi đi theo dẫn này, và tìm hiểu về wsdl.exequa đây bưu điện).

Trong trường hợp của tôi, chỉ cần chạy wsdl [ my-asmx-service-address ] đã tạo ra một .cstệp không có vấn đề , tôi đã đưa vào dự án của mình và sử dụng dịch vụ.


0

Như @dblood chỉ ra, nỗi đau chính nằm ở DataContractSerializer, đó là không sử dụng lại chính xác các loại. Đã có một số câu trả lời ở đây vì vậy tôi sẽ bắt đầu bằng cách thêm một số pro và nhược điểm về những điều này:

  • Cờ 'IsReference' gây ra nhiều rắc rối, nhưng loại bỏ nó không phải lúc nào cũng là câu trả lời (cụ thể: trong các tình huống có đệ quy).
  • Vấn đề cơ bản là hợp đồng dữ liệu bằng cách nào đó không giống với tên loại, mặc dù đôi khi chúng là (huh? Vâng, bạn đã đọc đúng!). Rõ ràng serializer khá kén chọn và rất khó để tìm ra vấn đề thực sự.
  • Xóa 'kiểm tra tham chiếu' khỏi 'Cấu hình tham chiếu dịch vụ', nhưng để lại cho bạn nhiều triển khai. Tuy nhiên, tôi thường sử dụng lại các giao diện SOAP trên toàn bộ DLL. Ngoài ra, trong hầu hết các API trưởng thành mà tôi biết, nhiều giao diện dịch vụ triển khai và mở rộng các lớp giao diện giống nhau. Xóa 'sử dụng các loại tham chiếu' kiểm tra kết quả trong tình huống bạn không thể đơn giản chuyển các đối tượng xung quanh nữa.

May mắn thay, nếu bạn kiểm soát dịch vụ của mình, có một giải pháp đơn giản giúp giải quyết tất cả những vấn đề này. Điều này có nghĩa là bạn vẫn có thể sử dụng lại các giao diện dịch vụ trên toàn bộ DLL - đó là IMO cần phải có cho một giải pháp thích hợp. Đây là cách giải pháp hoạt động:

  1. Tạo một giao diện DLL riêng. Trong DLL đó, bao gồm tất cả DataContract và ServiceContract's; đặt ServiceContract trên giao diện của bạn.
  2. Xuất phát từ việc thực hiện máy chủ từ giao diện.
  3. Sử dụng cùng một DLL để xây dựng ứng dụng khách bằng phương thức yêu thích của bạn. Ví dụ: (IMyInterface là giao diện hợp đồng dịch vụ):

    var httpBinding = new BasicHttpBinding();
    var identity = new DnsEndpointIdentity("");
    var address = new EndpointAddress(url, identity, new AddressHeaderCollection());
    var channel = new ChannelFactory<IMyInterface>(httpBinding, address);
    return channel.CreateChannel();

Nói cách khác: Không sử dụng chức năng 'thêm tham chiếu dịch vụ' , nhưng buộc WCF sử dụng các loại dịch vụ (chính xác) bằng cách bỏ qua việc tạo proxy. Rốt cuộc, bạn đã có những lớp học này.

Chuyên nghiệp:

  1. Bạn bỏ qua quá trình svcutil.exe, có nghĩa là bạn không có bất kỳ vấn đề IsReference nào
  2. Các kiểu và tên DataContract đúng theo định nghĩa; Rốt cuộc, cả máy chủ và máy khách đều sử dụng định nghĩa rất giống nhau.
  3. Nếu bạn mở rộng API hoặc sử dụng các loại từ một DLL khác, (1) và (2) vẫn giữ, do đó bạn sẽ không gặp rắc rối ở đó.

Nhược điểm:

  1. Phương pháp đồng bộ hóa là một nỗi đau, vì bạn không tạo proxy đồng bộ hóa. Do đó, tôi không khuyên bạn nên làm điều này trong các ứng dụng Silverlight.

0

Tôi cũng gặp vấn đề về các tham chiếu dịch vụ bị hỏng khi làm việc với các tham chiếu dự án ở cả hai bên (dự án dịch vụ và dự án có tham chiếu đến dịch vụ). Ví dụ, nếu dll của dự án được tham chiếu được gọi là "Contoso.Development.Common", nhưng tên dự án chỉ được rút ngắn thành "Chung", thì các tham chiếu dự án cho dự án này được đặt tên là "Chung". Tuy nhiên, dịch vụ mong đợi một tham chiếu đến "Contoso.Development.Common" để giải quyết các lớp (nếu tùy chọn này được kích hoạt trong các tùy chọn tham chiếu dịch vụ).

Vì vậy, với explorer tôi đã mở thư mục của dự án đang tham chiếu dịch vụ và dự án "Chung". Ở đó tôi chỉnh sửa tệp dự án VS (.csproj) bằng notepad. Tìm kiếm tên của dự án được giới thiệu lại (đó là "Common.csproj" trong ví dụ này) và bạn sẽ nhanh chóng tìm thấy mục cấu hình đại diện cho tham chiếu dự án.

tôi đã thay đổi

<ProjectReference Include="..\Common\Common.csproj"> <Project>{C90AAD45-6857-4F83-BD1D-4772ED50D44C}</Project> <Name>Common</Name> </ProjectReference>

đến

<ProjectReference Include="..\Common\Common.csproj"> <Project>{C90AAD45-6857-4F83-BD1D-4772ED50D44C}</Project> <Name>Contoso.Development.Common</Name> </ProjectReference>

Điều quan trọng là thay đổi tên của tham chiếu thành tên của dll mà dự án được tham chiếu có là đầu ra.

Sau đó chuyển về VS. Ở đó bạn sẽ được yêu cầu tải lại dự án vì nó đã được sửa đổi bên ngoài VS. Nhấp vào nút tải lại.

Sau khi làm như vậy, thêm cập nhật không tham chiếu dịch vụ làm việc như mong đợi.

Hy vọng điều này cũng giúp người khác.

Trân trọng


0

Tôi đã đối mặt với vấn đề tương tự ngày hôm qua trong quá trình phát triển. Tôi phát hiện ra rằng tôi đã sử dụng cùng một không gian tên trong 2 phiên bản hợp đồng khác nhau.

Chúng tôi đã có 2 phiên bản hợp đồng ví dụ phiên bản4 và phiên bản5. Tôi đã sao chép tất cả các hợp đồng từ phiên bản 4 và đổi tên tất cả các không gian tên từ phiên bản 4 sang phiên bản 5. Trong khi làm điều này, tôi quên đổi tên không gian tên từ v4 thành v5 trong một trong các tệp. Do xung đột không gian tên, tệp Reference.cs trống.

Vấn đề này khó khắc phục vì bạn không nhận được bất kỳ thông báo lỗi nào trong khi tạo tham chiếu dịch vụ. Để xác định vấn đề này, tôi xác nhận thủ công tất cả các tệp mới tôi đã tạo. Có nhiều cách khác để giải quyết vấn đề này. Đây là bước đầu tiên bạn nên thực hiện trước khi đi cho các tùy chọn khác.


0

Cảm ơn bài viết của John Saunders ở trên đã cho tôi một ý tưởng để xem xét cửa sổ Lỗi. Tôi đã đóng gói cả ngày đầu của tôi và tôi đang nhìn vào cửa sổ đầu ra cho bất kỳ lỗi.

Trong trường hợp của tôi, thủ phạm là ISerializable. Tôi có một lớp DataContract với thuộc tính DataMember loại Exception. Bạn không thể có bất kỳ DataMember nào có từ khóa ISerializable. Trong Ngoại lệ này có ISerializable ngay khi tôi gỡ bỏ nó, mọi thứ hoạt động như một bùa mê.


0

Khi cố gắng khắc phục sự cố này svcutil, tôi đã nhận được lỗi được đề cập trong câu trả lời của dblood ("loại tham chiếu không thể được sử dụng vì nó không khớp với DataContract đã nhập").

Trong trường hợp của tôi, nguyên nhân cơ bản dường như là một loại enum có thuộc tính DataContract, nhưng các thành viên không được đánh dấu bằng thuộc tính EnumMember. Lớp vấn đềsvcutil chỉ vào có một thuộc tính với kiểu enum đó.

Điều này sẽ phù hợp hơn khi bình luận cho câu trả lời của dblood, nhưng không đủ đại diện cho điều đó ...


0

Trong trường hợp của tôi, tôi đã có một giải pháp với dự án VB Web Forms có tham chiếu C # UserControl. Cả dự án VB và dự án CS đều có Tham chiếu dịch vụ cho cùng một dịch vụ. Tham chiếu xuất hiện trong Tài liệu tham khảo dịch vụ trong dự án VB và trong nhóm Dịch vụ được kết nối trong dự án CS (khung).

Để cập nhật tham chiếu dịch vụ (nghĩa là lấy tệp Reference.vb để không bị trống) trong dự án biểu mẫu web VB, tôi cần phải XÓA DỰ ÁN CS, sau đó cập nhật Tham chiếu dịch vụ VB, sau đó thêm dự án CS vào giải pháp.


0

Thực hiện theo các bước sau:

  1. Xóa tham chiếu dịch vụ
  2. Đóng Visual Studio
  3. Xóa / Bin và / Obj thư mục.
  4. Mở Visual Studio.
  5. Thêm tài liệu tham khảo dịch vụ.
  6. Không có gì :)

Có vẻ như một số tham chiếu được để lại trong các thư mục này khi thêm dịch vụ, gây ra lỗi trong quá trình tạo mã tự động.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.