From 34a0216ca74b52472f8e717c78e927672c0dd4cf Mon Sep 17 00:00:00 2001 From: Francois Ferrand Date: Wed, 25 Feb 2015 11:18:04 +0100 Subject: Add REST api to manage actions. --- app/Model/Action.php | 2 +- docs/api-json-rpc.markdown | 236 +++++++++++++++++++++++++++++++++ jsonrpc.php | 59 +++++++++ tests/units/ActionTest.php | 8 +- tests/units/ProjectDuplicationTest.php | 4 +- 5 files changed, 302 insertions(+), 7 deletions(-) diff --git a/app/Model/Action.php b/app/Model/Action.php index 6fb2a2f1..0ba889ba 100644 --- a/app/Model/Action.php +++ b/app/Model/Action.php @@ -248,7 +248,7 @@ class Action extends Base // $this->container['fileCache']->remove('proxy_action_getAll'); - return true; + return $action_id; } /** diff --git a/docs/api-json-rpc.markdown b/docs/api-json-rpc.markdown index eba47dc7..0c303d2c 100644 --- a/docs/api-json-rpc.markdown +++ b/docs/api-json-rpc.markdown @@ -1250,6 +1250,242 @@ Response example: } ``` +### getAvailableActions + +- Purpose: **Get list of available actions** +- Parameters: none +- Result on success: **list of actions** +- Result on failure: **false** + +Request example: + +```json +{ + "jsonrpc": "2.0", + "method": "getAvailableActions", + "id": 1433237746, +} +``` + +Response example: + +```json +{ + "jsonrpc": "2.0", + "id": 1433237746, + "result": { + "TaskLogMoveAnotherColumn" : "Add a comment logging moving the task between columns", + "TaskAssignColorUser" : "Assign a color to a specific user", + "TaskAssignCategoryColor" : "Assign automatically a category based on a color", + "TaskAssignColorCategory" : "Assign automatically a color based on a category", + "TaskAssignSpecificUser" : "Assign the task to a specific user", + "TaskAssignCurrentUser" : "Assign the task to the person who does the action", + "TaskAssignUser" : "Change the assignee based on an external username", + "TaskAssignCategoryLabel" : "Change the category based on an external label", + "TaskClose" : "Close a task", + "CommentCreation" : "Create a comment from an external provider", + "TaskCreation" : "Create a task from an external provider", + "TaskDuplicateAnotherProject" : "Duplicate the task to another project", + "TaskMoveAnotherProject" : "Move the task to another project", + "TaskOpen" : "Open a task" + } +} +``` + +### getAvailableEvents + +- Purpose: **Get list of available events** +- Parameters: none +- Result on success: **list of events** +- Result on failure: **false** + +Request example: + +```json +{ + "jsonrpc": "2.0", + "method": "getAvailableEvents", + "id": 1433237746, +} +``` + +Response example: + +```json +{ + "jsonrpc": "2.0", + "id": 1433237746, + "result": { + "bitbucket.webhook.commit" : "Bitbucket commit received", + "task.close" : "Closing a task", + "github.webhook.commit" : "Github commit received", + "github.webhook.issue.assignee" : "Github issue assignee change", + "github.webhook.issue.closed" : "Github issue closed", + "github.webhook.issue.commented" : "Github issue comment created", + "github.webhook.issue.label" : "Github issue label change", + "github.webhook.issue.opened" : "Github issue opened", + "github.webhook.issue.reopened" : "Github issue reopened", + "gitlab.webhook.commit" : "Gitlab commit received", + "gitlab.webhook.issue.closed" : "Gitlab issue closed", + "gitlab.webhook.issue.opened" : "Gitlab issue opened", + "task.move.column" : "Move a task to another column", + "task.open" : "Open a closed task", + "task.assignee_change" : "Task assignee change", + "task.create" : "Task creation", + "task.create_update" : "Task creation or modification", + "task.update" : "Task modification" + } +} +``` + +### getCompatibleEvents + +- Purpose: **Get list of events compatible with an action** +- Parameters: + - **action_name** (string, required) +- Result on success: **list of events** +- Result on failure: **false** + +Request example: + +```json +{ + "jsonrpc": "2.0", + "method": "getCompatibleEvents", + "id": 1433237746, + "params": [ + "TaskAssignSpecificUser" + ] +} +``` + +Response example: + +```json +{ + "jsonrpc": "2.0", + "id": 1433237746, + "result": { + "task.move.column" : "Move a task to another column", + "task.create_update" : "Task creation or modification", + } +} +``` + +### getActions + +- Purpose: **Get list of actions for a project** +- Parameters: + - **project_id** (integer, required) +- Result on success: **list of actions info** +- Result on failure: **false** + +Request example: + +```json +{ + "jsonrpc": "2.0", + "method": "getActions", + "id": 1433237746, + "params": [ + "1" + ] +} +``` + +Response example: + +```json +{ + "jsonrpc": "2.0", + "id": 1433237746, + "result": [ + { + "id" : "13", + "project_id" : "2", + "event_name" : "task.move.column", + "action_name" : "TaskAssignSpecificUser", + "params" : { + "column_id" : "5", + "user_id" : "1" + } + } + ] +} +``` + +### createAction + +- Purpose: **Create an action** +- Parameters: + - **project_id** (integer, required) + - **event_name** (string, required) + - **action_name** (string, required) + - **params** (list of string pairs, required) +- Result on success: **action_id** +- Result on failure: **false** + +Request example: + +```json +{ + "jsonrpc": "2.0", + "method": "createAction", + "id": 1433237746, + "params": { + "project_id" : "2", + "event_name" : "task.move.column", + "action_name" : "TaskAssignSpecificUser", + "params" : { + "column_id" : "3", + "user_id" : "2" + } + } +} +``` + +Response example: + +```json +{ + "jsonrpc": "2.0", + "id": 1433237746, + "result": 14 + ] +} +``` + +### removeAction + +- Purpose: **Remove an action** +- Parameters: + - **action_id** (integer, required) +- Result on success: **true** +- Result on failure: **false** + +Request example: + +```json +{ + "jsonrpc": "2.0", + "method": "getAvailableEvents", + "id": 1433237746, + "params": [ + "2", + ] +} +``` + +Response example: + +```json +{ + "jsonrpc": "2.0", + "id": 1433237746, + "result": true +} +``` + ### createTask - Purpose: **Create a new task** diff --git a/jsonrpc.php b/jsonrpc.php index 03f007c2..65d4405e 100644 --- a/jsonrpc.php +++ b/jsonrpc.php @@ -76,6 +76,65 @@ $server->bind('enableSwimlane', $container['swimlane'], 'enable'); $server->bind('moveSwimlaneUp', $container['swimlane'], 'moveUp'); $server->bind('moveSwimlaneDown', $container['swimlane'], 'moveDown'); +/** + * Actions procedures + */ +$server->bind('getAvailableActions', $container['action'], 'getAvailableActions'); +$server->bind('getAvailableEvents', $container['action'], 'getAvailableEvents'); +$server->bind('getCompatibleEvents', $container['action'], 'getCompatibleEvents'); +$server->register('getActions', function($project_id) use ($container) { + $actions = $container['action']->getAllByProject($project_id); + foreach($actions as $index => $action) { + $params = array(); + foreach($action['params'] as $param) + $params[$param['name']] = $param['value']; + $actions[$index]['params'] = $params; + } + return $actions; +}); +$server->register('createAction', function($project_id, $event_name, $action_name, $params) use ($container) { + + $values = array( + 'project_id' => $project_id, + 'event_name' => $event_name, + 'action_name' => $action_name, + 'params' => $params + ); + + list($valid,) = $container['action']->validateCreation($values); + if (! $valid) { + return false; + } + + //Check the action exists + if (! isset($container['action']->getAvailableActions()[$action_name])) { + return false; + } + + //Check the event + $action = $container['action']->load($action_name, $project_id, $event_name); + if (! in_array($event_name, $action->getCompatibleEvents())) { + return false; + } + + $required_params = $action->getActionRequiredParameters(); + + //Check missing parameters + foreach($required_params as $param => $value) + if (! isset($params[$param])) { + return false; + } + + //Check extra parameters + foreach($params as $param => $value) + if (! isset($required_params[$param])) { + return false; + } + + return $container['action']->create($values); +}); +$server->bind('removeAction', $container['action'], 'remove'); + /** * Project permissions procedures */ diff --git a/tests/units/ActionTest.php b/tests/units/ActionTest.php index 429a181a..67957a26 100644 --- a/tests/units/ActionTest.php +++ b/tests/units/ActionTest.php @@ -27,7 +27,7 @@ class ActionTest extends Base $this->assertEquals(1, $project->create(array('name' => 'unit_test'))); // We create a new action - $this->assertTrue($action->create(array( + $this->assertEquals(1, $action->create(array( 'project_id' => 1, 'event_name' => Task::EVENT_MOVE_COLUMN, 'action_name' => 'TaskClose', @@ -78,14 +78,14 @@ class ActionTest extends Base $this->assertEquals(1, $c->create(array('name' => 'unit_test'))); // We create a new action - $this->assertTrue($a->create(array( + $this->assertEquals(1, $a->create(array( 'project_id' => 1, 'event_name' => GithubWebhook::EVENT_ISSUE_OPENED, 'action_name' => 'TaskCreation', 'params' => array() ))); - $this->assertTrue($a->create(array( + $this->assertEquals(2, $a->create(array( 'project_id' => 1, 'event_name' => GithubWebhook::EVENT_ISSUE_LABEL_CHANGE, 'action_name' => 'TaskAssignCategoryLabel', @@ -95,7 +95,7 @@ class ActionTest extends Base ) ))); - $this->assertTrue($a->create(array( + $this->assertEquals(3, $a->create(array( 'project_id' => 1, 'event_name' => Task::EVENT_CREATE_UPDATE, 'action_name' => 'TaskAssignColorCategory', diff --git a/tests/units/ProjectDuplicationTest.php b/tests/units/ProjectDuplicationTest.php index b35575aa..311ecc4a 100644 --- a/tests/units/ProjectDuplicationTest.php +++ b/tests/units/ProjectDuplicationTest.php @@ -156,7 +156,7 @@ class ProjectDuplicationTest extends Base $this->assertEquals(1, $p->create(array('name' => 'P1'))); - $this->assertTrue($a->create(array( + $this->assertEquals(1, $a->create(array( 'project_id' => 1, 'event_name' => Task::EVENT_MOVE_COLUMN, 'action_name' => 'TaskAssignCurrentUser', @@ -186,7 +186,7 @@ class ProjectDuplicationTest extends Base $this->assertEquals(2, $c->create(array('name' => 'C2', 'project_id' => 1))); $this->assertEquals(3, $c->create(array('name' => 'C3', 'project_id' => 1))); - $this->assertTrue($a->create(array( + $this->assertEquals(1, $a->create(array( 'project_id' => 1, 'event_name' => Task::EVENT_CREATE_UPDATE, 'action_name' => 'TaskAssignColorCategory', -- cgit v1.2.3