Đối với những người quan tâm, tôi đã tìm thấy một giải pháp máy chủ ATL bán làm việc. Dưới đây là các mã chủ nhà, thấy nó đang sử dụng BasicHttpBinding, đó là người duy nhất mà làm việc với ATL Server:
var svc = new Service1();
Uri uri = new Uri("http://localhost:8200/Service1");
ServiceHost host = new ServiceHost(typeof(Service1), uri);
var binding = new BasicHttpBinding();
ServiceEndpoint endpoint = host.AddServiceEndpoint(typeof(IService1), binding, uri);
endpoint.Behaviors.Add(new InlineXsdInWsdlBehavior());
host.Description.Behaviors.Add(new ServiceMetadataBehavior() { HttpGetEnabled = true });
var mex = host.AddServiceEndpoint(typeof(IMetadataExchange), MetadataExchangeBindings.CreateMexHttpBinding(), "mex");
host.Open();
Console.ReadLine();
mã cho InlineXsdInWsdlBehavior thể được tìm thấy here. Một thay đổi quan trọng cần được thực hiện cho InlineXsdInWsdlBehavior để nó hoạt động đúng với sproxy khi các kiểu phức tạp có liên quan. Nó được gây ra bởi lỗi trong sproxy, mà không đúng phạm vi bí danh không gian tên, do đó, wsdl không thể có lặp lại bí danh không gian tên hoặc sproxy sẽ crap ra.Dưới đây là các chức năng mà cần phải thay đổi:
public void ExportEndpoint(WsdlExporter exporter, WsdlEndpointConversionContext context)
{
int tnsCount = 0;
XmlSchemaSet schemaSet = exporter.GeneratedXmlSchemas;
foreach (WsdlDescription wsdl in exporter.GeneratedWsdlDocuments)
{
//
// Recursively find all schemas imported by this wsdl
// and then add them. In the process, remove any
// <xsd:imports/>
//
List<XmlSchema> importsList = new List<XmlSchema>();
foreach (XmlSchema schema in wsdl.Types.Schemas)
{
AddImportedSchemas(schema, schemaSet, importsList, ref tnsCount);
}
wsdl.Types.Schemas.Clear();
foreach (XmlSchema schema in importsList)
{
RemoveXsdImports(schema);
wsdl.Types.Schemas.Add(schema);
}
}
}
private void AddImportedSchemas(XmlSchema schema, XmlSchemaSet schemaSet, List<XmlSchema> importsList, ref int tnsCount)
{
foreach (XmlSchemaImport import in schema.Includes)
{
ICollection realSchemas = schemaSet.Schemas(import.Namespace);
foreach (XmlSchema ixsd in realSchemas)
{
if (!importsList.Contains(ixsd))
{
var new_namespaces = new XmlSerializerNamespaces();
foreach (var ns in ixsd.Namespaces.ToArray())
{
var new_pfx = (ns.Name == "tns") ? string.Format("tns{0}", tnsCount++) : ns.Name;
new_namespaces.Add(new_pfx, ns.Namespace);
}
ixsd.Namespaces = new_namespaces;
importsList.Add(ixsd);
AddImportedSchemas(ixsd, schemaSet, importsList, ref tnsCount);
}
}
}
}
Bước tiếp theo là tạo ra C++ tiêu đề:
sproxy.exe /wsdl http://localhost:8200/Service1?wsdl
và sau đó chương trình C++ trông như thế này:
using namespace Service1;
CoInitializeEx(NULL, COINIT_MULTITHREADED );
{
CService1T<CSoapWininetClient> cli;
cli.SetUrl(_T("http://localhost:8200/Service1"));
HRESULT hr = cli.HelloWorld(); //todo: analyze hr
}
CoUninitialize();
return 0;
Kết quả C++ xử lý phức tạp loại khá decently, ngoại trừ việc nó không thể gán NULL cho các đối tượng.
Xin lỗi vì sự chậm trễ. Tôi đã cập nhật câu trả lời của mình. Hy vọng nó giúp. –
Bạn có thể sửa đổi dịch vụ WCF để cung cấp cả hai điểm cuối SOAP và REST, sau đó sử dụng điểm cuối REST từ C++. (Miễn là các kiểu dữ liệu của bạn được phân tích cú pháp dễ dàng trong C++). Xem: http://stackoverflow.com/questions/186631/rest-soap-endpoints-for-a-wcf-service –