diff --git a/modules/oauth/controllers/AuthorizeController.php b/modules/oauth/controllers/AuthorizeController.php index 2d2b26989..a503e0c47 100644 --- a/modules/oauth/controllers/AuthorizeController.php +++ b/modules/oauth/controllers/AuthorizeController.php @@ -85,8 +85,11 @@ function indexAction() /** * Submit login form. Will redirect the user to the redirect_uri on success - * @param redirect_uri - * @param [state] + * @param redirect_uri The client's desired redirect URI + * @param login The user's login + * @param password The user's password + * @param allowOrDeny Whether to allow or deny the request. Set to 'Allow' to allow. + * @param [state] Opaque state pointer string to be passed back to the client appended to the redirect URI */ function submitAction() { diff --git a/modules/oauth/controllers/ClientController.php b/modules/oauth/controllers/ClientController.php index 11ae737d6..08592569a 100644 --- a/modules/oauth/controllers/ClientController.php +++ b/modules/oauth/controllers/ClientController.php @@ -124,7 +124,7 @@ function deleteAction() { throw new Zend_Exception('Admin permission required', 403); } - + $this->Oauth_Client->delete($client); echo JsonComponent::encode(array('status' => 'ok', 'message' => 'Client deleted')); } diff --git a/modules/oauth/controllers/TokenController.php b/modules/oauth/controllers/TokenController.php index 1fcd9128e..405e0db17 100644 --- a/modules/oauth/controllers/TokenController.php +++ b/modules/oauth/controllers/TokenController.php @@ -103,7 +103,7 @@ function deleteAction() { throw new Zend_Exception('Admin permission required', 403); } - + $this->Oauth_Token->delete($token); echo JsonComponent::encode(array('status' => 'ok', 'message' => 'Token deleted')); } @@ -168,7 +168,7 @@ private function _authorizationCode($secret) $accessToken = $this->Oauth_Token->createAccessToken($codeDao, '+25 hours'); $refreshToken = $this->Oauth_Token->createRefreshToken($codeDao); $this->Oauth_Code->delete($codeDao); - + $obj = array('token_type' => 'bearer'); $obj['access_token'] = $accessToken->getToken(); $obj['refresh_token'] = $refreshToken->getToken(); diff --git a/modules/oauth/database/mysql/1.0.0.sql b/modules/oauth/database/mysql/1.0.0.sql index 53e96a2f0..a5df1bee5 100644 --- a/modules/oauth/database/mysql/1.0.0.sql +++ b/modules/oauth/database/mysql/1.0.0.sql @@ -5,7 +5,7 @@ CREATE TABLE IF NOT EXISTS `oauth_client` ( `owner_id` bigint(20) NOT NULL, `creation_date` timestamp NULL DEFAULT NULL, PRIMARY KEY (`client_id`), - INDEX (`identifier`) + INDEX (`owner_id`) ) DEFAULT CHARSET=utf8; CREATE TABLE IF NOT EXISTS `oauth_code` ( diff --git a/modules/oauth/database/pgsql/1.0.0.sql b/modules/oauth/database/pgsql/1.0.0.sql index 47e2f355b..6a461ed3d 100644 --- a/modules/oauth/database/pgsql/1.0.0.sql +++ b/modules/oauth/database/pgsql/1.0.0.sql @@ -5,7 +5,7 @@ CREATE TABLE oauth_client ( owner_id bigint NOT NULL, creation_date timestamp without time zone NULL DEFAULT NULL ); -CREATE INDEX oauth_client_identifier ON oauth_client (identifier); +CREATE INDEX oauth_client_owner_id ON oauth_client (owner_id); CREATE TABLE oauth_code ( code_id serial PRIMARY KEY, diff --git a/modules/oauth/tests/CMakeLists.txt b/modules/oauth/tests/CMakeLists.txt new file mode 100644 index 000000000..8107f4655 --- /dev/null +++ b/modules/oauth/tests/CMakeLists.txt @@ -0,0 +1,5 @@ +add_subdirectory( controllers ) + +add_midas_style_test( StyleOauthControllers ${CMAKE_SOURCE_DIR}/modules/oauth/controllers ) +add_midas_style_test( StyleOauthModels ${CMAKE_SOURCE_DIR}/modules/oauth/models ) +add_midas_style_test( StyleOauthNotification ${CMAKE_SOURCE_DIR}/modules/oauth/Notification.php ) diff --git a/modules/oauth/tests/controllers/AuthorizeControllerTest.php b/modules/oauth/tests/controllers/AuthorizeControllerTest.php new file mode 100644 index 000000000..291fd5167 --- /dev/null +++ b/modules/oauth/tests/controllers/AuthorizeControllerTest.php @@ -0,0 +1,130 @@ +setupDatabase(array('default')); //core dataset + $this->setupDatabase(array('default'), 'oauth'); + $this->enabledModules = array('api', 'oauth'); + $this->_models = array('User'); + + parent::setUp(); + } + + /** + * Helper function to get test that each paramter in the array is required + */ + private function _testParamsRequired($uri, $params, $userDao = null) + { + foreach($params as $key => $value) + { + $localParams = $params; //copy array + unset($localParams[$key]); + $this->resetAll(); + $this->params = $localParams; + $this->getRequest()->setMethod('GET'); + $this->dispatchUri($uri, $userDao, true); + $this->assertEquals($this->getResponse()->getHttpResponseCode(), 400); //IETF spec dictates we must send BAD_REQUEST response + } + } + + /** + * Tests the login screen used by the user to authorize the client + */ + public function testLoginScreen() + { + $_SERVER['HTTPS'] = true; //must set this to trick the action into thinking we're using SSL + $params = array( + 'client_id' => '1000', + 'response_type' => 'code', + 'redirect_uri' => 'http://google.com'); + $this->_testParamsRequired('/oauth/authorize', $params); + + $scopes = array(MIDAS_API_PERMISSION_SCOPE_READ_USER_INFO, + MIDAS_API_PERMISSION_SCOPE_WRITE_USER_INFO, + MIDAS_API_PERMISSION_SCOPE_READ_DATA); + $this->resetAll(); + $this->params = $params; + $this->params['state'] = 'my_state_value'; + $this->params['scope'] = JsonComponent::encode($scopes); + $this->dispatchUrI('/oauth/authorize', null); + $this->assertQueryCount('ul.scopeList li', count($scopes)); + $scopeMap = Zend_Registry::get('permissionScopeMap'); + + foreach($scopes as $scope) + { + $this->assertQueryContentContains('ul.scopeList li', $scopeMap[$scope]); + } + } + + /** + * Test the submission of the login form, authorizing the client + */ + public function testSubmitAction() + { + $user = $this->User->load(1); + $this->User->changePassword($user, 'myPassword'); //easiest way to set the password + $params = array( + 'client_id' => '1000', + 'login' => $user->getEmail(), + 'password' => 'wrongPass', + 'redirect_uri' => 'http://google.com'); + $this->_testParamsRequired('/oauth/authorize/submit', $params); + + $scopes = array(MIDAS_API_PERMISSION_SCOPE_READ_USER_INFO, + MIDAS_API_PERMISSION_SCOPE_WRITE_USER_INFO, + MIDAS_API_PERMISSION_SCOPE_READ_DATA); + + // Test with incorrect password + $this->resetAll(); + $this->params = $params; + $this->params['state'] = 'my_state_value'; + $this->params['scope'] = JsonComponent::encode($scopes); + $this->params['allowOrDeny'] = 'Allow'; + $this->dispatchUrI('/oauth/authorize/submit', null); + $json = JsonComponent::decode($this->getBody()); + $this->assertEquals($json['status'], 'error'); + $this->assertEquals($json['message'], 'Invalid username or password'); + + // Test user denying the request + $this->resetAll(); + $this->params = $params; + $this->params['state'] = 'my_state_value'; + $this->params['scope'] = JsonComponent::encode($scopes); + $this->params['allowOrDeny'] = 'Deny'; + $this->dispatchUrI('/oauth/authorize/submit', null); + $json = JsonComponent::decode($this->getBody()); + $this->assertEquals($json['status'], 'ok'); + $this->assertEquals($json['redirect'], $params['redirect_uri'].'?error=access_denied&state='.$this->params['state']); + + // Test user allowing the request + $this->resetAll(); + $this->params = $params; + $this->params['state'] = 'my_state_value'; + $this->params['scope'] = JsonComponent::encode($scopes); + $this->params['allowOrDeny'] = 'Allow'; + $this->params['password'] = 'myPassword'; + $this->dispatchUrI('/oauth/authorize/submit', null); + + $codeModel = MidasLoader::loadModel('Code', 'oauth'); + $codeDaos = $codeModel->getByUser($user); + $codeDao = end($codeDaos); + + $json = JsonComponent::decode($this->getBody()); + $this->assertEquals($json['status'], 'ok'); + $this->assertEquals($json['redirect'], $params['redirect_uri'].'?code='.$codeDao->getCode().'&state='.$this->params['state']); + } +} diff --git a/modules/oauth/tests/controllers/CMakeLists.txt b/modules/oauth/tests/controllers/CMakeLists.txt new file mode 100644 index 000000000..9010150cc --- /dev/null +++ b/modules/oauth/tests/controllers/CMakeLists.txt @@ -0,0 +1,3 @@ +add_midas_test( OauthAuthorizeController AuthorizeControllerTest.php ) +add_midas_test( OauthClientController ClientControllerTest.php ) +add_midas_test( OauthTokenController TokenControllerTest.php ) diff --git a/modules/oauth/tests/controllers/ClientControllerTest.php b/modules/oauth/tests/controllers/ClientControllerTest.php new file mode 100644 index 000000000..d16f61881 --- /dev/null +++ b/modules/oauth/tests/controllers/ClientControllerTest.php @@ -0,0 +1,33 @@ +setupDatabase(array('default')); //core dataset + $this->setupDatabase(array('default'), 'oauth'); + $this->enabledModules = array('api', 'oauth'); + $this->_models = array('User'); + + parent::setUp(); + } + + /** + * TODO stub + */ + public function testStub() + { + } +} diff --git a/modules/oauth/tests/controllers/TokenControllerTest.php b/modules/oauth/tests/controllers/TokenControllerTest.php new file mode 100644 index 000000000..b2a15920d --- /dev/null +++ b/modules/oauth/tests/controllers/TokenControllerTest.php @@ -0,0 +1,33 @@ +setupDatabase(array('default')); //core dataset + $this->setupDatabase(array('default'), 'oauth'); + $this->enabledModules = array('api', 'oauth'); + $this->_models = array('User'); + + parent::setUp(); + } + + /** + * TODO stub + */ + public function testStub() + { + } +} diff --git a/modules/oauth/tests/databaseDataset/default.xml b/modules/oauth/tests/databaseDataset/default.xml new file mode 100644 index 000000000..fcdb44f4a --- /dev/null +++ b/modules/oauth/tests/databaseDataset/default.xml @@ -0,0 +1,32 @@ + + + + + + + + + diff --git a/modules/oauth/translation/fr-main.csv b/modules/oauth/translation/fr-main.csv index e69de29bb..ec1f4c2f8 100644 --- a/modules/oauth/translation/fr-main.csv +++ b/modules/oauth/translation/fr-main.csv @@ -0,0 +1 @@ +foo;foo \ No newline at end of file