Curl PHP GET request - 504 - php

I'm trying to do a curl php get request to display some json data on page.
The issue that I'm having here is that I keep getting hit with a 504 gateway timeout.
So I was hopping to get a second pair of eyes on my code to make sure I'm not doing anything silly or missing something.
// get request
$ch = curl_init('http://*****');
$token = '****';
// Return Data
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLINFO_HEADER_OUT, true);
//User Agent
curl_setopt($ch, CURLOPT_USERAGENT, 'Fiddler');
//Set your auth headers
curl_setopt($ch, CURLOPT_HTTPHEADER, array(
'Host: ****:8090',
'Content-Type: application/json',
'Authorization: Bearer '.$token
));
$data = curl_exec($ch);
$info = curl_getinfo($ch);
// print details of request on page
echo 'info:' . $info ;
// close curl resource to free up system resources
curl_close($ch);

Issue was that the host's firewalls were blocking requests to certain ports and I had to get them to unblock the ports in order for it to work.

You have an error in headers, Host must contain only the hostname Host: *****:8090.
It must be like this one : Host: google.com.
The port must be specified using curl_setopt (), like this:
curl_setopt($ch, CURLOPT_PORT, 8090);

Related

Unable to access Flask web app from php curl

I have a Flask app, with a basic function, where I have exposed app.run() to a public ip, so that it is accessible from an external server;[ using Flask - Externally Visible Dev Server ]
#app.route('/')
def hello_world():
return 'Hello World!'
if __name__ == '__main__':
app.run(host = '0.0.0.0', port = 8080)
The curl request I have written in my php code is:
$signed_url = "http://my-ip-address:8080/";
$ch = curl_init($signed_url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_HEADER, 0);
$data= curl_exec($ch);
echo $data;
I can do a curl request :
curl http://my-ip-address:8080/
from command line. However, when the curl request is embedded within my PHP code, it gives me an error "Connection refused".
Kindly help!
If the PHP code is on another server, but your command line cURL request is on the same server, then you aren't comparing apples to apples.
Two things that might be wrong:
Your Flask server has a firewall that doesn't allow external connections.
You are connecting using an private network IP address rather than a public IP address.
For now your PHP code looks correct, so I would narrow down the problem a little bit. Ignore that PHP code and try to connect using cURL on the command line from the same server you are running your PHP code on.
try to set your port with curl options like this:
curl_setopt($ch, CURLOPT_PORT, 8080);
so your signed url will be:
$signed_url = "http://my-ip-address";
I use this code for my work and worked :)
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'http://localhost:5000/spmi/api/1');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, "{\"teks_analysis\":\"tidak ada skor nol\"}");
curl_setopt($ch, CURLOPT_POST, 1);
$headers = array();
$headers[] = 'Content-Type: application/json';
curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);
$result = curl_exec($ch);
if (curl_errno($ch)) {
echo 'Error:' . curl_error($ch);
}
curl_close($ch);
the key is CURLOPT_POSTFIELDS

Auth lost when doing a curl request to my laravel server

I'm trying to make a curl request to my laravel server, in that request I have to check whether the user of my laravel application is logged in or not. I use this code:
$transferAmount = 200;
//set POST variables
$url = URL::route('post-spend-partner');
$fields = array(
'transferAmount' => urlencode($transferAmount),
'cancelUrl' => urlencode(URL::route('get-return-page-example')),
'returnUrl' => urlencode(URL::route('get-return-page-example')),
);
// New Connection
$ch = curl_init();
curl_setopt($ch, CURLOPT_HEADER, 0);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 0);
curl_setopt($ch, CURLOPT_COOKIESESSION, true);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, $fields);
curl_setopt($ch, CURLOPT_URL, $url);
curl_exec($ch);
curl_close($ch);
In the requested url I'm just checking if I'm logged in or not, but it always returns false:
public function postSpendPartner() {
echo "Authenticated? " . (Auth::check() ? 'Yes' : 'No');
}
I know for sure that I'm logged in, if I try the exact same thing with Ajax it completely works!
Does anyone know what I could try, to solve this problem?
Best regards!
Fabrice
Some facts: HTTP is stateless. Session IDs need to be passed to the server in order to continue the session. Session IDs are (most of the time) stored in cookies. Cookies are included in the request.
Using a cookiejar could indeed be one possible solution. The fact that it works using Ajax, and not by re-submitting the request from your server might be because of the session-verification mechanism on the server: Some session implementations lock session IDs to the initial IP address. If the contents of your cookiejar file check out, that might be the culprit.
That aside: re-submitting the request via Curl from your server is a severe codesmell to me. A proper solution would to implement something such as OAuth.
Try sending your cookies as a header with your curl request.
// ...
$cookie_header = "Cookie:";
$headers = [];
foreach($_COOKIE as $key => $val) {
// Do sanitize cookie values
$cookie_header .= " ".$key."=".$value.";";
}
$headers[] = $cookie_header;
curl_setopt($curl, CURLOPT_HTTPHEADER, $headers);
// ...
You could filter out unnecessary cookie values from $cookie_header.

Android Push Notification unauthorized error 401

I have created an Android app with Googles' OAuth 2.0 (from developer console) and has an API key for Android application (it use Google Maps, which works by the way).
However, my problem is that I'm using Push Notifications and it works on the android application though (I get the registration ID), but on the server it doesn't work at all.
I'm using PHP and the problem seems to be the API key which is the same as the one I've for the Android application.
So what key am I supposed to use? And how do I retrieve it?
Code:
<?php
function send_push_notification($registatoin_ids, $message) {
// Set POST variables
$url = 'https://android.googleapis.com/gcm/send';
$fields = array(
'registration_ids' => $registatoin_ids,
'data' => $message,
);
$headers = array(
'Authorization: key=An_Api_Key',
'Content-Type: application/json'
);
//print_r($headers);
// Open connection
$ch = curl_init();
// Set the url, number of POST vars, POST data
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
// Disabling SSL Certificate support temporarly
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($fields));
// Execute post
$result = curl_exec($ch);
if ($result === FALSE) {
die('Curl failed: ' . curl_error($ch));
}
// Close connection
curl_close($ch);
echo $result;
}?>
Please check allowed IP addresses in your Google API. You can restrict API access to certain IP addresses and by default one IP address is set when you create new API project.
Remove that IP address so that any IP address (Including your local machine's server) can connect and access the API.
I have implemented similar kind of code and got 401 error. Above fix worked for me. Hope that helps you as well.

Use GCM with PHP

I've seen several posts about how to send GCM messages from my PHP server, but I can't get it working. This is my code:
public function test_gcm($id_user){
// Search user's RegIds and stores them in $regids
if(count($regids) == 0){
echo "This user has no registered device.";
return;
}
$ch = curl_init();
$data = array(
'data' => array('message'=>'my message', 'title'=>'message title'),
'registration_ids' => $regids
);
curl_setopt($ch, CURLOPT_URL, 'https://android.googleapis.com/gcm/send');
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($data));
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
// WRITE JSON HEADERS
curl_setopt($ch, CURLOPT_HTTPHEADER, array(
'Content-Type: application/json',
'Authorization:key=' . $apiKey)
);
curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, false);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
$result = curl_exec($ch);
curl_close($ch);
echo $result;
}
I'm using the browser key. I tried the server key too, but none of them work, the curl_exec always return false. Does anybody know why is it?
EDIT: I just used 'netstat -tuanc | grep 173' on my server and performed the server call. I'm using grep 173 because if I ping android.googleapis.com I ping this ip address. The netstat didn't show any connection to that ip address when I use the curl_exec. Does that mean I'm not connecting to android.googleapis.com? Or what I'm doing is wrong?
Thanks!
Check the "message" content are same or not in android code. 'message'=>'my message' should match with the message from IntentService class in android.
I've managed to fix it. It was a firewall issue, my firewall was blocking the connection. I've added the rules to accept these messages and now it works.
Thanks to all the people that tried to help :)
Try to change it from https to http
curl_setopt($ch, CURLOPT_URL, 'https://android.googleapis.com/gcm/send');
to
curl_setopt($ch, CURLOPT_URL, 'http://android.googleapis.com/gcm/send');
try this http://2mecode.blogspot.hk/2013/01/google-cloud-messaging-php.html
hope it can help you

Getting content body from http post using php CURL

I am trying to debug an http post the I am trying to send from list application. I have been able to send the correct post from php CURL which corectly interfaces with my drupal 7 website and uploads an image.
In order to get this to work in my lisp application I really need to see the content body of my http post I have been able to see the headers using a call like this:
curl_setopt($curl, CURLOPT_STDERR, $fp);
curl_setopt($curl, CURLOPT_VERBOSE, 1);
and the headers look the same in my lisp application but I have been unable to examine the body of the post. I have searched online and other people have asked this question but no one posted a response.
The content type of my http post is:
application/x-www-form-urlencoded
I have also tried many http proxy debuging tools but they only ever the http GET to get my php page but never capture the get sent from server once the php code is executed.
EDIT: I have added a code snipet showing where I actually upload the image file.
// file
$file = array(
'filesize' => filesize($filename),
'filename' => basename($filename),
'file' => base64_encode(file_get_contents($filename)),
'uid' => $logged_user->user->uid,
);
$file = http_build_query($file);
// REST Server URL for file upload
$request_url = $services_url . '/file';
// cURL
$curl = curl_init($request_url);
curl_setopt($curl, CURLOPT_HTTPHEADER, array('Content-type: application/x-www-form-urlencoded'));
curl_setopt($curl, CURLOPT_STDERR, $fp);
curl_setopt($curl, CURLOPT_VERBOSE, 1);
curl_setopt($curl, CURLOPT_POST, 1); // Do a regular HTTP POST
curl_setopt($curl, CURLOPT_POSTFIELDS, $file); // Set POST data
curl_setopt($curl, CURLOPT_HEADER, FALSE); // Ask to not return Header
curl_setopt($curl, CURLOPT_COOKIE, "$cookie_session"); // use the previously saved session
curl_setopt($curl, CURLOPT_RETURNTRANSFER, TRUE);
curl_setopt($curl, CURLOPT_FAILONERROR, TRUE);
curl_setopt_array($curl, array(CURLINFO_HEADER_OUT => true) );
$response = curl_exec($curl);
CURLOPT_VERBOSE should actually show the details. If you're looking for the response body content, you can also use CURLOPT_RETURNTRANSFER, curl_exec() will then return the response body.
If you need to inspect the request body, CURLOPT_VERBOSE should give that to you but I'm not totally sure.
In any case, a good network sniffer should give you all the details transparently.
Example:
$curlOptions = array(
CURLOPT_RETURNTRANSFER => TRUE,
CURLOPT_FOLLOWLOCATION => TRUE,
CURLOPT_VERBOSE => TRUE,
CURLOPT_STDERR => $verbose = fopen('php://temp', 'rw+'),
CURLOPT_FILETIME => TRUE,
);
$url = "http://stackoverflow.com/questions/tagged/java";
$handle = curl_init($url);
curl_setopt_array($handle, $curlOptions);
$content = curl_exec($handle);
echo "Verbose information:\n", !rewind($verbose), stream_get_contents($verbose), "\n";
curl_close($handle);
echo $content;
Output:
Verbose information:
* About to connect() to stackoverflow.com port 80 (#0)
* Trying 64.34.119.12...
* connected
* Connected to stackoverflow.com (64.34.119.12) port 80 (#0)
> GET /questions/tagged/java HTTP/1.1
Host: stackoverflow.com
Accept: */*
< HTTP/1.1 200 OK
< Cache-Control: private
< Content-Type: text/html; charset=utf-8
< Date: Wed, 14 Mar 2012 19:27:53 GMT
< Content-Length: 59110
<
* Connection #0 to host stackoverflow.com left intact
<!DOCTYPE html>
<html>
<head>
<title>Newest 'java' Questions - Stack Overflow</title>
<link rel="shortcut icon" href="http://cdn.sstatic.net/stackoverflow/img/favicon.ico">
<link rel="apple-touch-icon" href="http://cdn.sstatic.net/stackoverflow/img/apple-touch-icon.png">
<link rel="search" type="application/opensearchdescription+xml" title="Stack Overflow" href="/opensearch.xml">
...
Just send it to a random local port and listen on it.
# terminal 1
nc -l localhost 12345
# terminal 2
php -e
<?php
$curl = curl_init('http://localhost:12345');
// etc
If you're talking about viewing the response, if you add curl_setopt( $curl, CURLOPT_RETURNTRANSFER, true );, then the document returned by the request should be returned from your call to curl_exec.
If you're talking about viewing the postdata you are sending, well, you should be able to view that anyway since you're setting that in your PHP.
EDIT: Posting a file, eh? What is the content of $file? I'm guessing probably a call to file_get_contents()?
Try something like this:
$postdata = array( 'upload' => '#/path/to/upload/file.ext' );
curl_setopt( $curl, CURLOPT_POSTFIELDS, $postdata );
You can't just send the file, you still need a postdata array that assigns a key to that file (so you can access in PHP as $_FILES['upload']). Also, the # tells cURL to load the contents of the specified file and send that instead of the string.
You were close:
The PHP manual instructs that you must call the constant CURLINFO_HEADER_OUT in both curl_setopt and curl_getinfo.
$ch = curl_init($url);
... other curl options ...
curl_setopt($ch,CURLINFO_HEADER_OUT,true);
curl_exec(ch);
//Call curl_getinfo(*args) after curl_exec(*args) otherwise the output will be NULL.
$header_info = curl_getinfo($ch,CURLINFO_HEADER_OUT); //Where $header_info contains the HTTP Request information
Synopsis
Set curl_setopt
Set curl_getinfo
Call curl_getinfo after curl_exec
I think you're better off doing this with a proxy than in the PHP. I don't think it's possible to pull the raw POST data from the PHP CURL library.
A proxy should show you the request and response contents
To get the header the CURLINFO_HEADER_OUT flag needs to be set before curl_exec is called.
Then use curl_getinfo with the same flag to get the header after curl_exec.
If you want to see the post data, grab the value you set at CURLOPT_POSTFIELDS
For example:
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, "http://example.com/webservice");
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($payload));
curl_setopt($ch, CURLINFO_HEADER_OUT, true);
curl_exec($ch);
$header = curl_getinfo($ch, CURLINFO_HEADER_OUT);
curl_close($ch);
echo "Request-Header:\r\n" . $header . "\r\n";
echo "Request-Body(URL Encoded):\r\n" . http_build_query($payload) . "\r\n";
echo "Request-Body(Json Encoded):\r\n" . json_encode($payload) . "\r\n";

Categories