Ir para conteúdo

POWERED BY:

Arquivado

Este tópico foi arquivado e está fechado para novas respostas.

acg

Envio de parâmetros array via Nusoap

Recommended Posts

Pessoal,

 

Um serviço precisa receber a seguinte estrutura:

 

<soapenv:Envelope ........>
   <soapenv:Header/>
   <soapenv:Body>
      <ser:Teste>
         <ser:usuario>XXXXX</ser:usuario>
         <ser:senha>XXXX</ser:senha>
         <ser:id>XXX</ser:id>
         <ser:data>XXXXXX</ser:data>
         <ser:cpf>XXXXXX</ser:cpfSupervisor>
         
         <!--1 or more repetitions:-->
         <ser:resposta>
            <dto:desc>XXXXXX</dto:desc>
            <dto:id>XXXXXX</dto:id>
            <dto:resposta>XXXXXX</dto:resposta>
         </ser:resposta>
		 
      </ser:Teste>
   </soapenv:Body>
</soapenv:Envelope>

O problema está na quantidade de respostas a serem enviadas (<!--1 or more repetitions:-->), pois os parâmetros estão sendo enviados por array via NUSOAP.

 

Exemplo:

 

$this->params = array(
		'usuario'	=> usuarioWS,
		'senha'		=> senhaWS,
		'id'		=> $id,
		'data'		=> $P[data],
		'cpf'		=> $P[cpf],
);

foreach($P[respostas] as $indice => $respostas){
	$this->params['resposta']['id'] = $respostas[id];
	$this->params['resposta']['desc'] = $respostas[desc];
	$this->params['resposta']['resposta'] = $respostas[resposta];
}

$this->nomeMetodo = "Teste";

$result = $this->call($this->nomeMetodo, $this->params);

Não posso enviar valores diferentes para uma mesma chave de array, como estou fazendo no laço foreach. Esta é a ideia que eu tinha para enviar respostas diferentes, porém é inviável.

 

Como resolver esta situação? Pelo NUSOAP tem como enviar o XML montado ou tenho que obrigatoriamente enviar como um array?

Compartilhar este post


Link para o post
Compartilhar em outros sites

Certo,

 

class Resposta {
public $conformidade;
public $id;
public $resposta;

public function __construct( $conformidade , $id , $resposta = null ){
	$this->conformidade = $conformidade;
	$this->id = $id;
	$this->resposta = $resposta;
}
}

class Vistoria {
public $usuario;
public $senha;
public $idPropriedade;
public $dataVistoria;
public $cpfSupervisor;
public $resposta = array();

public function addResposta( Resposta $resposta ){
	$this->resposta[] = $resposta;
}
}

$lancarVistoria = new Vistoria();
$lancarVistoria->usuario = 'usuario';
$lancarVistoria->senha = 'senha';
$lancarVistoria->idPropriedade = 1;
$lancarVistoria->dataVistoria = 'xx/xx/xxxx'
$lancarVistoria->cpfSupervisor = 'xx.xxx.xxx-xx';
$lancarVistoria->addResposta( new Resposta( 'conformidade' , 1 ) );
$lancarVistoria->addResposta( new Resposta( 'conformidade' , 2 ) );
$lancarVistoria->addResposta( new Resposta( 'conformidade' , 3 ) );
$lancarVistoria->addResposta( new Resposta( 'conformidade' , 4 ) );
$lancarVistoria->addResposta( new Resposta( 'conformidade' , 5 ) );

try {
$cliente = new SoapClient(
	'http://homolog.agricultura.gov.br/sisbov_ws_nova_hom/services/WsSISBOV?wsdl',
	array(
		'trace'			=> 1,
		'exceptions'	=> 1,
		'style'			=> SOAP_DOCUMENT,
		'use'			=> SOAP_LITERAL,
		'soap_version'	=> SOAP_1_1,
		'encoding'		=> 'UTF-8'
	)
);

$ret = $cliente->lancarVistoria( $lancarVistoria );
} catch ( SoapFault $fault ){
echo 'Opz, ' , $fault->getMessage();
}

 

Tenta ai, caso não funcione ou caso tenha alguma dúvida poste nesse tópico.

Compartilhar este post


Link para o post
Compartilhar em outros sites

Farei os testes e verificarei se está tudo ok! :-)

 

Ok, faça o teste e, caso funcione adequadamente, poste no tópico para que possamos marcá-lo como resolvido.

 

;)

Compartilhar este post


Link para o post
Compartilhar em outros sites

 

Farei os testes e verificarei se está tudo ok! :-)

 

Ok, faça o teste e, caso funcione adequadamente, poste no tópico para que possamos marcá-lo como resolvido.

 

;)

 

João, agradeço muito a sua ajuda.

 

O PHP que utilizo aqui é a versão 4, e infelizmente não funciona bem com orientação a objetos. Não tenho como alterar esta versão.

 

Teria como eu montar um arquivo XML e enviar para este webservice? Acredito que seria a única solução no cenário em que me encontro.

 

Mais uma vez, obrigado.

Compartilhar este post


Link para o post
Compartilhar em outros sites

Teria como eu montar um arquivo XML e enviar para este webservice?

 

Claro que é possível, você precisará estabelecer uma conexão HTTP com o servidor em questão.

 

Primeiro você monta seu XML:

 

<soapenv:Envelope ........>
<soapenv:Header/>
<soapenv:Body>
	<ser:Teste>
	<ser:usuario>XXXXX</ser:usuario>
	<ser:senha>XXXX</ser:senha>
	<ser:id>XXX</ser:id>
	<ser:data>XXXXXX</ser:data>
	<ser:cpf>XXXXXX</ser:cpfSupervisor>

	<!--1 or more repetitions:-->
	<ser:resposta>
	<dto:desc>XXXXXX</dto:desc>
	<dto:id>XXXXXX</dto:id>
	<dto:resposta>XXXXXX</dto:resposta>
	</ser:resposta>

	</ser:Teste>
</soapenv:Body>
</soapenv:Envelope>

 

Pega esse conteúdo e joga em uma string e envia um POST para o servidor do webservice:

<?php
$xml = <<<XML
<soapenv:Envelope ........>
<soapenv:Header/>
<soapenv:Body>
	<ser:Teste>
	<ser:usuario>XXXXX</ser:usuario>
	<ser:senha>XXXX</ser:senha>
	<ser:id>XXX</ser:id>
	<ser:data>XXXXXX</ser:data>
	<ser:cpf>XXXXXX</ser:cpfSupervisor>

	<!--1 or more repetitions:-->
	<ser:resposta>
	<dto:desc>XXXXXX</dto:desc>
	<dto:id>XXXXXX</dto:id>
	<dto:resposta>XXXXXX</dto:resposta>
	</ser:resposta>

	</ser:Teste>
</soapenv:Body>
</soapenv:Envelope>
XML;

$errno = 0;
$error = null;

$fp = fsockopen( 'http-~~-//homolog.agricultura.gov.br/sisbov_ws_nova_hom/services/WsSISBOV' , 80 , $errno , $error );

if ( is_resource( $fp ) ){
	$resp = null;
	$post = "POST / HTTP/1.1\r\n";
	$post .= "Host: homolog.agricultura.gov.br\r\n";
	$post .= "SOAPAction: \r\n";
	$post .= "Content-Type: text/xml; charset=utf-8\r\n";
	$post .= sprintf( "Content-Length: %d\r\n\r\n" , strlen( $xml ) );
	$post .= $xml;

	fwrite( $fh , $post , strlen( $xml ) );

	while ( !feof( $fp ) ){
	$resp .= fgets( $fp , 1024 );
	}

	var_dump( $rest );

	fclose( $fp );
} else {
	echo 'Opz[ ' , $errno , ' ] -> ' , $error;
}

Compartilhar este post


Link para o post
Compartilhar em outros sites

João, ótimo!

 

Executei o script sugerido e me é retornado o seguinte erro:

 

Warning: fsockopen() [function.fsockopen]: php_network_getaddresses: getaddrinfo failed: Name or service not known in /var/www/htdocs/sistemas/devsirca/include/test.php on line 39

 

Warning: fsockopen() [function.fsockopen]: unable to connect to http://sisbov.agricultura.gov.br/sisbov_ws_prd/services/WsSISBOV?wsdl:80 in /var/www/htdocs/sistemas/devsirca/include/test.php on line 39

 

Isso pode ser que o servidor sisbov.agricultura.gov.br não permite que eu realize uma conexão http ou pode ser uma configuração do php do meu servidor?

Compartilhar este post


Link para o post
Compartilhar em outros sites

Warning: fsockopen() [function.fsockopen]: php_network_getaddresses: getaddrinfo failed: Name or service not known in /var/www/htdocs/sistemas/devsirca/include/test.php on line 39

Warning: fsockopen() [function.fsockopen]: unable to connect to http://sisbov.agricu...sSISBOV?wsdl:80 in /var/www/htdocs/sistemas/devsirca/include/test.php on line 39

 

O primeiro erro é falha de resolução de nome (DNS) a segunda linha é consequencia da primeira.

 

Veja se a versão do seu PHP é a mesma reportada aqui: http://bugs.php.net/bug.php?id=22302&edit=1

Compartilhar este post


Link para o post
Compartilhar em outros sites

Olá Joao, estou acompanhando aqui e tive mais ou menos o mesmo problema...

 

Estou precisando consumir um SOAP com PHP (nuSOAP) e estou tendo um problema ao submeter um tipo complexo de dado.

 

O WDSL está no seguinte link: http://dev.gridnet.com.br/physio/services/doctorWS?WSDL

 

O link para o serviço é: http://dev.gridnet.com.br/physio/services/doctorWS

 

A questao toda, é na hora de chamar a funcao "registerDoctor" , tenho que passar pra ela como parametro um tipo complexo, que é o tipo "Doctor".

 

Se fosse fazer no JAVA, seria um objeto e ficaria mais ou menos assim:

 

Doctor doc = new Doctor();

doc.setIdentifier( "123.123.123-87");
doc.setEmail( "mail@mail.com");
doc.setPassword("teste");
doc.setName( "Teste WS" );
doc.setCrmCro( "xyz");
doc.setSpecialization( "mail@mail.com");

Para enviar atraves do nuSOAP, estou usando o seguinte:

 

<?php

require('lib/nusoap.php');

/* create client */
$endpoint = "http://dev.gridnet.com.br/physio/services/doctorWS";

$ns = "http://physio.gridnet.com";

$client = new soapclient($endpoint);

// Add Doctor

$doctor = array( 'crmCro' => '12' , 'email' => 'a@a.com' , 'identifier' => '222.222.222-22' , 'name' => 'Jose Ferreira' , 'password' => 'teste123' , 'phoneHome' => '3131-3131' , 'phoneMobile' => '2121-2121' , 'specialization' => 'Fisioterapeuta' );

// Chamada da funcao

$result = $client->call( 'registerDoctor' , array( 'doctor' => $doctor ) , $ns );

// Resultado

echo '<pre>';
print_r($result);

?>

E o WebService me retorna a mensagem:

 

[faultcode] => soap:Server

[faultstring] => Fault: java.lang.NullPointerException

Sera que voce pode me dar uma luz ?

 

Estou usando como referencia, o documento: http://users.skynet.be/pascalbotte/rcx-ws-doc/phpclient.htm no tópico 2.1.2

 

VLW !!!

Compartilhar este post


Link para o post
Compartilhar em outros sites

Joao!

 

Consegui um servidor PHP 5.

 

Executei o script de OO e foi exibido o seguinte erro:

 

Fatal error: Call to undefined method soapclient::lancarVistoria() in C:\Inetpub\vhosts\locadoradvdoteca.com.br\httpdocs\teste\teste.php on line 54

 

Penso que o correto seria

 

$ret = $cliente->call("lancarVistoria",$lancarVistoria);

 

ao invés de

 

$ret = $cliente->lancarVistoria($lancarVistoria);

 

Se executo da maneira que acho que é correta e dou um echo $ret ou print_r($ret) nada é exibido.

Compartilhar este post


Link para o post
Compartilhar em outros sites

Bom dia!

 

Eu continuei a estudar o assunto e me deparei com o arquivo wsdlclient3b.php que acompanha a biblioteca NuSoap. E há um trecho interessante que se encaixa no meu problema (acredito que no meu caso só enviando o xml terei sucesso):

 

$client = new soapclient('[b]http://www.scottnichol.com/samples/hellowsdl2.php?wsdl[/b]',true,$proxyhost, $proxyport, $proxyusername, $proxypassword);
$err = $client->getError();
if ($err) {
	echo '<h2>Constructor error</h2><pre>' . $err . '</pre>';
}
[b]$params = '<person xsi:type="tns:Person"><firstname xsi:type="xsd:string">Willi</firstname><age xsi:type="xsd:int">22</age><gender xsi:type="xsd:string">male</gender></person>';[/b]
$result = $client->call('hello', $params);

Porém eu tentei enviar, seguindo a mesma estrutura, e me retorna um erro:

 

$this->params = '<SOAP-ENV:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:ser="http://servicosWeb.sisbov.mapa.gov.br" xmlns:dto="http://dto.checklist.certificado.negocio.sisbov.mapa.gov.br"><SOAP-ENV:Header><SOAP-ENV:Body><ser:lancarVistoria>';
		
$this->params .= '<ser:usuario>usuario</ser:usuario><ser:senha>senha</ser:senha><ser:idPropriedade>1234</ser:idPropriedade><ser:dataVistoria>'.$P[data_vistoria].'</ser:dataVistoria><ser:cpfSupervisor>00000000000s</ser:cpfSupervisor><ser:resposta><dto:conformidade>C</dto:conformidade><dto:id>741</dto:id><dto:resposta>teste 1</dto:resposta></ser:resposta><ser:resposta><dto:conformidade>C</dto:conformidade><dto:id>481</dto:id><dto:resposta>teste 2</dto:resposta></ser:resposta>';
		
$this->params .= '</ser:lancarVistoria></SOAP-ENV:Body></SOAP-ENV:Header></SOAP-ENV:Envelope>';
				
$result = $this->call($this->nomeMetodo,$this->params);

Array( [faultcode] => soapenv:Server.userException [faultstring] => org.xml.sax.SAXException: SimpleDeserializer encountered a child element, which is NOT expected, in something it was trying to deserialize. [detail] => Array ( [hostname] => masrv536.agricultura.gov.br ))

 

Estou enviando os parâmetros corretamente? Estão no formato correto?

Compartilhar este post


Link para o post
Compartilhar em outros sites

×

Informação importante

Ao usar o fórum, você concorda com nossos Termos e condições.