Powershell: ошибка при использовании служб WCF с кодировкой сообщений MTOM - PullRequest
10 голосов
/ 07 апреля 2011

В настоящее время я изучаю возможности PowerShell, но столкнулся с проблемой, которую не смог решить.Будем весьма благодарны за любые быстрые советы =)

Моя цель: вызывать методы из службы WCF (настроенной с кодировкой сообщений MTOM) из powershell v2.0 (возможно, с использованием командлета new-webserviceproxy)

Моя проблема: командлет new-webserviceproxy не может правильно проанализировать ответ службы, если для кодировки сообщений установлено значение Mtom.Я получаю следующую ошибку:

PowerShell :

$proxyObject = New-WebServiceProxy -URI "<a href="http://myserver.com/AccessService.svc?wsdl" rel="noreferrer">http://myserver.com/AccessService.svc?wsdl</a>"<br> $proxyObject.TestWebServiceConnection()

Исключительная ситуация, вызывающая "TestWebServiceConnection" с аргументом (ами) "0": "Клиент обнаружил тип содержимого ответа 'multipart / related; type = "application / xop + xml"; start = " успех </ s: Body></ s: Envelope>--uuid: 4001d529-32b9-4560-9f4b-550c35c67b03 + ID = 4--- «.В строке: 1 символ: 38+ $ proxyObject.TestWebServiceConnection <<<< () >> error.txt+ CategoryInfo: NotSpecified: (:) [], MethodInvocationException+ FullyQualifiedErrorId: DotNetMethodException

Примечание Я могу использовать службу WCF через других клиентов и даже инструмент wcfclient, предоставляемый Microsoft.Вы можете видеть, что TestWebServiceConnectionResult вернул success , но не похоже, что прокси-объект смог проанализировать ответ.

Поведение :

<поведение name = "MyServiceBehavior"></ Поведение>

Binding (я исключил значения тайм-аута / квоту считывателя и размеры сообщений, так как перестановки их значений не имеют отношения к моей проблеме):

</ Безопасность>

Служба

<конечная точка address = "" binding = "basicHttpBinding" bindingConfiguration = "basicHttpEndpointBinding" name = "basicHttpEndpointAccessService" bindingNamespace = "http://myserver.com/" contract =" MyService.IAccessService "/><конечная точка address = "mex" binding = "basicHttpBinding" bindingConfiguration = "basicHttpEndpointBinding" name = "mexEndpointAccess" contract = "IMetadataExchange" />

Ответы [ 2 ]

5 голосов
/ 05 апреля 2012

На момент написания этой статьи мне все еще не удавалось успешно использовать командлет New-WebServiceProxy с службой WCF с включенным MTOM; это не похоже, что командлет поддерживает это. Мой обходной путь включал запуск svcutil.exe для wsdl, а затем компиляцию класса в dll с использованием csc.exe. Затем я загрузил сгенерированную сборку во время выполнения powershell, а затем вручную настроил конечную точку и привязку прокси-класса:

Создание файла .cs из вашего wsdl:

$svcUri = "http://yourdomain/yourService.svc?wsdl";
$csFile = $className + '.cs';   # The name of the generated .cs file
$dllName = [System.IO.Path]::Combine($temp, $className + ".dll")
$svcUtilresult = svcutil.exe /noConfig /out:$csFile $svcUri

Примечание svcutil.exe и csc.exe могут отсутствовать в PATH вашего PowerShell. Вы можете добавить его в свой путь или использовать полный путь. Svcutil можно найти в вашем Microsoft SDKs\Windows\<version>\bin. csc.exe находится в вашей папке %windir%Microsoft .Net

После того, как вы сгенерировали файл .cs, вам нужно скомпилировать его в dll:

&"csc.exe" /t:library /out:$dllName $csFile

Загрузите скомпилированную dll в powershell:

$fileStream = ([System.IO.FileInfo] (Get-Item ".\$dllName")).OpenRead()
$dllBytes = new-object byte[] $fileStream.Length
$fileStream.Read($dllBytes, 0, $fileStream.Length)
$fileStream.Close()

[System.Reflection.Assembly]::Load($dllBytes)

Создание прокси-клиента в powershell:

# Load System.ServiceModel, which can be found in your Framework\v3.0\Windows Communication Foundation folder
[System.Reflection.Assembly]::LoadFile($pathToSystemServiceModel)

# className is the name of your service
$serviceClientName = $className + "Client"

$basicHttpBinding = New-Object System.ServiceModel.BasicHttpBinding
$basicHttpBinding.MessageEncoding = [System.ServiceModel.WSMessageEncoding]::Mtom

$endPoint = New-Object System.ServiceModel.EndpointAddress($svcUri)
$wsClient = New-Object $serviceClientname($basicHttpBinding, $endPoint)
1 голос
/ 11 мая 2013

У меня была похожая проблема. Тем не менее, мне уже удалось сгенерировать код ClientBase, скомпилированный в локальную сборку.

Мое решение было:

add-type -path "..\..\bin\MYassemblyWithWCFCLient.dll"
$binding = new-object system.servicemodel.basichttpbinding
$binding.MessageEncoding = "Mtom"
$endpoint = new-object System.ServiceModel.EndpointAddress("http://whodunit.oops/mtomandjerry.svc")
$regProxy = new-object MySpecialNamespace.OopsServiceContractClient($binding, $endpoint)
...