if "message" is protected, how do I retrieve SOAP response called "message"? - php

I'm really stuck on this one. At the bottom of this post, I've attached the API documentation I'm working with. I want to catch the "message" when the response ("ask") isn't "Success". Seems reasonable enough, right? But when I do something like:
sfcSendError('Something went wrong. This is the message from the API: ' . $result->message);
I get a fatal error:
PHP Fatal error: Cannot access protected property SoapFault::$message
I found this seemingly related question on SO, so I tried changing "message" to "getMessage()" but (no surprise) that results in a different fatal error about calling an undefined function.
Here's my code snippet:
$client = mySoapClient(MODULE_SHIPPING_SFC_API_URL);
if (!$client) {
sfcSendError('could not make a SOAP connection. Halting until next CRON. [' . __FILE__ . ':' . __LINE__ . ']', 'SOAP Failure in cron job');
exit; //halt and wait for the next time cron runs
} else {
$HeaderRequest = array(
'customerId' => MODULE_SHIPPING_SFC_ACCOUNT,
'appToken' => MODULE_SHIPPING_SFC_TOKEN,
'appKey' => MODULE_SHIPPING_SFC_KEY
);
$reg = array(
'HeaderRequest' => $HeaderRequest,
'detailLevel' => 1,
'ordersCode' => $_query->fields['sfc_ordersCode']
);
$result = $client->getOrderByCode($reg);
if ($result->ask != "Success") {
sfcSendError('Something went wrong. This is the message from SFC: ' . $result->message, 'SOAP Failure in cron job');
$_query->MoveNext();
continue;
}
}
This is the referenced function:
function mySoapClient($url)
{
try {
$client = #new SoapClient($url, array(
'trace' => 1,
'exceptions' => 0,
'encoding' => 'UTF-8'
));
} catch (SoapFault $e) {
return 0;
}
return $client;
}
What am I doing wrong? Or is this a "bug" with the API where they really shouldn't be using "message" in their response?

Related

Arbitrage Trading of ETH/BTC using ccxt crypto API throws error while creating buy order

I am working on an app that does ETH/BTC arbitrage trading of crypto-currency using ccxt crypto API for PHP, and i keep receiving this Network Error exception thrown from the API call usually while trying to place a limit buy order.
{"status":-124,"error_message":"Enter the size in units of 0.0000001 ETH.","data":null}
This above exception is thrown from Bitflyer exchange.
My code is as follows:
$name = '\\ccxt\\'.$exchangeId;
$exchange = new $name(array (
'apiKey' => $api_key, // ←------------ replace with your keys
'secret' => $secret_key,
'enableRateLimit' => true,
));
try{
$symbol = 'ETH/BTC';
$type = 'limit'; // # or 'market', or 'Stop' or 'StopLimit'
$side = 'buy'; // 'sell' or 'buy'
$amount = $data['trade_base_amount']; //0.0515996
$price = $data['exchange_rate']; // 0.01938
// extra params and overrides
$params = array();
$response = $exchange->create_order($symbol, $type, $side, $amount, $price, $params);
print_r($response);
}catch (\ccxt\NetworkError $e) {
echo $exchange->id . ' fetch_trades failed due to a network error: '.$e->getMessage () . "\n";
}catch (\ccxt\ExchangeError $e) {
echo $exchange->id . ' fetch_trades failed due to exchange error: ' .$e->getMessage () . "\n";
}catch (\Exception $e) {
echo $exchange->id . ' fetch_trades failed with: ' . $e->getMessage () . "\n";
}
Can anyone please explain why am I getting this error?
Thanks in advance.
Try using amountToPrecision for me worked
get the documentation on CCXT

Uploaded video status via Facebook PHP Business SDK for advertisements

I'm trying to create a ad via the Facebook Business SDK. Everything works well until I'm trying to create a AdCreativeVideoData. Code:
protected function createAdVideoCreative($thumbnail_url, $video_id, $name){
$video_data = new AdCreativeVideoData();
$video_data->setData(array(
AdCreativeVideoDataFields::IMAGE_URL => $thumbnail_url,
AdCreativeVideoDataFields::VIDEO_ID => $video_id,
AdCreativeVideoDataFields::CALL_TO_ACTION => array(
'type' => AdCreativeCallToActionTypeValues::LIKE_PAGE,
'value' => array(
'page' => FbAds::PAGE_ID,
),
),
));
$object_story_spec = new AdCreativeObjectStorySpec();
$object_story_spec->setData(array(
AdCreativeObjectStorySpecFields::PAGE_ID => FbAds::PAGE_ID,
AdCreativeObjectStorySpecFields::VIDEO_DATA => $video_data,
));
$creative = new AdCreative(null, FbAds::AD_ACCOUNT_ID);
$creative->setData(array(
AdCreativeFields::NAME => $name,
AdCreativeFields::OBJECT_STORY_SPEC => $object_story_spec,
));
try {
$creative->create();
return $creative;
} catch (Exception $e) {
print("Create Ad Video Creative Exception: " . $e->getMessage() . " (" . $e->getCode() . ")");
exit;
}
}
The above method is called when the selected video is uploaded to Facebook via the following method:
protected function createAdVideo($video_path){
$video = new Advideo(null, FbAds::AD_ACCOUNT_ID);
$video->{AdVideoFields::SOURCE} = $video_path;
try {
$video->create();
return $video->{AdVideoFields::ID};
} catch (Exception $e) {
print("Create Ad Video Exception: " . $e->getMessage() . " (" . $e->getCode() . ")");
exit;
}
}
The problem is that when I'm trying to create the AdCreativeVideoData, the following error is thrown:
[message] => Invalid parameter
[type] => OAuthException
[code] => 100
[error_subcode] => 1885252
[is_transient] =>
[error_user_title] => Video not ready for use in an ad
[error_user_msg] => The video is still being processed. Please wait for the video to finish processing before using it in an ad.
[fbtrace_id] => AwW0d9+Piz1
As you can see, the video is not yet processed. My question is: how can I check the status of the video? Is there a endpoint available somewhere which I can ping to check the status? The documentation states that I can check the status, but the AdVideo object in the createAdVideo() method doesn't have a status field:
I'm at a loss here so I hope someone can shed a light on this problem. Thanks in advance!
AdVideo does not have a status field since then, but Video does: https://developers.facebook.com/docs/graph-api/reference/video
Internally it's the same id, so you can request https://graph.facebook.com/v4.0/{video-id}?fields=id,status which will return the status of the uploaded (Ad)Video.
I'll assume it is because the video is not uploaded at all.
Instead of using "source" try using "file_url". You may also want to add a parameter "title" so it will not be named untitled video- but it is not required.
And try using the SDK smarter like so:
$myVideoUpload = (new AdAccount("act_123456676"))-
>createAdVideo(
array() //fields
array( //params
"file_url"=>"http://whatever.com",
"title"=>"my title"
)
);
if this works, it'll return a json_encodes string with id=video_id.
If you want to be able to retrieve errors- if any- and a general method for all api calls, do use the graph api as such:
$fb = new Facebook(array(
"app_id"=>"blalaa",
"app_secret"=>"blaaaaa",
"default_graph_version"=>"v9.0"
));
$url = "/act_123456789/advideos";
$access_token = "my token";
$params =
array("file_url"=>"https://whatever.com","title"=>"some video");
try{
$response = $fb->post(
$url,
$params,
$access_token
)
$response = $response->getGraphNode();
} catch(FacebookResponseException $e) {
return "graph error:: " . $e->getMessage();
} catch(FacebookSDKException$e) {
return "sdk error:: " . $e->getMessage();
}
The last one can be applied to everything given that you have an access_token that has access to the specific edge that you are requesting thus only he URL needs to be changed accordingly along with the parameters.
Note:
While using the graph-api: Use POST if you want to change or create something, and GET if you only want to read.

Why is a parameter empty/broken in SoapClient::__getLastRequest() when attempting to use a Soap web service?

We are attempting to call a function OrderInteractive() defined by a wsdl at https://demo2.mvrs.com/AdrConnect/AdrConnectWebService.svc?singlewsdl. It takes two parameters, a communications block with login info, and an order block with data in it. I know the login info is correct, and we are getting a response from the service, but it gives us the default "unknown error has occurred" message. When checking the result of __getLastRequest(), we get this:
<ns1:OrderInteractive>
<ns1:inCommunications>
<Communications>
<Host>Online</Host>
<Account>xxxxx</Account>
<UserID>01</UserID>
<Password>xxxxxxxxx</Password>
<ReportTypes>
<Type>XML2.02</Type>
</ReportTypes>
</Communications>
</ns1:inCommunications>
<ns1:inOrder/>
</ns1:OrderInteractive>
If you look, the order parameter is just empty. My question is why is SOAP stripping the order block, or why is the order block empty? I also tried 2 other methods of calling the function but both result in this logged in my error log:
"The formatter threw an exception while trying to deserialize the message: Error in deserializing body of request message for operation 'OrderInteractive'. End element 'Body' from namespace 'http://schemas.xmlsoap.org/soap/envelope/' expected. Found element 'InOrder' from namespace ''. Line 2, position 185."
My code is below:
$commsBlock = "<Communications>
<Host>Online</Host>
<Account>xxxxx</Account>
<UserID>01</UserID>
<Password>xxxxxxxxx</Password>
<ReportTypes>
<Type>XML2.02</Type>
</ReportTypes>
</Communications>";
$orderBlock = "<Order>
<Handling>OL</Handling>
<Account>xxxxx</Account>
<ProductID>DL</ProductID>
<State>
<Abbrev>" . $order['state'] . "</Abbrev>
<Full></Full>
</State>
<Subtype>3Y</Subtype>
<Purpose>AA</Purpose>
<License>" . $order['dln'] . "</License>
<FirstName>" . $order['firstname'] . "</FirstName>
<MiddleName>" . $order['middlename'] . "</MiddleName>
<LastName>" . $order['lastname'] . "</LastName>
<DOB>
<Year>" . date('Y', $order['dob']) . "</Year>
<Month>" . date('m', $order['dob']) . "</Month>
<Day>" . date( 'd', $order['dob']) . "</Day>
</DOB>
<Misc>TEST ORDER INTERACTIVE</Misc>
</Order>";
$soap_url = 'https://demo2.mvrs.com/AdrConnect/AdrConnectWebService.svc?singlewsdl'; // test system url
$soap_params = array(
'trace' => true,
'exceptions' => true,
'cache_wsdl' => false
);
$_client = new SoapClient($soap_url, $soap_params);
$params = array("inCommunications" => $commsBlock, "inOrder" => $orderBlock);
// TRY TO SEND
try {
$_client->OrderInteractive($params); // works, but sends broken order node
//$_client->__soapCall('OrderInteractive', $params); // breaks, goes to catch
//$_client->OrderInteractive(new SoapParam($commsBlock, 'InCommunications'), new SoapParam($orderBlock, 'InOrder')); // breaks, goes to catch
} catch(SoapFault $e) {
capDebug(__FILE__, __LINE__, "Error: SoapFault:\n" . $e->getMessage(), '/tmp/SOAP_errors.log');
}
class inOrder {
function inOrder($xml) {
$this->OrderXml = $xml;
}
}
$xml_order = '<Order>
<Handling>OL</Handling>
<ProductID>DL</ProductID>
.
.
.
<Misc>TEST ORDER INTERACTIVE</Misc></Order>';
// create our order object that is needed
$order = new inOrder($xml_order);
// create our OrderInteractive parameters
$parameters = array(
"inCommunications" => $xml_communication,
"inOrder" => $order
);
try {
$xml = $_client->OrderInteractive($parameters);
} catch (Exception $e) {
print $e->getMessage() . "\n"; exit();
}
The code above worked. WSDL expecting a string and an object as params. Created a class for the order and used a string for the communications block, and we are receiving data fine.

Codeigniter SOAP Server Error - Reserved XML - already tried trim

I am working on this legacy system that needs to maintain its SOAP service, and I am currently trying to integrate it with codeigniter, keeps giving me an error XML error parsing SOAP payload on line 70: Reserved XML Name. I have tried the trim solution that someone mention and that did not work. It does not give me this error with normal arrays. Only multidimensional arrays. Any advice would be appreviated
<?php
class Employee_Trainings_Soap extends MY_Controller {
public function __construct() {
parent::__construct();
$this->load->library("Soap_lib");
$this->nusoap_server = new soap_server();
}
public function employee_detail() {
$namespace = 'http://localhost/employee_trainings_soap/employee_detail?wsdl';
$this->nusoap_server->debug_flag = true;
$this->nusoap_server->configureWSDL('EmployeeTrainings', $namespace);
$this->nusoap_server->wsdl->schemaTargetNamespace = $namespace;
$this->nusoap_server->wsdl->addComplexType('response', 'complexType', 'struct', 'all', '', array(
"validOPIN" => array(
"name" => "valid_OPIN",
"type" => "xsd:string"
),
"message" => array(
"name" => "message",
"type" => "xsd:string"
)
));
$this->nusoap_server->wsdl->addComplexType('responses', 'complexType', 'array', '', 'SOAP-ENC:Array', array(), array(
array(
"ref" => "SOAP-ENC:arrayType",
"wsdl:arrayType" => "tns:response[]"
)),
"tns:response"
);
$this->nusoap_server->register('getEmployeeTrainings', array("id" => "xsd:string"), array('test'=>'tns:responses'),
$namespace, $namespace."#getEmployeeTrainings", "rpc", "encoded",
'Use this service to list notaries connected to the signed-in title company.'
);
function getEmployeeTrainings($id) {
$data = array();
$data[] = array('valid_OPIN'=>'test','message'=>'test2');
$data[] = array('valid_OPIN'=>'test','message'=>'test2');
//$data = array('valid_OPIN'=>'test','message'=>'test2');
return array('test'=>$data);
}
$POST_DATA = isset($GLOBALS['HTTP_RAW_POST_DATA']) ? $GLOBALS['HTTP_RAW_POST_DATA'] : '';
$this->nusoap_server->service($POST_DATA);
}
function live_client_test() {
$this->soapclient = new nusoap_client('http://localhost/employee_trainings_soap/employee_detail');
$err = $this->soapclient->getError();
if ($err) {
echo '<h2>Constructor error</h2><pre>' . $err . '</pre>';
}
$result = $this->soapclient->call('getEmployeeTrainings', array('id' => 'test'));
if ($this->soapclient->fault) {
echo '<h2>Fault</h2><pre>';
print_r($result);
echo '</pre>';
} else {
$err = $this->soapclient->getError();
if ($err) {
echo '<h2>Error</h2><pre>' . $err . '</pre>';
} else {
// Display the result
echo '<h2>Result</h2><pre>';
print_r($result);
echo '</pre>';
}
}
}
}
So I have found the issue, this may not be the only solution, it is the solution that we found that worked for us. We had to take the SOAP Service out of Code Igniter for it to work. The moment that we took the service outside of Code Igniter, it worked. This may be a bug with code igniter or it could have been with the way we were using it, but as a quick solution it worked. Additionally, we also found it worked better on a Linux dev box compared to an XAMPP dev box. I hope this helps anyone else that might have the same issue.

unable to receive xml response from SOAP web service using CRON

I have a function which handles the SOAP based web service.
When I run the function via URL I am getting XML response. but when I run the function through CRON I am not getting xml response.
<?php
$logFile = 'checking'.date('Y-m-d').'.log';
$client = new SoapClient("http://DOMAIN/services/weburl?wsdl",array( "trace" => true, 'use' => SOAP_LITERAL));
$params = array('username' => 'username', 'Password' => 'password', 'delatdate' => '17/06/2015 18:00:00');
try{
$response = $client>-productOnHand($params);
} catch(SoapFault $e){
echo $e->faultcode; echo '<br />';
echo $e->getMessage(); echo '<br />';
}
require_once 'app/Mage.php';
Mage::app();
Mage::log(print_r($response, true), null, $logFile);
Mage::log(print_r($client->__getLastResponse(), true), null, $logFile);
?>
If I run this web page via URL I am getting valid xml response. But when this page is being called through CRON I am not getting valid response.
I fixed this issue.
Before default_socket_timeout was set as 60. I raised it as 600. Now I could able to receive.

Categories