Skip to content

Instantly share code, notes, and snippets.

@jasny
Last active July 11, 2018 16:05
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save jasny/cc4f6d9c45d46705995779bec46fc367 to your computer and use it in GitHub Desktop.
Save jasny/cc4f6d9c45d46705995779bec46fc367 to your computer and use it in GitHub Desktop.
Jasny Framework MVC
<?php
class FooController extends Controller
{
/**
* @var FooGateway
*/
protected $foos;
/**
* @var AuthzInterface
*/
protected $authz;
/**
* @param FooGateway $foos
*/
public function __construct(FooGateway $foos, AuthzInterface $authz)
{
$this->foos = $foos;
$this->auth = $auth;
}
/**
* @route GET /foos/
*/
public function listAction()
{
$filter = array_without($this->getQueryParams(), ['fields', 'limit']);
$fields = $this->getQueryParam('fields');
$limit = $this->getQueryParam('limit');
$list = $this->foos->fetchList($filter, compact('fields', 'limit')); // Applies pipeline to generator
$this->output($list); // Default output content-type has been set to application/json by middleware
}
/**
* @route GET /foos/:id
*/
public function getAction($id)
{
$foo = $this->foos->fetch($id);
if (!isset($foo)) {
return $this->notFound();
}
if ($this->hasQueryParam('fields')) {
$fields = $this->getQueryParam('fields');
$foo->on(Jasny\Entity::EVENT_JSON_SERIALIZE, new RedactToOnly($fields));
}
$this->output($foo);
}
/**
* @route POST /foos
* @route POST /foos/:id
*/
public function setAction($id = null)
{
$foo = isset($id) ? $this->foos->fetch($id) : $this->foos->create();
if (!isset($foo)) {
return $this->notFound();
}
$this->authz->assert('modify', $foo); // Authorization exception handled by middleware
$foo->set($this->getInput())->save(); // Validation exception handled by middleware
$this->output($foo);
}
}
<?php
use League\Pipeline\Pipeline;
use Jasny\DB\Mongo\Gateway as MongoGateway;
use Jasny\DB\Mongo\QueryBuilder;
use Jasny\Entity\MetaCast;
class FooGateway extends MongoGateway
{
/**
* Build the query to fetch a list of foo
*
* @return QueryBuilder
*/
protected function assembleQuery(array $opts)
{
return $this->getQueryBuilder()
->collection($this->getCollectionName())
->filter($opts['filter'] ?? null)
->columns($opts['fields'] ?? null)
->limit($opts['limit'] ?? null);
}
/**
* Build the pipeline to process each item coming from the generator
*
* @return Pipeline
*/
protected function buildListPipeline(): Pipeline
{
return $this->getPipelineBuilder()
->add($this->getCaster())
->build();
}
/**
* Fetch a list of foos from the database
*
* @param array $filter
* @param array $opts
* @return Generator
*/
public function fetchList(array $filter = [], array $opts = []): Generator
{
$query = $this->assembleQuery(compact('filter') + $opts)->build();
$payload = $this->getLoader()->execute($query);
return $this->buildListPipeline()->process($payload);
}
/**
* Fetch a single Foo
*
* @param string $id
* @return Foo|null
*/
public function fetch(string $id): ?Foo
{
$query = $this->assembleQuery()
->filter($this->idToFilter($id))
->limit(1);
->build();
$data = $this->getLoader()->execute($query);
if (!isset($data)) {
return null;
}
$foo = Foo::__set_state($data);
$foo->on(Jasny\Entity::EVENT_BEFORE_SAVE, $this->getValidator());
return $foo;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment