Commit 20f52904 authored by Morris Jobke's avatar Morris Jobke
Browse files

Merge pull request #15195 from owncloud/reanimate-add-guzzle

Add wrapper for Guzzle
parents c8f0cbab 5f044ebf
Subproject commit 244f75dc8d4552bb73a4aa93a1c6eeafdeb801d8
Subproject commit e4f341066a2f9740cabffd20aa76742ce7cd8bfd
......@@ -122,9 +122,9 @@ class Share extends TestCase {
private function createMocks() {
$config = $this->getMockBuilder('\OCP\IConfig')
->disableOriginalConstructor()->getMock();
$certificateManager = $this->getMock('\OCP\ICertificateManager');
$clientService = $this->getMock('\OCP\Http\Client\IClientService');
$httpHelperMock = $this->getMockBuilder('\OC\HTTPHelper')
->setConstructorArgs(array($config, $certificateManager))
->setConstructorArgs([$config, $clientService])
->getMock();
$httpHelperMock->expects($this->any())->method('post')->with($this->anything())->will($this->returnValue(array('success' => true, 'result' => "{'ocs' : { 'meta' : { 'statuscode' : 100 }}}")));
......
......@@ -11,6 +11,7 @@
namespace OCA\Files_Sharing\Controllers;
use Hoa\Core\Data\Data;
use OC;
use OC\Files\Filesystem;
use OC_Files;
......@@ -30,6 +31,7 @@ use OCA\Files_Sharing\Helper;
use OCP\User;
use OCP\Util;
use OCA\Files_Sharing\Activity;
use OCP\AppFramework\Http\DataResponse;
/**
* Class ShareController
......
......@@ -210,37 +210,23 @@ class Storage extends DAV implements ISharedStorage {
}
}
/**
* @return mixed
* @throws ForbiddenException
* @throws NotFoundException
* @throws \Exception
*/
public function getShareInfo() {
$remote = $this->getRemote();
$token = $this->getToken();
$password = $this->getPassword();
$url = rtrim($remote, '/') . '/index.php/apps/files_sharing/shareinfo?t=' . $token;
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS,
http_build_query(array('password' => $password)));
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, true);
curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, 2);
$path = $this->certificateManager->getCertificateBundle();
if (is_readable($path)) {
curl_setopt($ch, CURLOPT_CAINFO, $path);
}
$result = curl_exec($ch);
$status = curl_getinfo($ch, CURLINFO_HTTP_CODE);
$errorMessage = curl_error($ch);
curl_close($ch);
if (!empty($errorMessage)) {
throw new \Exception($errorMessage);
}
// TODO: DI
$client = \OC::$server->getHTTPClientService()->newClient();
$response = $client->post($url, ['body' => ['password' => $password]]);
switch ($status) {
switch ($response->getStatusCode()) {
case 401:
case 403:
throw new ForbiddenException();
......@@ -250,6 +236,6 @@ class Storage extends DAV implements ISharedStorage {
throw new \Exception();
}
return json_decode($result, true);
return json_decode($response->getBody(), true);
}
}
......@@ -48,9 +48,9 @@ class Test_Files_Sharing_S2S_OCS_API extends TestCase {
$config = $this->getMockBuilder('\OCP\IConfig')
->disableOriginalConstructor()->getMock();
$certificateManager = $this->getMock('\OCP\ICertificateManager');
$clientService = $this->getMock('\OCP\Http\Client\IClientService');
$httpHelperMock = $this->getMockBuilder('\OC\HTTPHelper')
->setConstructorArgs(array($config, $certificateManager))
->setConstructorArgs([$config, $clientService])
->getMock();
$httpHelperMock->expects($this->any())->method('post')->with($this->anything())->will($this->returnValue(true));
......
This source diff could not be displayed because it is too large. You can view the blob instead.
<?php
/**
* Copyright (c) 2015 Lukas Reschke <lukas@owncloud.com>
* This file is licensed under the Affero General Public License version 3 or
* later.
* See the COPYING-README file.
*/
namespace OC\Http\Client;
use GuzzleHttp\Client as GuzzleClient;
use OCP\Http\Client\IClient;
use OCP\ICertificateManager;
use OCP\IConfig;
/**
* Class Client
*
* @package OC\Http
*/
class Client implements IClient {
/** @var GuzzleClient */
private $client;
/** @var IConfig */
private $config;
/** @var ICertificateManager */
private $certificateManager;
/**
* @param IConfig $config
* @param ICertificateManager $certificateManager
* @param GuzzleClient $client
*/
public function __construct(IConfig $config,
ICertificateManager $certificateManager,
GuzzleClient $client) {
$this->config = $config;
$this->client = $client;
$this->certificateManager = $certificateManager;
$this->setDefaultOptions();
}
/**
* Sets the default options to the client
*/
private function setDefaultOptions() {
// Either use default bundle or the user bundle if nothing is specified
if($this->certificateManager->listCertificates() !== []) {
$dataDir = $this->config->getSystemValue('datadirectory');
$this->client->setDefaultOption('verify', $dataDir.'/'.$this->certificateManager->getCertificateBundle());
} else {
$this->client->setDefaultOption('verify', \OC::$SERVERROOT . '/config/ca-bundle.crt');
}
$this->client->setDefaultOption('headers/User-Agent', 'ownCloud Server Crawler');
if($this->getProxyUri() !== '') {
$this->client->setDefaultOption('proxy', $this->getProxyUri());
}
}
/**
* Get the proxy URI
* @return string
*/
private function getProxyUri() {
$proxyHost = $this->config->getSystemValue('proxy', null);
$proxyUserPwd = $this->config->getSystemValue('proxyuserpwd', null);
$proxyUri = '';
if(!is_null($proxyUserPwd)) {
$proxyUri .= $proxyUserPwd.'@';
}
if(!is_null($proxyHost)) {
$proxyUri .= $proxyHost;
}
return $proxyUri;
}
/**
* Sends a GET request
* @param string $uri
* @param array $options Array such as
* 'query' => [
* 'field' => 'abc',
* 'other_field' => '123',
* 'file_name' => fopen('/path/to/file', 'r'),
* ],
* 'headers' => [
* 'foo' => 'bar',
* ],
* 'cookies' => ['
* 'foo' => 'bar',
* ],
* 'allow_redirects' => [
* 'max' => 10, // allow at most 10 redirects.
* 'strict' => true, // use "strict" RFC compliant redirects.
* 'referer' => true, // add a Referer header
* 'protocols' => ['https'] // only allow https URLs
* ],
* 'save_to' => '/path/to/file', // save to a file or a stream
* 'verify' => true, // bool or string to CA file
* 'debug' => true,
* 'timeout' => 5,
* @return Response
* @throws \Exception If the request could not get completed
*/
public function get($uri, array $options = []) {
$response = $this->client->get($uri, $options);
return new Response($response);
}
/**
* Sends a HEAD request
* @param string $uri
* @param array $options Array such as
* 'headers' => [
* 'foo' => 'bar',
* ],
* 'cookies' => ['
* 'foo' => 'bar',
* ],
* 'allow_redirects' => [
* 'max' => 10, // allow at most 10 redirects.
* 'strict' => true, // use "strict" RFC compliant redirects.
* 'referer' => true, // add a Referer header
* 'protocols' => ['https'] // only allow https URLs
* ],
* 'save_to' => '/path/to/file', // save to a file or a stream
* 'verify' => true, // bool or string to CA file
* 'debug' => true,
* 'timeout' => 5,
* @return Response
*/
public function head($uri, $options = []) {
$response = $this->client->head($uri, $options);
return new Response($response);
}
/**
* Sends a POST request
* @param string $uri
* @param array $options Array such as
* 'body' => [
* 'field' => 'abc',
* 'other_field' => '123',
* 'file_name' => fopen('/path/to/file', 'r'),
* ],
* 'headers' => [
* 'foo' => 'bar',
* ],
* 'cookies' => ['
* 'foo' => 'bar',
* ],
* 'allow_redirects' => [
* 'max' => 10, // allow at most 10 redirects.
* 'strict' => true, // use "strict" RFC compliant redirects.
* 'referer' => true, // add a Referer header
* 'protocols' => ['https'] // only allow https URLs
* ],
* 'save_to' => '/path/to/file', // save to a file or a stream
* 'verify' => true, // bool or string to CA file
* 'debug' => true,
* 'timeout' => 5,
* @return Response
*/
public function post($uri, array $options = []) {
$response = $this->client->post($uri, $options);
return new Response($response);
}
/**
* Sends a PUT request
* @param string $uri
* @param array $options Array such as
* 'body' => [
* 'field' => 'abc',
* 'other_field' => '123',
* 'file_name' => fopen('/path/to/file', 'r'),
* ],
* 'headers' => [
* 'foo' => 'bar',
* ],
* 'cookies' => ['
* 'foo' => 'bar',
* ],
* 'allow_redirects' => [
* 'max' => 10, // allow at most 10 redirects.
* 'strict' => true, // use "strict" RFC compliant redirects.
* 'referer' => true, // add a Referer header
* 'protocols' => ['https'] // only allow https URLs
* ],
* 'save_to' => '/path/to/file', // save to a file or a stream
* 'verify' => true, // bool or string to CA file
* 'debug' => true,
* 'timeout' => 5,
* @return Response
*/
public function put($uri, array $options = []) {
$response = $this->client->put($uri, $options);
return new Response($response);
}
/**
* Sends a DELETE request
* @param string $uri
* @param array $options Array such as
* 'body' => [
* 'field' => 'abc',
* 'other_field' => '123',
* 'file_name' => fopen('/path/to/file', 'r'),
* ],
* 'headers' => [
* 'foo' => 'bar',
* ],
* 'cookies' => ['
* 'foo' => 'bar',
* ],
* 'allow_redirects' => [
* 'max' => 10, // allow at most 10 redirects.
* 'strict' => true, // use "strict" RFC compliant redirects.
* 'referer' => true, // add a Referer header
* 'protocols' => ['https'] // only allow https URLs
* ],
* 'save_to' => '/path/to/file', // save to a file or a stream
* 'verify' => true, // bool or string to CA file
* 'debug' => true,
* 'timeout' => 5,
* @return Response
*/
public function delete($uri, array $options = []) {
$response = $this->client->delete($uri, $options);
return new Response($response);
}
/**
* Sends a options request
* @param string $uri
* @param array $options Array such as
* 'body' => [
* 'field' => 'abc',
* 'other_field' => '123',
* 'file_name' => fopen('/path/to/file', 'r'),
* ],
* 'headers' => [
* 'foo' => 'bar',
* ],
* 'cookies' => ['
* 'foo' => 'bar',
* ],
* 'allow_redirects' => [
* 'max' => 10, // allow at most 10 redirects.
* 'strict' => true, // use "strict" RFC compliant redirects.
* 'referer' => true, // add a Referer header
* 'protocols' => ['https'] // only allow https URLs
* ],
* 'save_to' => '/path/to/file', // save to a file or a stream
* 'verify' => true, // bool or string to CA file
* 'debug' => true,
* 'timeout' => 5,
* @return Response
*/
public function options($uri, array $options = []) {
$response = $this->client->options($uri, $options);
return new Response($response);
}
}
<?php
/**
* Copyright (c) 2015 Lukas Reschke <lukas@owncloud.com>
* This file is licensed under the Affero General Public License version 3 or
* later.
* See the COPYING-README file.
*/
namespace OC\Http\Client;
use GuzzleHttp\Client as GuzzleClient;
use OCP\Http\Client\IClientService;
use OCP\ICertificateManager;
use OCP\IConfig;
/**
* Class ClientService
*
* @package OC\Http
*/
class ClientService implements IClientService {
/** @var IConfig */
private $config;
/** @var ICertificateManager */
private $certificateManager;
/**
* @param IConfig $config
* @param ICertificateManager $certificateManager
*/
public function __construct(IConfig $config,
ICertificateManager $certificateManager) {
$this->config = $config;
$this->certificateManager = $certificateManager;
}
/**
* @return Client
*/
public function newClient() {
return new Client($this->config, $this->certificateManager, new GuzzleClient());
}
}
<?php
/**
* Copyright (c) 2015 Lukas Reschke <lukas@owncloud.com>
* This file is licensed under the Affero General Public License version 3 or
* later.
* See the COPYING-README file.
*/
namespace OC\Http\Client;
use OCP\Http\Client\IResponse;
use GuzzleHttp\Message\Response as GuzzleResponse;
/**
* Class Response
*
* @package OC\Http
*/
class Response implements IResponse {
/** @var GuzzleResponse */
private $response;
/**
* @param GuzzleResponse $response
*/
public function __construct(GuzzleResponse $response) {
$this->response = $response;
}
/**
* @return string
*/
public function getBody() {
return $this->response->getBody()->getContents();
}
/**
* @return int
*/
public function getStatusCode() {
return $this->response->getStatusCode();
}
/**
* @param $key
* @return string
*/
public function getHeader($key) {
return $this->response->getHeader($key);
}
/**
* @return array
*/
public function getHeaders() {
return $this->response->getHeaders();
}
}
<?php
/**
* Copyright (c) 2014 Lukas Reschke <lukas@owncloud.com>
* Copyright (c) 2014-2015 Lukas Reschke <lukas@owncloud.com>
* This file is licensed under the Affero General Public License version 3 or
* later.
* See the COPYING-README file.
......@@ -8,41 +8,31 @@
namespace OC;
use OCP\Http\Client\IClientService;
use OCP\IConfig;
use OCP\ICertificateManager;
/**
* Class HTTPHelper
*
* @package OC
* @deprecated Use \OCP\Http\Client\IClientService
*/
class HTTPHelper {
const USER_AGENT = 'ownCloud Server Crawler';
/** @var \OCP\IConfig */
private $config;
/** @var \OC\Security\CertificateManager */
private $certificateManager;
/** @var IClientService */
private $clientService;
/**
* @param \OCP\IConfig $config
* @param IConfig $config
* @param IClientService $clientService
*/
public function __construct(IConfig $config, ICertificateManager $certificateManager) {
public function __construct(IConfig $config,
IClientService $clientService) {
$this->config = $config;
$this->certificateManager = $certificateManager;
}
/**
* Returns the default context array
* @return array
*/
public function getDefaultContextArray() {
return array(
'http' => array(
'header' => 'User-Agent: ' . self::USER_AGENT . "\r\n",
'timeout' => 10,
'follow_location' => false, // Do not follow the location since we can't limit the protocol
),
'ssl' => array(
'disable_compression' => true
)
);
$this->clientService = $clientService;
}
/**
......@@ -52,87 +42,28 @@ class HTTPHelper {
* @return string of the response or false on error
* This function get the content of a page via curl, if curl is enabled.
* If not, file_get_contents is used.
* @deprecated Use \OCP\Http\Client\IClientService
*/
public function getUrlContent($url) {
if (!$this->isHTTPURL($url)) {
throw new \Exception('$url must start with https:// or http://', 1);
}
$proxy = $this->config->getSystemValue('proxy', null);
$proxyUserPwd = $this->config->getSystemValue('proxyuserpwd', null);
$curl = curl_init();
$max_redirects = 10;
curl_setopt($curl, CURLOPT_HEADER, 0);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($curl, CURLOPT_CONNECTTIMEOUT, 10);
curl_setopt($curl, CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_PROTOCOLS, CURLPROTO_HTTP | CURLPROTO_HTTPS);
curl_setopt($curl, CURLOPT_REDIR_PROTOCOLS, CURLPROTO_HTTP | CURLPROTO_HTTPS);
curl_setopt($curl, CURLOPT_USERAGENT, self::USER_AGENT);
if ($proxy !== null) {
curl_setopt($curl, CURLOPT_PROXY, $proxy);
}
if ($proxyUserPwd !== null) {
curl_setopt($curl, CURLOPT_PROXYUSERPWD, $proxyUserPwd);
}
if (ini_get('open_basedir') === '') {
curl_setopt($curl, CURLOPT_FOLLOWLOCATION, true);
curl_setopt($curl, CURLOPT_MAXREDIRS, $max_redirects);
$data = curl_exec($curl);
} else {
curl_setopt($curl, CURLOPT_FOLLOWLOCATION, false);
$mr = $max_redirects;
if ($mr > 0) {
$newURL = curl_getinfo($curl, CURLINFO_EFFECTIVE_URL);
$rCurl = curl_copy_handle($curl);
curl_setopt($rCurl, CURLOPT_HEADER, true);
curl_setopt($rCurl, CURLOPT_NOBODY, true);
curl_setopt($rCurl, CURLOPT_FORBID_REUSE, false);
curl_setopt($rCurl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($rCurl, CURLOPT_USERAGENT, self::USER_AGENT);
do {
curl_setopt($rCurl, CURLOPT_URL, $newURL);
$header = curl_exec($rCurl);
if (curl_errno($rCurl)) {
$code = 0;
} else {
$code = curl_getinfo($rCurl, CURLINFO_HTTP_CODE);
if ($code == 301 || $code == 302) {
preg_match('/Location:(.*?)\n/', $header, $matches);
$newURL = trim(array_pop($matches));
} else {
$code = 0;
}
}
} while ($code && --$mr);
curl_close($rCurl);
if ($mr > 0) {
curl_setopt($curl, CURLOPT_URL, $newURL);
}
}
if ($mr == 0 && $max_redirects > 0) {
$data = false;
} else {
$data = curl_exec($curl);
}
try {
$client = $this->clientService->newClient();
$response = $client->get($url);
return $response->getBody();
} catch (\Exception $e) {
return false;