Created
October 25, 2012 13:17
-
-
Save chanmix51/3952489 to your computer and use it in GitHub Desktop.
REST API with Silex and Pomm
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php // sources/application.php | |
use \Symfony\Component\HttpFoundation\Request; | |
use \Symfony\Component\HttpFoundation\Response; | |
use Symfony\Component\Validator\Constraints as Assert; | |
$app = require "bootstrap.php"; | |
$app['generate_token'] = $app->protect(function(\Taf\Member\Worker $member) use ($app) { return md5($member->getEmail().date('U')); }); | |
$check_token = function(Request $request) use ($app) { | |
if (!$request->headers->get('member-token')) { | |
return new Response('No token provided.', 401); | |
} | |
$where = \Pomm\Query\Where::create("token = ?", array($request->headers->get('member-token'))) | |
->andWhere("created_at + ? > now()", array(sprintf("%d seconds", 1800))); | |
$session = $app['pomm.connection'] | |
->getMapFor('\Taf\Member\Session') | |
->findWhere($where) | |
->current(); | |
if (!$session) { | |
return new Response(sprintf("Invalid or expired token '%s'.", $request->headers->get('member-token')), 401); | |
} | |
$app['taf.session'] = $session; | |
}; | |
/** POST "/workers/{email}/token" | |
* | |
* Create a new token for the given user. | |
* If the user does not exist, it is created. | |
* Set the lastlog attribute for the worker. | |
**/ | |
$app->post('/workers/{email}/session', function($email) use ($app) { | |
$worker_map = $app['pomm.connection']->getMapFor('\Taf\Member\Worker'); | |
$worker = $worker_map | |
->findWhere('email = ?', array($email)) | |
->current(); | |
try | |
{ | |
$app['pomm.connection']->begin(); | |
if (!$worker) { | |
$worker = $worker_map->createAndSaveObject(array('email' => $email)); | |
} | |
$worker['session'] = $app['pomm.connection'] | |
->getMapFor('\Taf\Member\Session') | |
->renew(new \Taf\Member\Session(array('token' => $app['generate_token']($worker), 'worker_id' => $worker['worker_id']))); | |
$app['pomm.connection']->commit(); | |
} | |
catch (\Pomm\Exception\Exception $e) | |
{ | |
$app['pomm.connection']->rollback(); | |
throw new \RuntimeException(sprintf(sprintf("Error while saving session info (member = '%s', token = '%s').", $worker['email'], $worker['session']['token']), 0, $e)); | |
} | |
return $app->json(array('worker' => $worker->extract())); | |
}); | |
$app->get('/tasks', function() use ($app) { | |
$task_map = $app['pomm.connection'] | |
->getMapFor('\Taf\Task\Task'); | |
$tasks = $task_map | |
->findWhere('worker_id = ?', array($app['taf.session']->getWorkerId()), 'ORDER BY created_at DESC'); | |
return $app->json(array('tasks' => $tasks->extract())); | |
})->before($check_token); | |
$app->post('/tasks', function() use ($app) { | |
$new_task = $app['request']->request->get('task'); | |
$new_task['worker_id'] = $app['taf.session']->getWorkerId(); | |
$errors = $app['validator']->validateValue($new_task, new Assert\Collection(array( | |
'fields' => array( | |
'title' => new Assert\MaxLength(100), | |
'content' => new Assert\NotBlank(), | |
'worker_id' => new Assert\Type('integer') | |
), | |
))); | |
if (count($errors) == 0) | |
{ | |
$task = $app['pomm.connection'] | |
->getMapFor('\Taf\Task\Task') | |
->createAndSaveObject((array) $new_task); | |
return $app->json(array('task' => $task->extract()), 201); | |
} | |
return new Response(sprintf("Invalid or missing parameters. === %s ===", print_r($errors, true)), 400); | |
})->before($check_token); | |
$app->delete('/tasks/{id}', function($id) use ($app) { | |
$task = $app['pomm.connection'] | |
->getMapFor('\Taf\Task\Task') | |
->deleteByPk(array('task_id' => $id)); | |
if (!$task) | |
{ | |
return new Response(sprintf("No such task id '%d'.", $id), 404); | |
} | |
return $app->json(array('task' => $task->extract())); | |
})->before($check_token); | |
$app->put('/tasks/{id}', function($id) use ($app) { | |
$update_task = $app['request']->request->get('task'); | |
$errors = $app['validator']->validateValue($update_task, new Assert\Collection(array( | |
'fields' => array( | |
'title' => new Assert\MaxLength(array('limit' => 100)), | |
'time_spent' => new Assert\Min(array('limit' => 0)), | |
), | |
'allowMissingFields' => true) | |
)); | |
if (count($errors) == 0) | |
{ | |
$task = $app['pomm.connection'] | |
->getMapFor('\Taf\Task\Task') | |
->updateByPk(array('task_id' => $id), $update_task); | |
if (!$task) | |
{ | |
return new Response(sprintf("No such task id '%d'.", $id), 404); | |
} | |
return $app->json(array('task' => $task->extract())); | |
} | |
return new Response(sprintf("Bad parameters. == %s ==.", print_r($errors, true)), 400); | |
})->before($check_token); | |
$app->get('/tasks/{id}', function($id) use ($app) { | |
$task = $app['pomm.connection'] | |
->getMapFor('\Taf\Task\Task') | |
->findByPk(array('task_id' => $id)); | |
if ($task) | |
{ | |
return $app->json(array('task' => $task->extract())); | |
} | |
return new Response(sprintf("No such task id='%d'.", $id), 404); | |
})->before($check_token); | |
$app->delete('/token', function() use ($app) | |
{ | |
$app['pomm.connection'] | |
->getMapFor('\Taf\Member\Session') | |
->deleteOne($app['taf.session']) | |
; | |
return new Response(null, 202); | |
})->before($check_token); | |
return $app; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php #sources/bootstrap.php | |
// This script sets up the application DI with services. | |
define('PROJECT_DIR', dirname(__DIR__)); | |
require PROJECT_DIR.'/sources/config/environment.php'; | |
// autoloader | |
$loader = require PROJECT_DIR.'/vendor/autoload.php'; | |
$loader->add('Taf', PROJECT_DIR.'/sources/model'); | |
$loader->add('Validation', PROJECT_DIR.'/sources'); | |
$app = new Silex\Application(); | |
// configuration parameters | |
if (!file_exists(PROJECT_DIR.'/sources/config/config.php')) { | |
throw new \RunTimeException("No config.php found in config."); | |
} | |
require PROJECT_DIR.'/sources/config/config.php'; | |
// extensions registration | |
use Silex\Provider; | |
$app->register(new Provider\ValidatorServiceProvider()); | |
$app->register(new Provider\UrlGeneratorServiceProvider()); | |
$app->register(new Provider\SessionServiceProvider()); | |
$app->register(new Provider\TwigServiceProvider(), array( | |
'twig.path' => array(PROJECT_DIR.'/sources/twig'), | |
)); | |
$app->register(new \Pomm\Silex\PommServiceProvider(), array( | |
'pomm.databases' => $app['config.pomm.dsn'][ENV] | |
)); | |
// Service container customization. | |
$app['loader'] = $loader; | |
$app['pomm.connection'] = $app['pomm'] | |
->getDatabase() | |
->registerTypeForConverter('public.email_address', 'String') | |
->createConnection(new \Pomm\Identity\IdentityMapperSmart()); | |
// set DEBUG mode or not | |
if (preg_match('/^dev/', ENV)) | |
{ | |
$app['debug'] = true; | |
$app['pomm.logger'] = $app->share(function() { return new Pomm\Tools\Logger(); }); | |
$app['pomm.connection'] | |
->registerFilter(new Pomm\FilterChain\LoggerFilter($app['pomm.logger'])); | |
} | |
return $app; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
namespace Taf\Member; | |
use Taf\Member\Base\SessionMap as BaseSessionMap; | |
use Taf\Member\Session; | |
use \Pomm\Exception\Exception; | |
use \Pomm\Query\Where; | |
use \Pomm\Object\BaseObject; | |
class SessionMap extends BaseSessionMap | |
{ | |
public function renew(BaseObject &$object) | |
{ | |
$sql = <<<SQL | |
WITH | |
deleted_session AS (DELETE FROM %s WHERE worker_id = ?) | |
INSERT INTO %s (%s) VALUES (%s) RETURNING %s | |
SQL; | |
$values = $this->convertToPg($object->getFields()); | |
$sql = sprintf($sql, | |
$this->getTableName(), | |
$this->getTableName(), | |
join(', ', array_keys($values)), | |
join(', ', $values), | |
$this->formatFieldsWithAlias('getSelectFields') | |
); | |
$object = $this->query($sql, array($object['worker_id']))->current(); | |
return $object; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment