Skip to content

Commit 117fff7

Browse files
Merge pull request #31 from ethancarlsson-pf/ethan.carlsson/DEV-4690
Ethan.carlsson/dev 4690 - Update authorization with OAuth in SDK
2 parents 7102ce2 + 4eb36e0 commit 117fff7

File tree

5 files changed

+178
-10
lines changed

5 files changed

+178
-10
lines changed

README.md

+26
Original file line numberDiff line numberDiff line change
@@ -12,3 +12,29 @@ API endpoint documentation can be found here: https://www.printful.com/docs
1212
Using composer, run `composer require printful/php-api-sdk`
1313

1414
Check out **example** and **test** directories for more specific usage examples.
15+
16+
# OAuth
17+
[OAuth 2.0](https://developers.printful.com/docs/#section/Authentication:~:text=OAuth%202.0%20is%20the%20preferred%20way%20of%20doing%20authorization%20in%20Printful%20API.)
18+
is the preferred way of doing authorization in Printful API. Read more about how to acquire and
19+
use an access token in our docs: https://developers.printful.com/docs/#section/Authentication
20+
21+
You can create an OAuth enabled APIClient using the following factory method:
22+
```php
23+
...
24+
use Printful\PrintfulApiClient;
25+
...
26+
$client = PrintfulApiClient::createOauthClient('my-oauth-token')
27+
```
28+
29+
You can still use the old store keys, like this:
30+
```php
31+
...
32+
use Printful\PrintfulApiClient;
33+
...
34+
$client = PrintfulApiClient::createLegacyStoreKeyClient('my-legacy-store-key')
35+
```
36+
or, by using the constructor like this:
37+
```php
38+
$client = new PrintfulApiClient($storeKey)
39+
```
40+
However, please note that legacy keys will be phased out on September 30th, 2022.

src/PrintfulApiClient.php

+54-8
Original file line numberDiff line numberDiff line change
@@ -10,11 +10,21 @@
1010
*/
1111
class PrintfulApiClient
1212
{
13+
const TYPE_LEGACY_STORE_KEY = 'legacy-store-key';
14+
const TYPE_OAUTH_TOKEN = 'oauth-token';
15+
const DEFAULT_KEY = self::TYPE_LEGACY_STORE_KEY;
16+
1317
/**
1418
* Printful API key
15-
* @var string
19+
* @var string|null
20+
*/
21+
private $legacyStoreKey;
22+
23+
/**
24+
* Printful OAuth token
25+
* @var string|null
1626
*/
17-
private $key = '';
27+
private $oauthToken;
1828

1929
private $lastResponseRaw;
2030

@@ -37,16 +47,36 @@ class PrintfulApiClient
3747
public $curlTimeout = 20;
3848

3949
/**
40-
* @param string $key Printful Store API key
50+
* @param string $key
51+
* @param string $type // PrintfulApiClient::TYPE_LEGACY_STORE_KEY or PrintfulApiClient::TYPE_OAUTH_TOKEN
4152
* @throws \Printful\Exceptions\PrintfulException if the library failed to initialize
4253
*/
43-
public function __construct($key)
54+
public function __construct($key, $type = self::DEFAULT_KEY)
4455
{
45-
if (strlen($key) < 32) {
46-
throw new PrintfulException('Missing or invalid Printful store key!');
56+
if ($type === self::TYPE_LEGACY_STORE_KEY && strlen($key) < 32) {
57+
throw new PrintfulException('Invalid Printful store key!');
4758
}
4859

49-
$this->key = $key;
60+
$this->legacyStoreKey = $type === self::TYPE_LEGACY_STORE_KEY ? $key : null;
61+
$this->oauthToken = $type === self::TYPE_OAUTH_TOKEN ? $key : null;
62+
}
63+
64+
/**
65+
* @param string $oAuthToken
66+
* @throws PrintfulException
67+
*/
68+
public static function createOauthClient($oAuthToken)
69+
{
70+
return new self($oAuthToken, self::TYPE_OAUTH_TOKEN);
71+
}
72+
73+
/**
74+
* @param string $legacyStoreKey
75+
* @throws PrintfulException
76+
*/
77+
public static function createLegacyStoreKeyClient($legacyStoreKey)
78+
{
79+
return new self($legacyStoreKey, self::TYPE_LEGACY_STORE_KEY);
5080
}
5181

5282
/**
@@ -154,7 +184,8 @@ private function request($method, $path, array $params = [], $data = null)
154184

155185
$curl = curl_init($this->url . $url);
156186

157-
curl_setopt($curl, CURLOPT_USERPWD, $this->key);
187+
$this->setCredentials($curl);
188+
158189
curl_setopt($curl, CURLOPT_CUSTOMREQUEST, $method);
159190
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
160191
curl_setopt($curl, CURLOPT_FOLLOWLOCATION, true);
@@ -194,4 +225,19 @@ private function request($method, $path, array $params = [], $data = null)
194225
}
195226
return $response['result'];
196227
}
228+
229+
/**
230+
* @param resource $curl
231+
* @throws PrintfulException
232+
*/
233+
private function setCredentials($curl)
234+
{
235+
if ($this->oauthToken !== null) {
236+
curl_setopt($curl, CURLOPT_HTTPHEADER, ["Authorization: Bearer $this->oauthToken"]);
237+
} elseif ($this->legacyStoreKey !== null) {
238+
curl_setopt($curl, CURLOPT_USERPWD, $this->legacyStoreKey);
239+
} else {
240+
throw new PrintfulException('Either OAuth token or store key must be set to make this request.');
241+
}
242+
}
197243
}
+81
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,81 @@
1+
<?php
2+
3+
namespace Printful\Tests\ApiClient;
4+
5+
use Printful\Exceptions\PrintfulException;
6+
use Printful\PrintfulApiClient;
7+
use Printful\Tests\Credentials;
8+
use Printful\Tests\TestCase;
9+
10+
class PrintfulApiClientTest extends TestCase
11+
{
12+
/**
13+
* @throws \Printful\Exceptions\PrintfulException
14+
* @throws \Printful\Exceptions\PrintfulApiException
15+
*/
16+
public function testGet_withApiKey_returnsWithNoAuthErrors()
17+
{
18+
if (Credentials::$legacyStoreKey === '') {
19+
$this->markTestSkipped('You need apiKey to be set in Credentials.php for this test to run');
20+
}
21+
22+
$sut = PrintfulApiClient::createLegacyStoreKeyClient(Credentials::$legacyStoreKey);
23+
24+
$this->overrideUrl($sut);
25+
26+
$result = $sut->get('orders', [
27+
'offset' => 0,
28+
'limit' => 10,
29+
'status' => null,
30+
]);
31+
32+
self::assertNotNull($result);
33+
}
34+
35+
/**
36+
* @throws \Printful\Exceptions\PrintfulException
37+
* @throws \Printful\Exceptions\PrintfulApiException
38+
*/
39+
public function testGet_withOauthToken_returnsWithNoAuthErrors()
40+
{
41+
if (Credentials::$oAuthToken === '') {
42+
$this->markTestSkipped('You need oAuthToken to be set in Credentials.php for this test to run');
43+
}
44+
45+
$sut = PrintfulApiClient::createOauthClient(Credentials::$oAuthToken);
46+
47+
$this->overrideUrl($sut);
48+
49+
$result = $sut->get('orders', [
50+
'offset' => 0,
51+
'limit' => 10,
52+
'status' => null,
53+
]);
54+
self::assertNotNull($result);
55+
}
56+
57+
/**
58+
* @throws \Printful\Exceptions\PrintfulException
59+
* @throws \Printful\Exceptions\PrintfulApiException
60+
*/
61+
public function testGet_withInvalidCredentials_throwsApiException()
62+
{
63+
$sut = PrintfulApiClient::createOauthClient('invalid key');
64+
65+
$this->overrideUrl($sut);
66+
67+
$this->expectException(PrintfulException::class);
68+
$sut->get('orders', [
69+
'offset' => 0,
70+
'limit' => 10,
71+
'status' => null,
72+
]);
73+
}
74+
75+
private function overrideUrl(PrintfulApiClient $sut)
76+
{
77+
if (Credentials::$apiUrlOverride) {
78+
$sut->url = Credentials::$apiUrlOverride;
79+
}
80+
}
81+
}

tests/Credentials.php.dist

+6-1
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,12 @@ class Credentials
1111
/**
1212
* @var string
1313
*/
14-
public static $apiKey = '';
14+
public static $legacyStoreKey = '';
15+
16+
/**
17+
* @var string
18+
*/
19+
public static $oAuthToken = '';
1520

1621
/**
1722
* Option to override API URL

tests/TestCase.php

+11-1
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,10 @@ abstract class TestCase extends \PHPUnit_Framework_TestCase
1010
/** @var PrintfulApiClient */
1111
protected $api;
1212

13+
/**
14+
* @throws \Printful\Exceptions\PrintfulException
15+
* @throws \Exception
16+
*/
1317
protected function setUp()
1418
{
1519
parent::setUp();
@@ -18,7 +22,13 @@ protected function setUp()
1822
throw new \Exception('Printful test credentials are not set. Copy "tests/Credentials.php.dist" to "tests/Credentials.php and enter the API key');
1923
}
2024

21-
$this->api = new PrintfulApiClient(Credentials::$apiKey);
25+
if (Credentials::$oAuthToken !== '') {
26+
$this->api = PrintfulApiClient::createOauthClient(Credentials::$oAuthToken);
27+
} elseif (Credentials::$legacyStoreKey !== '') {
28+
$this->api = PrintfulApiClient::createLegacyStoreKeyClient(Credentials::$legacyStoreKey);
29+
} else {
30+
throw new \Exception('Printful test credentials are not set. Please enter a valid $oAuthToken or $legacyStoreKey in your tests/Credentials.php file');
31+
}
2232

2333
// Override API URL if is set
2434
if (Credentials::$apiUrlOverride) {

0 commit comments

Comments
 (0)