Usamos cookies para medir audiência e melhorar sua experiência. Você pode aceitar ou recusar a qualquer momento. Veja sobre o iMasters.
Galera,
preciso criar uma aplicação com cURL, que acesse determinada action do meu site, e devolva por exemplo, os valores em XML. Essa aplicação teria que ter um tipo de autenticação, como informando uma string (TOKEN) que cada cliente (que fosse cadastrado em meu sistema) teria. Seria algo semelhante com o oAuth do Twitter, mas eu já pesquisei (muito), e não consegui usar esse oAuth de forma personalizada para o meu site.
Eu sei como recuperar os dados com cURL. Também sei ler o arquivo XML. O que não sei como fazer é essa parte da autenticação.
Essa aplicação é necessária, pois alguns sites de clientes meus, utilizam um serviço compartilhado de meu site (serviço de notícias, por exemplo), mas em alguns desses sites, o servidor não está conectando com o banco de dados, e assim, não consegue recuperar as informações.
Imagino que acessando essas informações com o cURL, eu possa poupar um pouco o banco de dados, salvando em cache o arquivo recuperado (XML).
Alguém sabe como posso começar a fazer esse sistema?
o mais correto seria utilizar soap q ja tem recursos de autenticacao...porem você tera q estudar muita coisa: webservices, soap, xml..wsdl...
>
o mais correto seria utilizar soap q ja tem recursos de autenticacao...porem você tera q estudar muita coisa: webservices, soap, xml..wsdl...
Sim e não, SOAP vai dificultar ainda mais o que ele tem que fazer, quando poderia resolver simplesmente da forma que falei, e na verdade, a autenticação feita no WSDL não é grandes coisas, se não me engano os meios fornecidos são de autenticação interna.
mas se ele vai criar uma API para terceiros, o ideal nao eh soap? se fosse algo interno at concordo com curl...mas pra terceiros ?
>
mas se ele vai criar uma API para terceiros, o ideal nao eh soap? se fosse algo interno at concordo com curl...mas pra terceiros ?
Certo, então mostre a ele um exemplo de autenticação com SOAP da forma que ele quer.
Concordo com o Andrey.
É uma solução simples e fácil, logo, pouparia performace no Banco de Dados, já que os dados seriam mostrados como XML ou...
Imprimir um jSON com PHP e retorná-los para os seus clientes como Objeto Javascript, mas essa opção é mais... Trabalhosa! :upset:
SOAP para uma aplicação dessa? Eeerk...
>
Concordo com o Andrey.
É uma solução simples e fácil, logo, pouparia performace no Banco de Dados, já que os dados seriam mostrados como XML ou...
Imprimir um jSON com PHP e retorná-los para os seus clientes como Objeto Javascript, mas essa opção é mais... Trabalhosa! :upset:
SOAP para uma aplicação dessa? Eeerk...
SOAP é uma opção sim. Por que não seria? Desempenho?
>
Certo, então mostre a ele um exemplo de autenticação com SOAP da forma que ele quer.
eu nao sei tudo, por isso eu lhe perguntei...gostaria de saber a resposta de alguem mais experiente, at pq eu nunca fiz isso, sempre li a respeito...
SOAP é, de fato, uma opção para o que quero fazer. Já havia estudado essa opção, mas ele é, como vocês mesmo disseram, muito complicado de se implementar. Pelo menos eu não consegui fazer de primeira nada de util.
Demorei um pouquinho pra entender, mas acho que essa sua dica resolve o problema Andrey Knupp. Eu já havia pensado em fazer assim, mas com tanta coisa na cabeça, essa idéia estava confusa.
A idéia aqui não é fazer um Twitter da vida, mas quanto mais próximo possível de sua API (como segurança, rapidez e flexibilidade) melhor.
Obrigado a todos pelas dicas... Mas se alguém souber de algum outro método "comprovadamente eficaz" de se fazer essa aplicação, por favor comente.
>
SOAP é uma opção sim.
Claro que é uma opção, o está correto ao sugeri-la! O único erro dele (do Igor) foi afirmar que é o mais correto.
muito complicado de se implementar.
Também não é complicado de se implementar.
1. Criação da interface, no caso do SOAP chama-se WSDL:
service.wsdl
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<wsdl:definitions xmlns:im="urn:com.imasters/forum"
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
name="news"
targetNamespace="urn:com.imasters/forum">
<wsdl:types>
<xsd:schema targetNamespace="urn:com.imasters/forum">
<xsd:import namespace="http://schemas.xmlsoap.org/soap/encoding/" />
<xsd:element name="datetime" type="xsd:dateTime" nillable="true" />
<xsd:element name="feed" type="im:ArrayOfTopic" />
<xsd:element name="authentication" type="im:User"/>
<xsd:complexType name="ArrayOfTopic">
<xsd:complexContent>
<xsd:restriction base="soapenc:Array">
<xsd:attribute ref="soapenc:arrayType" wsdl:arrayType="im:Topic" />
</xsd:restriction>
</xsd:complexContent>
</xsd:complexType>
<xsd:complexType name="Topic">
<xsd:sequence>
<xsd:element name="title" type="xsd:string" />
<xsd:element name="datetime" type="xsd:dateTime" />
<xsd:element name="content" type="xsd:normalizedString" />
</xsd:sequence>
</xsd:complexType>
<xsd:complexType name="User">
<xsd:sequence>
<xsd:element name="name" type="xsd:normalizedString" />
<xsd:element name="pswd" type="xsd:normalizedString" />
<xsd:element name="token">
<xsd:simpleType>
<xsd:restriction base="xsd:normalizedString">
<xsd:length value="40"/>
</xsd:restriction>
</xsd:simpleType>
</xsd:element>
</xsd:sequence>
</xsd:complexType>
</xsd:schema>
</wsdl:types>
<wsdl:message name="authenticationHeader">
<wsdl:part element="im:authentication" name="authentication"/>
</wsdl:message>
<wsdl:message name="getNewsRequest">
<wsdl:part element="im:datetime" name="request" />
</wsdl:message>
<wsdl:message name="getNewsResponse">
<wsdl:part element="im:feed" name="response" />
</wsdl:message>
<wsdl:portType name="service">
<wsdl:operation name="getNews">
<wsdl:input message="im:getNewsRequest" />
<wsdl:output message="im:getNewsResponse" />
</wsdl:operation>
</wsdl:portType>
<wsdl:binding name="serviceSOAP" type="im:service">
<soap:binding style="document"
transport="http://schemas.xmlsoap.org/soap/http" />
<wsdl:operation name="getNews">
<soap:operation soapAction="urn:com.imasters/forum/getNews" />
<wsdl:input>
<soap:header use="literal"
part="authentication"
message="im:authenticationHeader"
wsdl:required="true"/>
<soap:body use="literal" />
</wsdl:input>
<wsdl:output>
<soap:body use="literal" />
</wsdl:output>
</wsdl:operation>
</wsdl:binding>
<wsdl:service name="service">
<wsdl:port binding="im:serviceSOAP" name="serviceSOAP">
<soap:address location="http://seu-dominio.com/service.php" />
</wsdl:port>
</wsdl:service>
</wsdl:definitions>
O WSDL define as operações do serviço e também as entradas e saídas, veja o detalhe da entrada na operação getNews:
<wsdl:input>
<soap:header use="literal"
part="authentication"
message="im:authenticationHeader"
wsdl:required="true"/>
<soap:body use="literal" />
</wsdl:input>
O serviço fica assim:
Service.php
<?php
require_once 'Topic.php';
require_once 'User.php';
class Service {
/**
* Autenticação do usuário.
* @param User $request Usuário que está utilizando o webservice.
*/
public function authentication( User $request ) {
// TODO: Regras de negócio para validação da autenticação
if ( $request->getName() !== 'usuario' ||
$request->getPswd() !== 'senha' ||
$request->getToken() !== sha1( 'token' ) ){
throw new SoapFault( 'AUTH' , 'Não autenticado' );
}
}
/**
* Recupera os tópicos de notícias.
* @param string $request Data no formato YYYY-MM-DDTHH:MM:SS
* @return array[Topic]
*/
public function getNews( $request ) {
//TODO: Utilizar a model já existente para recuperar as notícias.
return array( new Topic() , new Topic() );
}
}
Perceba que foram utilizadas duas entidades, Topic e User:
Topic.php
<?php
class Topic {
/**
* @var string
*/
private $title;
/**
* @var string
*/
private $datetime;
/**
* @var string
*/
private $content;
/**
* @return string
*/
public function getTitle() {
return $this->title;
}
/**
* @return string
*/
public function getDatetime() {
return $this->datetime;
}
/**
* @return string
*/
public function getContent() {
return $this->content;
}
/**
* @param string $title
*/
public function setTitle($title) {
$this->title = $title;
}
/**
* @param string $datetime
*/
public function setDatetime($datetime) {
$this->datetime = $datetime;
}
/**
* @param string $content
*/
public function setContent($content) {
$this->content = $content;
}
}
User.php
<?php
class User {
/**
* @var string
*/
private $name;
/**
* @var string
*/
private $pswd;
/**
* @var string
*/
private $token;
/**
* @return string
*/
public function getName() {
return $this->name;
}
/**
* @return string
*/
public function getPswd() {
return $this->pswd;
}
/**
* @return string
*/
public function getToken() {
return $this->token;
}
/**
* @param string $name
*/
public function setName($name) {
$this->name = $name;
}
/**
* @param string $pswd
*/
public function setPswd($pswd) {
$this->pswd = $pswd;
}
/**
* @param string $token
*/
public function setToken($token) {
$this->token = $token;
}
}
Para configurar o servidor SOAP é bem simples:
service.php
<?php
require_once 'Service.php';
require_once 'User.php';
$server = new SoapServer( 'service.wsdl' , array(
'trace' => true,
'exceptions' => true,
'style' => SOAP_DOCUMENT,
'use' => SOAP_LITERAL,
'soap_version' => SOAP_1_1,
'encoding' => 'UTF-8',
'classmap' => array(
'User' => 'User',
)
) );
$server->setObject( new Service() );
$server->handle();
Perceba que esse service.php é o que está configurado no WSDL, lá em soapaddress:
<soap:address location="http://seu-dominio.com/service.php" />
Bom, com isso você tem um web service SOAP pronto, para seu clientes utilizarem isso basta fazerem:
client.php
<?php
require_once 'Topic.php';
//Configura o client
$client = new SoapClient( 'http://127.0.0.3/dg/service.wsdl' , array(
'trace' => true,
'exceptions' => true,
'style' => SOAP_DOCUMENT,
'use' => SOAP_LITERAL,
'soap_version' => SOAP_1_1,'classmap' => array(
'Topic' => 'Topic',
)
) );
//Configura a autenticação
$client->__setSoapHeaders( new SoapHeader(
'urn:com.imasters/forum',
'authentication',
(object) array(
'name' => 'usuario',
'pswd' => 'senha',
'token' => sha1( 'token' )
)
) );
//Recupera as notícias
try {
$news = $client->getNews();
print_r( $news );Just simple!
O código do exemplo do servidor está em: [https://github.com/netojoaobatista/soap
;)
Vish! API RESTful é a solução.
>
Vish! API RESTful é a solução.
Sou obrigado a concordar ..
>
Vish! API RESTful é a solução.
>
Sou obrigado a concordar ..
Concordo plenamente.
Nesse caso específico, sim, é a solução. Mas alguém que discorda da implementação SOAP, consegue dizer o motivo de REST ser a solução para esse caso específico?
Já que concordam que RESTful é a solução, devem ter algum argumento que não seja mero "achismo".
:seta: Quem se habilita a apontar o motivo de REST ser a solução desse caso?
Bom para mim pq seria um webservice simples e fazer em RESTful eh bem mais simples e bonito. Gostaria de saber quais APIs conhecidas como twitter, facebook, youtube, gmaps e cia usam SOAP, alguem sabe?
Bom para mim pq seria um webservice simples e fazer em RESTful eh bem mais simples e bonito. Gostaria de saber quais APIs conhecidas como twitter, facebook, youtube, gmaps e cia usam SOAP, alguem sabe?
Alguns links:
http://geeknizer.com/rest-vs-soap-using-http-choosing-the-right-webservice-protocol/
http://ajaxonomy.com/2008/xml/web-services-part-1-soap-vs-rest
http://www.devx.com/DevX/Article/8155
Esse aqui eh bom pois diz onde é melhor usar cada:
>
bem mais simples e bonito.
Bonito é uma questão pessoal, dessa forma não é um argumento válido.
Simples, bom, mapeie todas as URIs das requisições, implemente a autenticação utilizando certificados digitais ou 3 tokens e depois compare com a versão SOAP, você vai ver que não é tão simples assim.
>
Gostaria de saber quais APIs conhecidas como twitter, facebook, youtube, gmaps e cia usam SOAP, alguem sabe?
Existem várias APIs públicas, você citou apenas algumas. Posso citar algumas também:
PayPal :seta: https://cms.paypal.com/us/cgi-bin/?cmd=_render-content&content_ID=developer/e_howto_api_soap_PayPalSOAPAPIArchitecture
ECT :seta: http://www.correios.com.br/webservices/
SERASA :seta: http://www.serasaexperian.com.br
Nfe :seta: http://www.sped.fazenda.pr.gov.br/modules/conteudo/conteudo.php?conteudo=69
Sendo assim, sou obrigado a discordar do motivo que você usou para discordar.
;)
Ta e por ue o SOAP eh melhor?
Soh o trampo de criar esse WSDL eh o trampo de criar o webservice inteiro em REST, ae vai do cara neh ;D
>
Ta e por ue o SOAP eh melhor?
Quem disse que é melhor?
Veja na primeira frase do meu primeiro post que eu disse que o único erro do Igor foi dizer que era o mais correto: http://forum.imasters.com.br/topic/455759-criar-api-com-autenticacao/page__view__findpost__p__1803910
Veja também que eu disse várias vezes que nesse caso específico, REST é o mais adequado. Mas eu quero saber, daqueles que discordam da implementação SOAP, o motivo de acharem REST ser melhor, um motivo claro e direto, com foco exclusivamente técnico e que não seja baseado em "achismo".
>
:seta: Quem se habilita a apontar o motivo de REST ser a solução desse caso?
Por ser mais fácil de implementar.
Na verdade, pelo que ele descreveu sobre o que quer fazer, é algo tão simples como validar uma chave recebida e a disponibilidade do serviço pra esta chave, só fazer a comparação lógica, e dar as respostas para o serviço solicitado.
Algo que pra mim, não passaria de uma função, isso conta a usabilidade também, da pessoa que ira utilizar o serviço..
Olha a forma que você utilizou somente para chamar o serviço, temos que pensar na pessoa que vai integrar isso ao website, claro que o provedor do serviço pode oferecer exemplos de uso, mas ainda sim é meio complicado pra alguns.
>
Simples, bom, mapeie todas as URIs das requisições, implemente a autenticação utilizando certificados digitais ou 3 tokens e depois compare com a versão SOAP, você vai ver que não é tão simples assim.
Nesse caso eu colocaria um bunker no servidor, seria mais simples huauauhauha, mas João, veja bem o token só serve pra identificar quem está utilizando o serviço e que é permitido a utilizar, se esses tokens ficam em um banco de dados e é validado na hora da requisição, não tem como alguém 'driblar' isso, até mesmo porque eu duvido muito que alguém esteja preocupado em fazer isso.
Colocar o serviço a sete chaves é a mesma coisa que você colocar 3 formulários pra fazer o login no fórum, o que iria acontecer ? ninguém ia usar.
No final das contas, dependendo do serviço que ele oferece, um SOAP acaba colocando mais pedras no caminho dele, enquanto algo parecido com REST ou um REST em si, seria bem mais fácil de implementar e usar.
>
Por ser mais fácil de implementar.
Fácil é um conceito e, como tal, é relativo, lembre-se sempre disso.
>
mas ainda sim é meio complicado pra alguns.
Implemente um OAuth provider e um OAuth client e depois conversamos sobre fácil e complicado.
:P
http://www.w3.org/Submission/SA-REST/#sec_1_1
bastando ir ali no google, basta ver q o rest nao eh tao simples como muitos acham...e eh parecido com o soap
essas apis publicas do google cia, lhe disponibilizado um cliente onde você le a documentacao o, dos codigos, metodos, para poder utilizar-se deles, como um soap...pode ver q dentro deste cliente você tem o endereco do server, como no soap...
http://www.w3.org/2005/Talks/1115-hh-k-ecows/#%281%29
http://www.w3.org/2005/Talks/1115-hh-k-ecows/#%289%29
http://www.w3.org/2005/Talks/1115-hh-k-ecows/#%2810%29
Fora que ele apenas precisa consumir alguns dados, isso eh Stateless, logo REST.
Realmente o OAuth eh chatinho mesmo para implementar. Mas em casos de consumo de informações ou operações CRUD você deve criar suas rotas ja pensando no obvio e utilizando os verbos corretamente, sua api sera intuitiva.
>
Implemente um OAuth provider e um OAuth client e depois conversamos sobre fácil e complicado.
Eu não iria implementar, mas a opinião que eu dei anteriormente foi totalmente contra
>
Porque não faz algo mais simples ? quando você cadastra um cliente, gera um token aleatório pra ele, daí na hora que ele enviar a requisição para um serviço que recupere as notícias por exemplo, você procura no banco se existe um token pra esse cliente, se existir, libera o xml ..
Ele pode passar esse token através de um parâmetro na url, algo como:
http://seusite.com/service?auth={TOKEN}&service=notices
Mas, em relação a hipótese de implementar, eu concordo com o Jean :seta: http://forum.imasters.com.br/topic/455759-criar-api-com-autenticacao/page__view__findpost__p__1804009
Tá Andrey, que REST é a solução para esse caso, já falamos. O ponto que estou levantando aqui é "Porque?".
Estou fazendo essa pergunta, de certa forma agressiva, porque vejo constantemente as pessoas fazendo as coisas porque acham bonitas. Usam padrões de design só para falarem que usaram, usam uma linguagem só pra falarem que usaram, usam ferramentas, muitas vezes desnecessárias só para falarem que estão usando.
:seta: Isso é errado!
REST é a solução para esse caso por um motivo muito específico, simples até, eu só quero que alguém poste o motivo para eu poder postar a implementação REST do mesmo serviço que já está pronta aqui.
;)
>
http://www.w3.org/Su...A-REST/#sec_1_1
bastando ir ali no google, basta ver q o rest nao eh tao simples como muitos acham...e eh parecido com o soap
essas apis publicas do google cia, lhe disponibilizado um cliente onde você le a documentacao o, dos codigos, metodos, para poder utilizar-se deles, como um soap...pode ver q dentro deste cliente você tem o endereco do server, como no soap...
http://www.w3.org/20...-ecows/#%281%29
http://www.w3.org/20...-ecows/#%289%29
http://www.w3.org/20...ecows/#%2810%29
Porque não faz algo mais simples ? quando você cadastra um cliente, gera um token aleatório pra ele, daí na hora que ele enviar a requisição para um serviço que recupere as notícias por exemplo, você procura no banco se existe um token pra esse cliente, se existir, libera o xml ..
Ele pode passar esse token através de um parâmetro na url, algo como:
http://seusite.com/service?auth={TOKEN}&service=notices