I am trying to get a soap response in php. It keeps coming as an object onto my web browser but not as xml. WSDL shows as XML but not the response received. Below is my server side code. The soap server is Zend Soap
ini_set("soap.wsdl_cache_enabled", 0);
if (isset($_GET['wsdl'])){
$wsdl = 'http://localhost/webservice/soap';
$autoDiscover = new AutoDiscover();
$autoDiscover->setOperationBodyStyle(
array('use' => 'literal',
'namespace' => 'http://localhost/webservice/soap')
);
$autoDiscover->setBindingStyle(
array('style' => 'rpc',
'transport' => 'http://schemas.xmlsoap.org/soap/http')
);
$autoDiscover->setComplexTypeStrategy(new ArrayOfTypeComplex());
// $service is the class that does the handling of functions
$autoDiscover->setClass($service);
$autoDiscover->setUri($wsdl);
$response->getHeaders()->addHeaderLine('Content-Type', 'text/xml');
$response->setContent($autoDiscover->toXml());
} else {
$server = new Server('http://localhost/webservice/soap?wsdl'
);
// $service is the class that does the handling of functions
$server->setObject($service);
$response->setContent($server->handle());
}
return $response;
}
Service class
class service
{
/**
*
* #param string $Email
* #return int $Credit
*/
public function checkCredits($Email)
{
$validator = new email();
if (!$validator->isValid($Email))
{
return new \SoapFault('5', 'Please Provide an Email');
}
$rowset = $this->tableGateway->select(array('EMAIL'=>$Email))
$row = $rowset->current();
$credits = $row->CREDITS;
return $credits;
}
}
Request is :
try{
$sClient = new SoapClient('http://localhost/webservice/soap?wsdl');
$params = "email";
$response = $sClient->checkCredits($params);
var_dump($response);
} catch(SoapFault $e){
var_dump($e);
}
This is an example of how I handle my functions with SoapClient:
$client = new SoapClient('http://url/Service.svc?wsdl');
$var = array('arg' => 10,
'VA' => 48);
$varresponse = $client->Function($var);
print_r( $varresponse->FunctionResult);
Hope this will help you out.
Your soapserver should look a bit like this:
<?php
if(!extension_loaded("soap")){
dl("php_soap.dll");
}
ini_set("soap.wsdl_cache_enabled","0");
$server = new SoapServer("hello.wsdl");
function doHello($yourName){
return "Hello, ".$yourName;
}
$server->AddFunction("doHello");
$server->handle();
?>
How did you set up yours? Do you return anything?
Now, your client should look like this:
<?php
try{
$sClient = new SoapClient('http://localhost/test/wsdl/hello.xml');
$params = "Name";
$response = $sClient->doHello($params);
var_dump($response);
} catch(SoapFault $e){
var_dump($e);
}
?>
Related
I am brand new to PSR standards, and I am not sure if I adapted my code to PSR-7, PSR-15 correctly.
My code is handling a POST request to delete a group of products by receiving an array of ids.
Is that a correct adaptation? Thanks.
<?php
require_once 'DataBase.php';
require_once 'config.php';
use Psr\Http\Server\RequestHandlerInterface;
use Psr\Http\Message\ServerRequestInterface;
use Psr\Http\Message\ResponseInterface;
class DeleteRequest implements RequestHandlerInterface
{
private $DB;
public function __construct(DataBase $DB)
{
$this->DB = $DB;
}
//Delete each product from the database using the ID
public function handle(ServerRequestInterface $request): ResponseInterface
{
// Make sure it is a POST request
if ($request->getMethod() !== 'POST') {
throw new Exception('Incorrect REQUEST_METHOD. '.
'Only POST requests are allowed.');
}
// Extract the 'ids' array from the request data
MyLogV($request->getBody()->getContents());
$data = json_decode($request->getBody()->getContents(), true);
// Make sure the 'ids' array is present in the data
if (!isset($data['ids'])) {
throw new Exception('Missing required parameter: ids');
}
$ids = $data['ids'];
foreach ($ids as $id) {
myLog("DeleteRequest->handle","id",$id);
$result = $this->DB->deleteProduct($id);
if ($result['status'] != 'success') break;
}
// Generate the response: 200 => OK, 400 => Bad request
$status = $result['status'] == 'success' ? 200 : 400;
$response = new JsonResponse($result, $status);
myLogV($result['status']);
return $response;
}
}
try {
$serverRequest = ServerRequestFactory::fromGlobals();
$DB = new DataBase();
$deleteRequest = new DeleteRequest($DB);
$response = $deleteRequest->handle($serverRequest);
$response->send();
} catch (Exception $e) {
myLog("delete.php","Exception",$e->getMessage());
$result = ['status' => 'error','message'=> $e->getMessage()];
$response = new JsonResponse($result, 400);
$response->send();
}
exit();
?>
I tried to understand the PSR standards.
I am using cakephp 2.10.24. I need to use the variable returned from the controller in a php file(not a view), so I used the dispatch function to make a Cakephp request. The data is displayed by itself and I'm not able to execute some code after the dispatch call.
I tried adding to the controller but it didn't work
$this->autoRender = false;
$this->layout = false;
$this->autoLayout = false;
the controller action:
$this->autoRender = false;
$this->layout = false;
$this->autoLayout = false;
$this->response->body(json_encode(array(
'key' => 0,
'message' => 'Invalid request.'
)));
$this->response->send();
$this->_stop();
php file:
<?php
echo ('i\'m test file <br />');
include 'app/webroot/index.php';
$request = new CakeRequest('/controller/action/param');
$response = new CakeResponse(array('type' => 'application/json'));
echo $results = $Dispatcher->dispatch(
$request ,
$response,
array('return' => 'vars')
);
//some codes not running
var_dump($response);
print_r(json_decode($response));
?>
Got the results but still auto printing the result on the screen.
test file:
$dispatcher = new Dispatcher();
$response = new CakeResponse();
$results = $dispatcher->dispatch(new CakeRequest('/Controlller/Action/params'),$response);
print_r("response: ".$response);
action in the controller:
$this->autoRender=false;
$this->autoLayout=false;
$this->response->body($result);
$this->response->send();
I have 'sendsms' function which i used it in one of my controllers and worked fine. now what i need to know how i can make class reference of this code to use it in other controllers, instead of copy/paste whole code in all controllers.
In other Q/A they mentioned about only creating reference but i wanted to do it properly like using constructor or etc, not just doing things work, i want to do it like real-world project.
Here's the code in controller :
public function store(Request $request)
{
$this->validate($request,[
'title' => 'required|string|min:6',
'gametype' => 'required|string|min:3',
'description' => 'required|string|min:1|max:180',
'price' => 'required|numeric|min:4',
'buyyer_id' => 'required|numeric|min:1'
// 'seller_id' => 'required|numeric|min:1'
]);
// return RequestModel::create([
// 'title' => $request['title'],
// 'description' => $request['description'],
// 'gametype' => $request['gametype'],
// 'price' => $request['price'],
// 'buyyer_id' => $request['buyyer_id'],
// 'seller_id' => Auth::user()->id,
// ]);
//
$requestModel = new RequestModel;
// store
$requestModel->title = $request['title'];
$requestModel->description = $request['description'];
$requestModel->gametype = $request['gametype'];
$requestModel->price = $request['price'];
$requestModel->buyyer_id = $request['buyyer_id'];
$requestModel->seller_id = Auth::user()->id;
$requestModel->save();
return $this->sendSms($request['title'], $request['gametype']);
}
// I want to use this code in another class to use it in all controllers without copy/paste it.
function sendSms($reqid, $recgametype) {
//Send sms to getway
//implement later.
$otp_prefix = ':';
$response_type = 'json';
$textMSGATLAS = iconv("UTF-8", 'UTF-8//TRANSLIT',"req : ( " .$reqid. " ) for ( " .$recgametype. " ) submitted ");
ini_set("soap.wsdl_cache_enabled", "0");
try {
$client = new SoapClient("http://xxxx");
$user = "user";
$pass = "pass";
$fromNum = "+xxx";
$toNum = "+xxxx";
$messageContent = $textMSGATLAS;
$op = "send";
$client->SendSMS($fromNum,$toNum,$messageContent,$user,$pass,$op);
} catch (SoapFault $ex) {
echo $ex->faultstring;
}
}
I'm right now learning and I'm beginner at this so help to understand how to make it work properly. Thanks.
You can create a separate SMS class like :
<?php
namespace App;
class SMS {
private $reqid;
private $recgametype;
public function __construct($reqid, $recgametype)
{
$this->reqid = $reqid;
$this->recgametype = $recgametype;
}
public function send()
{
$otp_prefix = ':';
$response_type = 'json';
$textMSGATLAS = iconv("UTF-8", 'UTF-8//TRANSLIT',"req : ( " .$this->reqid. " ) for ( " .$this->recgametype. " ) submitted ");
ini_set("soap.wsdl_cache_enabled", "0");
try {
$client = new SoapClient("http://xxxx");
$user = "user";
$pass = "pass";
$fromNum = "+xxx";
$toNum = "+xxxx";
$messageContent = $textMSGATLAS;
$op = "send";
return $client->SendSMS($fromNum,$toNum,$messageContent,$user,$pass,$op);
} catch (SoapFault $ex) {
throw new \Exception('SMS sending failed')
}
}
}
And then inside controller or wherever you would need :
public function sendSms($reqid, $recgametype) {
$sms = new \App\SMS($reqid, $recgametype);
$sms->send();
}
You can also create custom exception like SMSSendingFailedException and throw it instead of standard \Exception inside send() function.
That will help you to send appropriate response in controller like :
public function sendSms($reqid, $recgametype) {
try{
$sms = new \App\SMS($reqid, $recgametype);
$sms->send();
return response()->json('message' => 'SMS sent successfully', 200);
}
catch(SMSSendingFailedException $e){
return response()->json('message' => 'SMS sending failed', 500);
}
}
Then to go one step further, you can use concept of laravel facade if you need it all over the project with a quick class alias.
I am developing rest web services using zend 2.
For error handling I am using below mentioned code in Module.php
public function onBootstrap(MvcEvent $e)
{
$eventManager = $e->getApplication()->getEventManager();
$moduleRouteListener = new ModuleRouteListener();
$moduleRouteListener->attach($eventManager);
$eventManager->attach(MvcEvent::EVENT_DISPATCH_ERROR, array(
$this,
'onDispatchError'
), 0);
$eventManager->attach(MvcEvent::EVENT_RENDER_ERROR, array(
$this,
'onRenderError'
), 0);
}
public function onDispatchError($e)
{
return $this->getJsonModelError($e);
}
public function onRenderError($e)
{
return $this->getJsonModelError($e);
}
/*
* Manages error's and return response_code and error message
*
* #return Zend\View\Model\JsonModel
*/
public function getJsonModelError($e)
{
$error = $e->getError();
if (! $error) {
return;
}
$response = $e->getResponse();
$sm = StaticServiceManager::getDefaultServiceManager();
$config = $sm->get('config');
$err_code = $response->getStatusCode();
$err_msg = $response->getReasonPhrase();
$response_code = $config['HTTP_ERROR'][$err_code]['response_code'];
$errorJson = array(
'response_code' => $response_code,
// 'status' => $err_code,
'message' => $err_msg
);
$model = new JsonModel($errorJson);
$e->setResult($model);
return $model;
}
However there are still cases which are not tracked by this approach. For e.g. Invalid HTTP method passed. Does there any way I can check final response and manipulate it e.g. I can check final response content-type & http status code to finally change the response to send some meaning full json message.
im working with magento api, and i need verify my connect.
how to call method APIauthentication with $client object? because im getting error on this: Error: Function ("APIauthentication") is not a valid method for this service
thanks for the help.
this is my class:
<?php
class Magento {
const PRODUCTS_LIST = 'catalog_product.list';
public function Verify( $data )
{
$client = new SoapClient( $data['store_url'] );
$verify = $client->APIauthentication( $data['api_user'], $data['api_key'] );
if ($verify)
{
return $this->Register( $data['store_url'], $data['api_user'], $data['api_key'] );
}
}
public function APIauthentication( $apiUser, $apiKey ) {
$client = $this->_getClient();
$token = $client->login( $apiUser, $apiKey );
$this->_setToken( $token );
return $this->_apiJsonResult( $token );
}
}
there is url:
$data['store_url'] = 'http://localhost:8888/magento/api/soap/?wsdl';
firstly i need verify, second - get list:
// For products
public function getProducts()
{
return $client->APIgetProductsList();
}
/*
* Get product list
*/
public function APIgetProductsList() {
$token = $this->_getToken();
$client = $this->_getClient();
$products = $client->call($token, self::PRODUCTS_LIST );
return $this->_apiJsonResult( $products );
}
You need to create your own api by creating new module then you can use that api method refer this link http://www.magentocommerce.com/wiki/5_-_modules_and_development/web_services/custom_api_complete_example