Skip to content

Commit

Permalink
Add function to have sub routes and list has now paramter q for filte…
Browse files Browse the repository at this point in the history
…r the list
  • Loading branch information
damack committed Feb 11, 2016
1 parent dcf2790 commit b574580
Show file tree
Hide file tree
Showing 8 changed files with 144 additions and 17 deletions.
60 changes: 53 additions & 7 deletions src/RestController.php
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,13 @@ public function getListAction($objectType, Request $request)
->from($objectType, 'o')
;

if ($sort = $request->query->get('_sort')) {
$q = $request->query->get('q');
$foreignKeys = $this->getForeignKeys($request->attributes);
$where = $this->createWhere($queryBuilder, $q, $foreignKeys);
if ($where) {
$queryBuilder->where($where);
}
if ($sort = $request->query->get('sort')) {
$queryBuilder->orderBy($sort, $request->query->get('_sortDir', 'ASC'));
}

Expand All @@ -57,7 +63,7 @@ public function getListAction($objectType, Request $request)
$results = $pager->getSlice($request->query->get('_start', 0), $request->query->get('_end', 20));

foreach($results as &$obj) {
$this->removeHiddenFields($objectType, $obj);
$this->removeHiddenFields($objectType, $obj, $foreignKeys);
}

return new JsonResponse($results, 200, array(
Expand All @@ -68,9 +74,10 @@ public function getListAction($objectType, Request $request)
public function postListAction($objectType, Request $request)
{
$tenant = $request->headers->get('Tenant');
$this->createTable($tenant, $objectType);
$foreignKeys = $this->getForeignKeys($request->attributes);
$this->createTable($tenant, $objectType, $foreignKeys);
try {
$this->dbal[$tenant]->insert($objectType, $request->request->all());
$this->dbal[$tenant]->insert($objectType, array_merge($request->request->all(), $foreignKeys));
} catch (\Exception $e) {
return new JsonResponse(array(
'errors' => array('detail' => $e->getMessage()),
Expand All @@ -96,7 +103,7 @@ public function getObjectAction($objectId, $objectType, Request $request)
if (false === $result) {
return new Response('', 404);
}
$this->removeHiddenFields($objectType, $result);
$this->removeHiddenFields($objectType, $result, $this->getForeignKeys($request->attributes));

return new JsonResponse($result, 200);
}
Expand Down Expand Up @@ -174,7 +181,39 @@ public function getAuthGooglemeAction($objectType, Request $request) {
return new JsonResponse($result, 200);
}

private function removeHiddenFields($schemaName, &$obj) {
private function getForeignKeys($attributes) {
$return = array();
foreach($attributes as $key => $value) {
if(strpos($key, 'Id') && $key !== 'objectId') {
$return[$key] = $value;
}
}
return $return;
}

private function createWhere($queryBuilder, $q, $foreignKeys) {
$return = '';

if ($q) {
$qSplit = explode(',', $q);
foreach($qSplit as $value) {
$valueSplit = explode(':', $value);
if (strlen($return) > 0) {
$return .= ',';
}
$return .= trim($valueSplit[0]) . "=" . $queryBuilder->createPositionalParameter($valueSplit[1]);
}
}
foreach($foreignKeys as $key => $value) {
if (strlen($return) > 0) {
$return .= ',';
}
$return .= $key . "=" . $queryBuilder->createPositionalParameter($value);
}
return $return;
}

private function removeHiddenFields($schemaName, &$obj, $foreignKeys = array()) {
$apiDefinition = $this->app['ramlToSilex.apiDefinition'];
foreach ($apiDefinition->getSchemaCollections() as $schema) {
if (key($schema) == $schemaName) {
Expand All @@ -186,9 +225,12 @@ private function removeHiddenFields($schemaName, &$obj) {
}
}
}
foreach ($foreignKeys as $key => $value) {
unset($obj[$key]);
}
}

private function createTable($tenant, $name) {
private function createTable($tenant, $name, $foreignKeys = []) {
$findTable = false;
$schema = $this->dbal[$tenant]->getSchemaManager();

Expand Down Expand Up @@ -229,6 +271,10 @@ private function createTable($tenant, $name) {
}
}
}
//Add foreign keys
foreach($foreignKeys as $key => $value) {
$table->addColumn($key, 'integer');
}
}
}

Expand Down
16 changes: 9 additions & 7 deletions src/RouteBuilder.php
Original file line number Diff line number Diff line change
Expand Up @@ -38,17 +38,21 @@ public function build(Application $app)
}

$availableRoutes[] = $index;

if (preg_match('/auth/', $route['path'])) {
$route['type'] = str_replace('google', 'Google', str_replace('auth', 'Auth', str_replace('/', '', $route['path'])));
$route['objectType'] = 'users';
} else if (preg_match('/{[\w-]+}/', $route['path'], $identifier)) {
} else if (preg_match_all('/{[\w-]+}/', $route['path'], $identifier) && strrpos($route['path'], "}") === (strlen($route['path']) - 1)) {
$route['type'] = 'Object';
$route['objectType'] = strtolower(str_replace(array('/', $identifier[0]), '', $route['path']));
$route['path'] = str_replace($identifier[0], '{objectId}', $route['path']);
$route['objectType'] = strtolower(str_replace(array('/', $identifier[0][count($identifier[0]) - 1]), '', $route['path']));
$route['path'] = str_replace($identifier[0][count($identifier[0]) - 1], '{objectId}', $route['path']);

//object type is last element
if (strpos($route['objectType'], "}") !== false) {
$route['objectType'] = substr(strrchr($route['objectType'], "}"), 1);
}
} else {
$route['type'] = 'List';
$route['objectType'] = strtolower(str_replace('/', '', $route['path']));
$route['objectType'] = substr($route['path'], strrpos($route['path'], "/") + 1, strlen($route['path']));
}
if (property_exists($app['ramlToSilex.customControllerMapping'], $routePath) && $app['ramlToSilex.customControllerMapping']->{$routePath}) {
$mapping = $app['ramlToSilex.customControllerMapping']->{$routePath};
Expand All @@ -58,14 +62,12 @@ public function build(Application $app)
} else {
$action = 'ramlToSilex.restController:'.strtolower($route['method']).$route['type'].'Action';
}
$name = 'ramlToSilex.'.strtolower($route['method']).ucfirst($route['objectType']).$route['type'];

$controllers
->match($route['path'], $action)
->method($route['method'])
->setDefault('objectType', $route['objectType'])
->setDefault('path', $routePath)
->bind($name)
->before($beforeMiddleware);
}

Expand Down
35 changes: 34 additions & 1 deletion tests/RamlToSilexServiceProviderTest.php
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
<?php

namespace Damack\RamlToSilex;

use Damack\RamlToSilex\RamlToSilexServiceProvider;
Expand Down Expand Up @@ -71,6 +70,15 @@ public function testGetList() {
$this->assertEquals('[{"id":"1","name":"Hans Walter Admin","mail":"hans.walter@gmail.com","role":"Admin","activ":"1"},{"id":"2","name":"Hans Walter Describer","mail":"hans.walter@gmail.com","role":"Describer","activ":"1"},{"id":"3","name":"Hans Walter Anonymous","mail":"hans.walter@gmail.com","role":"Anonymous","activ":"1"}]', $response->getContent());
}

public function testGetListQFilter() {
$request = Request::create('/users?q=role:Admin', 'GET');
$request->headers->set('Authorization', 'Bearer admin');
$request->headers->set('Tenant', 'test');
$response = $this->app->handle($request);

$this->assertEquals('[{"id":"1","name":"Hans Walter Admin","mail":"hans.walter@gmail.com","role":"Admin","activ":"1"}]', $response->getContent());
}

public function testGetListAnonymous() {
$request = Request::create('/users', 'GET');
$request->headers->set('Authorization', 'Bearer anonymous');
Expand Down Expand Up @@ -132,4 +140,29 @@ public function testCustomController() {
$response = $this->app->handle($request);
$this->assertEquals('{"id":"1","name":"Hans Walter Admin","mail":"hans.walter@gmail.com","role":"Admin","activ":"1","token":"admin"}', $response->getContent());
}

public function testToDoPost() {
$request = Request::create('/users/1/todos', 'POST', array(), array(), array(), array('CONTENT_TYPE' => 'application/json'), '{"name":"Test"}');
$request->headers->set('Authorization', 'Bearer admin');
$request->headers->set('Tenant', 'test');
$response = $this->app->handle($request);

$this->assertEquals(201, $response->getStatusCode());
}

public function testToDoGetList() {
$request = Request::create('/users/2/todos', 'GET');
$request->headers->set('Authorization', 'Bearer admin');
$request->headers->set('Tenant', 'test');
$response = $this->app->handle($request);

$this->assertEquals('[]', $response->getContent());

$request = Request::create('/users/1/todos', 'GET');
$request->headers->set('Authorization', 'Bearer admin');
$request->headers->set('Tenant', 'test');
$response = $this->app->handle($request);

$this->assertEquals('[{"id":"1","name":"Test"}]', $response->getContent());
}
}
2 changes: 2 additions & 0 deletions tests/config.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@
"PUT /users/{userId}": "Admin",
"DELETE /users/{userId}": "Admin",
"PUT /users/{userId}/test": "Admin",
"GET /users/{userId}/todos": "Admin",
"POST /users/{userId}/todos": "Admin",
"GET /auth/google/me": "Admin, Describer, Anonymous"
},
"controllers": {
Expand Down
2 changes: 1 addition & 1 deletion tests/controller/CustomController.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ public function __construct($app) {
$this->dbal = $app['dbs'];
}

public function testAction($objectId, $objectType, Request $request) {
public function testAction($objectType, Request $request) {
$tenant = $request->headers->get('Tenant');
$token = $request->headers->get('Authorization') ? $request->headers->get('Authorization') : getallheaders()['Authorization'];
$token = str_replace('Bearer ', '', $token);
Expand Down
24 changes: 23 additions & 1 deletion tests/raml/api.raml
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@ mediaType: application/json
schemas:
- users: !include users.json
- user: !include user.json
- todos: !include todos.json
- todo: !include todo.json

traits:
- oauth2:
Expand Down Expand Up @@ -48,7 +50,7 @@ traits:
Used to use the right site
type: string
required: true

/users:
get:
is: [oauth2, tenant]
Expand Down Expand Up @@ -115,6 +117,26 @@ traits:
description: The resource has been successfully created
500:
description: Some server side error occurred.
/todos:
get:
is: [oauth2, tenant]
description: Gets all todos for a user
responses:
200:
body:
application/json:
schema: todos
post:
is: [oauth2, tenant]
description: Add a new todo for a user
body:
application/json:
schema: todo
responses:
201:
description: The resource has been successfully created
500:
description: Some server side error occurred.
/auth:
/google:
get:
Expand Down
14 changes: 14 additions & 0 deletions tests/raml/todo.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"$schema": "http://json-schema.org/draft-04/schema#",
"title": "Todo",
"type": "object",
"properties": {
"id": {
"type": "integer"
},
"name": {
"type": "string"
}
},
"required": ["name"]
}
8 changes: 8 additions & 0 deletions tests/raml/todos.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
{
"$schema": "http://json-schema.org/draft-04/schema#",
"title": "Collection of Todos for user",
"type": "array",
"items": {
"$ref": "todo.json"
}
}

0 comments on commit b574580

Please sign in to comment.