Wordpress wp_remote_post - php

I want to use wp_remote_post to send information from one server to my other website.
So basically, I have added this line to my code -
$sidebarHTTP = site_url(); // Retrieves HTTP Url of sidebar
$sidebarActivation = $sidebar.' , '.$sidebarHTTP; // Activate Sidebar
$args = array(
'method' => 'post',
'body' => array('sidebar' => $sidebar, 'sidebarHTTP' => $sidebarHTTP),
'user-agent' => 'My site'
);
wp_remote_post( 'http://mysite.com', $args ); // Loads all default data
So basically, it doesn't send anything. Yes, I have correct domain entered. Maybe it does send something, but I don't know how can I retrieve the $args['body'] from that site. Also, I tried adding $response = wp_remote_post.... and then sending mail $response['body'], but it just sends source code of homepage to email.
Would appreciate help.

You will need to enable cURL in your php.ini file.
wp_remote_post() uses a class called WP_Http that in turn can use one of three transport classes (see file class-http.php function _get_first_available_transport).
POST method will work with class WP_Http_Curl, but will not work with class WP_Http_Streams (the cURL fallback).
The alternative is to use wp_remote_get()

Related

Submit Sitemap With PHP

I have been tyring to get this api working for literally hours. I can't even get the try this api part working with api key. I tried to use it with cURL like this:
$submitSite = curl_init($submit_url);
curl_setopt_array($submitSite, [CURLOPT_PUT => true,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HTTPHEADER => ["Accept: application/json"]]);
$responseContent = curl_exec($submitSite);
But it returns 0. I url encoded siteUrl and feedpath parts and added the api key at the end. How can I submit my website's sitemap automatically?
You're missing the authorization part. You must have the proper permissions to https://www.googleapis.com/auth/webmasters to add the sitemap.
In your code I don't see any headers for this authorization.
For more info check: https://developers.google.com/webmaster-tools/search-console-api-original/v3/how-tos/authorizing

Authenticate with Wordpress cookie through API from a subdomain

I want to access the current logged in Wordpress user in a separate Laravel installation.
Wordpress is running as website.com and I've got a subdomain with tool.website.com with the Laravel application (on another server but same domain).
I'm using the Native Wordpress API and created an authentication route.
The issue:
When I access the /authenticate route directly, the user ID is returned and works correctly. But when I access the route through tool.website.com false is returned..
Things I've got working:
I've created an API request which returns the user id in an API call:
add_action( 'rest_api_init', function () {
register_rest_route( '/authenticate', array(
'methods' => 'GET',
'callback' => 'authenticate',
) );
} );
The function looks like this:
$user_id = wp_validate_auth_cookie( $_COOKIE[LOGGED_IN_COOKIE], 'logged_in' );
The WP cookie is available on both the sub / main domain. I can see they are identical and toplevel.
define('COOKIE_DOMAIN', '.website.dev');
Things I've tried:
Using wp_get_current_user() to retrieve the user, this seems to need a nonce. I experimented hours and hours with the nonce approach on many different ways, but I could not get this to work (false or 0 was returned). I understand this is due to restrictions of using a nonce from outside of Wordpress.
Using the default native API approach to get the user, also needs the nonce.
Reading the https://developer.wordpress.org/rest-api/ manual, git repository & several articles / comments online.
Thinking about the OAuth approach, but I do not want users to login again as they are already logged in when they reach the tool.
Sending stuff like posts etc works without problems, so the API connection is not the problem.
I'm wondering if my approach is in the right direction. Hopefully someone can give me some guidance.
I found the following workaround:
- tool.website.com
Send the Cookies from tool.website.com to the API as post data.
$cookie_array = $_COOKIE;
// use key 'http' even if you send the request to https://...
$options = array(
'http' => array(
'header' => "Content-type: application/x-www-form-urlencoded\r\n",
'method' => 'POST',
'content' => http_build_query($cookie_array)
)
);
$context = stream_context_create($options);
$data = file_get_contents(self::BASE_URL . "authenticate", false, $context);
- website.com
Retrieve the cookie from Post data, and use the standard LOGGED_IN_COOKIE constant in Wordpress to select the correct one (this can be refactored to sending the correct cookie at once).
// We retrieve the cookie (which is sadly not available through the API call alone)
$the_cookie = $request->get_body_params();
// As the cookie lives at domain level, we can use the same Cookie key in the WP API and other subdomains of this domain
// The cookie key remains the same
$user_id = wp_validate_auth_cookie( $the_cookie[LOGGED_IN_COOKIE], 'logged_in' );
This solution seems steady; hopefully it will help someone. If there are other solutions, please add them in this topic; as I'm sure there must be different ways achieving this.

wp_remote_get() request failed when requested from certain server

I'm creating a WordPress plugin for my client using WP REST API V2,
and i got a problem with the wp_remote_get() function,
My wp_remote_get() always return "http_request_failed" when I send the get request to the server from the client-side plugin,
BUT its weirdly works well when I try the wp_remote_get() in other domain or when I send the request to other url,
I use this simple code
$allstores = wp_remote_get( 'http://admin.shopsaver.dk/wp-json/wp/v2/shop', array( 'timeout' => 20 ) );
var_dump( $allstores );
Please help :)
Thank you

GET works but POST doesn't for silent login

We have 2 systems one in PHP and one in asp.net which currently require separate logins even though both use the same username/password information.
As a quick (and temporary) fix I thought I might be able to amend the PHP login page to pass the login details to the asp.net page behind the scenes so the user could be logged in automatically to both systems rather than having to enter their credentials again when navigating to a different page.
This works fine when I use a GET to pass the parameters but of course the GET parameters including the password get stored in the server log which is not a good idea.
So I would like to use POST instead, but I can't get it to work. I used the CURL-less method in How do I send a POST request with PHP? (code below) and it appears to work but the asp.net login process creates secure cookies and while they are stored if I GET the page they are not being stored when I POST to it instead.
$url = 'https://server.com/path';
$data = array('key1' => 'value1', 'key2' => 'value2');
// use key 'http' even if you send the request to https://...
$options = array(
'http' => array(
'header' => "Content-type: application/x-www-form-urlencoded\r\n",
'method' => 'POST',
'content' => http_build_query($data),
),
);
$context = stream_context_create($options);
$result = file_get_contents($url, false, $context);
var_dump($result);
I have tried something similar with CURL in the past so I know that CURL creates it's own browser context but I thought a straight POST request would work, however it seems to be behaving much the same as CURL.
Is there some way to get this to work or do I have a fundamental misunderstanding of how POST works? If so could somebody point me at a good explanation.

Salesforce creates record but responds with a 405

I've written a Wordpress Plug-in that interacts with Salesforce via the REST API. It successfully gets an Instance URL and an Authentication Token using a username/password.
I'm able to submit queries and create objects using wp_remote_post with GET and POST respectively.
However, when creating objects, though successfully created in the Salesforce instance, I get the following in response to my POST:
{"message":"HTTP Method 'POST' not allowed. Allowed are HEAD,GET,PATCH,DELETE","errorCode":"METHOD_NOT_ALLOWED"}
Using the same json body content from these requests, I am able to submit and create via the Salesforce Workbench with no problems at all. I get a proper response that looks like this:
{
"id" : "003E000000OubjkIAB",
"success" : true,
"errors" : [ ]
}
Is there something in the Headers that I'm sending that Salesforce only partially disagrees with? Here are some other arguments that are getting sent as a result of using wp_remote_post - http://codex.wordpress.org/HTTP_API#Other_Arguments
Here's the php code that's calling it:
$connInfo['access_token'] = get_transient('npsf_access_token');
$connInfo['instance_url'] = get_transient('npsf_instance_url');
$url = $connInfo['instance_url'] . $service;
$sfResponse = wp_remote_post($url, array(
'method' => $method,
'timeout' => 5,
'redirection' => 5,
'httpversion' => 1.0,
'blocking' => true,
'headers' => array("Authorization" => "OAuth ". $connInfo['access_token'], "Content-type" => "application/json"),
'body' => $content,
'cookies' => array()
)
);
The $content is being encoded via json_encode before it gets to this point.
Update:
It is specific to one of the extra CURL options being sent by the WP_Http_Curl class. I haven't yet narrowed down which one Salesforce is having a problem with.
The solution is disable redirection in the request. You have it as 5 (the default) -- it needs to be set to 0 for this to work.
The initial request works but Salesforce sends a location header as a part of the response (the URL of the newly created object). WordPress thinks it is being told that the URL moved and that it should try again at this new URL. The response you're seeing is the result of that second request to the actual object you just created. That URL doesn't accept POST requests apparently.
It's a bit odd for Salesforce to be sending such a header, but there's also some discussion going on on the WordPress side that WordPress shouldn't follow location headers for non-301/302 responses which would solve this.
Thanks for posting this by the way. You update made me start debugging WP_Http_Curl which made me realize it was actually making a second HTTP request.

Categories