Skip to content

Commit ec9b369

Browse files
author
Ian Barber
committed
Adding an experimental AppIdentity auth impl
Included an example file. It's a tricky one to unit test as there's not a lot to it, and it only works on GAE!
1 parent 46396ef commit ec9b369

File tree

5 files changed

+142
-47
lines changed

5 files changed

+142
-47
lines changed

examples/appengineauth.php

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
<?php
2+
/*
3+
* Copyright 2013 Google Inc.
4+
*
5+
* Licensed under the Apache License, Version 2.0 (the "License");
6+
* you may not use this file except in compliance with the License.
7+
* You may obtain a copy of the License at
8+
*
9+
* http://www.apache.org/licenses/LICENSE-2.0
10+
*
11+
* Unless required by applicable law or agreed to in writing, software
12+
* distributed under the License is distributed on an "AS IS" BASIS,
13+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14+
* See the License for the specific language governing permissions and
15+
* limitations under the License.
16+
*/
17+
session_start();
18+
include_once "templates/base.php";
19+
20+
/************************************************
21+
Make an API request authenticated via the
22+
AppIdentity service on AppEngine.
23+
************************************************/
24+
set_include_path("../src/" . PATH_SEPARATOR . get_include_path());
25+
require_once 'Google/Client.php';
26+
require_once 'Google/Auth/AppIdentity.php';
27+
require_once 'Google/Service/Storage.php';
28+
29+
echo pageHeader("AppIdentity Account Access");
30+
31+
$client = new Google_Client();
32+
$client->setApplicationName("Client_Library_Examples");
33+
34+
$auth = new Google_Auth_AppIdentity($client);
35+
$token = $auth->authenticateForScope(Google_Service_Storage::DEVSTORAGE_READ_ONLY);
36+
if (!$token) {
37+
die("Could not authenticate to AppIdentity service");
38+
}
39+
$client->setAuth($auth);
40+
41+
$service = new Google_Service_Storage($client);
42+
$results = $service->buckets->listBuckets(str_replace("s~", "", $_SERVER['APPLICATION_ID']));
43+
44+
echo "<h3>Results Of Call:</h3>";
45+
echo "<pre>";
46+
var_dump($results);
47+
echo "</pre>";
48+
49+
echo pageFooter(__FILE__);

src/Google/Auth/Abstract.php

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -31,11 +31,5 @@ abstract class Google_Auth_Abstract
3131
* @return Google_Http_Request $request
3232
*/
3333
abstract public function authenticatedRequest(Google_Http_Request $request);
34-
35-
abstract public function authenticate($code);
3634
abstract public function sign(Google_Http_Request $request);
37-
abstract public function createAuthUrl($scope);
38-
39-
abstract public function refreshToken($refreshToken);
40-
abstract public function revokeToken();
4135
}

src/Google/Auth/AppIdentity.php

Lines changed: 93 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,93 @@
1+
<?php
2+
/*
3+
* Copyright 2014 Google Inc.
4+
*
5+
* Licensed under the Apache License, Version 2.0 (the "License");
6+
* you may not use this file except in compliance with the License.
7+
* You may obtain a copy of the License at
8+
*
9+
* http://www.apache.org/licenses/LICENSE-2.0
10+
*
11+
* Unless required by applicable law or agreed to in writing, software
12+
* distributed under the License is distributed on an "AS IS" BASIS,
13+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14+
* See the License for the specific language governing permissions and
15+
* limitations under the License.
16+
*/
17+
18+
/*
19+
* WARNING - this class depends on the Google App Engine PHP library
20+
* which is 5.3 and above only, so if you include this in a PHP 5.2
21+
* setup or one without 5.3 things will blow up.
22+
*/
23+
use google\appengine\api\app_identity\AppIdentityService;
24+
25+
require_once "Google/Auth/Abstract.php";
26+
require_once "Google/Http/Request.php";
27+
28+
/**
29+
* Authentication via the Google App Engine App Identity service.
30+
*/
31+
class Google_Auth_AppIdentity extends Google_Auth_Abstract
32+
{
33+
const CACHE_PREFIX = "Google_Auth_AppIdentity::";
34+
const CACHE_LIFETIME = 1500;
35+
private $key = null;
36+
private $client;
37+
private $token = false;
38+
private $tokenScopes = false;
39+
40+
public function __construct(Google_Client $client, $config = null)
41+
{
42+
$this->client = $client;
43+
}
44+
45+
/**
46+
* Retrieve an access token for the scopes supplied.
47+
*/
48+
public function authenticateForScope($scopes) {
49+
if ($this->token && $this->tokenScopes == $scopes) {
50+
return $this->token;
51+
}
52+
$memcache = new Memcached();
53+
$this->token = $memcache->get(self::CACHE_PREFIX . $scopes);
54+
if (!$this->token) {
55+
$this->token = AppIdentityService::getAccessToken($scopes);
56+
if ($this->token) {
57+
$memcache->set(self::CACHE_PREFIX . $scopes, $this->token, self::CACHE_LIFETIME);
58+
}
59+
}
60+
$this->tokenScopes = $scopes;
61+
return $this->token;
62+
}
63+
64+
/**
65+
* Perform an authenticated / signed apiHttpRequest.
66+
* This function takes the apiHttpRequest, calls apiAuth->sign on it
67+
* (which can modify the request in what ever way fits the auth mechanism)
68+
* and then calls apiCurlIO::makeRequest on the signed request
69+
*
70+
* @param Google_Http_Request $request
71+
* @return Google_Http_Request The resulting HTTP response including the
72+
* responseHttpCode, responseHeaders and responseBody.
73+
*/
74+
public function authenticatedRequest(Google_Http_Request $request)
75+
{
76+
$request = $this->sign($request);
77+
return $this->io->makeRequest($request);
78+
}
79+
80+
public function sign(Google_Http_Request $request)
81+
{
82+
if (!$this->token) {
83+
// No token, so nothing to do.
84+
return $request;
85+
}
86+
// Add the OAuth2 header to the request
87+
$request->setRequestHeaders(
88+
array('Authorization' => 'Bearer ' . $this->token['access_token'])
89+
);
90+
91+
return $request;
92+
}
93+
}

src/Google/Auth/Simple.php

Lines changed: 0 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -51,36 +51,6 @@ public function authenticatedRequest(Google_Http_Request $request)
5151
return $this->io->makeRequest($request);
5252
}
5353

54-
public function authenticate($code)
55-
{
56-
throw new Google_Auth_Exception("Simple auth does not exchange tokens.");
57-
}
58-
59-
public function setAccessToken($accessToken)
60-
{
61-
/* noop*/
62-
}
63-
64-
public function getAccessToken()
65-
{
66-
return null;
67-
}
68-
69-
public function createAuthUrl($scope)
70-
{
71-
return null;
72-
}
73-
74-
public function refreshToken($refreshToken)
75-
{
76-
/* noop*/
77-
}
78-
79-
public function revokeToken()
80-
{
81-
/* noop*/
82-
}
83-
8454
public function sign(Google_Http_Request $request)
8555
{
8656
$key = $this->client->getClassConfig($this, 'developer_key');

tests/general/AuthTest.php

Lines changed: 0 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -234,17 +234,6 @@ public function testNoAuth() {
234234
$req = new Google_Http_Request("http://example.com");
235235

236236
$resp = $noAuth->sign($req);
237-
try {
238-
$noAuth->authenticate(null);
239-
$this->assertTrue(false, "Exception expected");
240-
} catch (Google_Auth_Exception $e) {
241-
242-
}
243-
$noAuth->createAuthUrl(null);
244-
$noAuth->setAccessToken(null);
245-
$noAuth->getAccessToken();
246-
$noAuth->refreshToken(null);
247-
$noAuth->revokeToken();
248237
$this->assertEquals("http://example.com", $resp->getUrl());
249238
$this->getClient()->setAuth($oldAuth);
250239
}

0 commit comments

Comments
 (0)