Skip to content

Instantly share code, notes, and snippets.

@arrobeusa
Last active August 29, 2015 14:21
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 arrobeusa/295dedd61ffe4f39d019 to your computer and use it in GitHub Desktop.
Save arrobeusa/295dedd61ffe4f39d019 to your computer and use it in GitHub Desktop.
A web services pattern with MongoDB and Symfony
namespace AppBundle\Controller;
use AppBundle\Document\Report;
use AppBundle\Form\ReportType;
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use FOS\RestBundle\View\View,
FOS\RestBundle\View\ViewHandler,
FOS\RestBundle\View\RouteRedirectView;
use FOS\RestBundle\Controller\FOSRestController;
use Symfony\Component\Routing\Route;
/**
* Class ReportsController
* @package AppBundle\Controller
*/
class ReportsController extends Controller
{
/**
* @return View
*/
public function listAction()
{
$reports = $this->get('doctrine_mongodb')
->getRepository('AppBundle:Report')
->findAll()
;
$view = View::create(array(
'circles' => $reports
));
return $this->get('fos_rest.view_handler')->handle($view);
}
/**
* @param Request $request
* @return View
*/
public function createAction(Request $request)
{
$form = $this->createForm(new ReportType(), new Report());
$form->handleRequest($request);
if ($form->isValid()) {
$report = $form->getData();
$dm = $this->get('doctrine_mongodb')->getManager();
$dm->persist($report);
$dm->flush();
$view = View::create(array('report' => $report));
}
else {
$view = View::create($form);
$view->setStatusCode(400);
}
$view->getFormat('json');
return $this->get('fos_rest.view_handler')->handle($view);
}
/**
* @param $id
* @return View
*/
public function showAction($id)
{
$report = $this->get('doctrine_mongodb')
->getRepository('AppBundle:Report')
->find($id)
;
$view = View::create($report);
return $this->get('fos_rest.view_handler')->handle($view);
}
}
<?php
namespace RM\Document;
use RM\Document\ReportColumn;
use RM\Document\FilterGroup;
use RM\Document\User;
use Doctrine\Common\Collections\ArrayCollection;
use Doctrine\ODM\MongoDB\Mapping\Annotations as MongoDB;
/**
* @MongoDB\Document(repositoryClass="RM\Document\ReportRepository")
*/
class Report
{
/**
* @MongoDB\Id
*/
public $id;
/**
* @MongoDB\String
*/
public $name;
/**
* @MongoDB\String
*/
public $slug;
/**
* @MongoDB\String
*/
public $type;
/**
*
* MongoDB\ReferenceOne(targetDocument="User")
*/
public $user;
/**
* @MongoDB\String
*/
public $category;
/**
* @MongoDB\EmbedMany(targetDocument="FilterGroup")
*/
public $filter_groups;
/**
* @MongoDB\EmbedMany(targetDocument="ReportColumn")
*/
public $report_columns;
/**
* @MongoDB\Date
*/
public $created;
/**
* @MongoDB\Date
*/
public $updated;
/**
* @MongoDB\String
*/
public $description;
/**
* @MongoDB\Boolean
*/
public $is_deleted = false;
/**
* @MongoDB\Boolean
*/
public $is_runnable = false;
}
?>
<?php
namespace AppBundle\EventListener;
use Symfony\Component\DependencyInjection\Container;
use Symfony\Component\HttpFoundation\Session\Session;
use Symfony\Component\HttpKernel\Event\GetResponseEvent;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
class MongoReadPreferredSubscriber implements EventSubscriberInterface
{
/**
* @var Session
*/
protected $session;
/**
* @var Container
*/
protected $container;
public function __construct(Container $container)
{
$this->container = $container;
}
public function postPersist($event)
{
$this->container->get('session')->getFlashBag()->set('READ_PREFERENCE', \MongoClient::RP_PRIMARY);
}
public function postUpdate()
{
$this->container->get('session')->getFlashBag()->set('READ_PREFERENCE', \MongoClient::RP_PRIMARY);
}
/**
* @param GetResponseEvent $event
*/
public function onKernelRequest(GetResponseEvent $event)
{
$this->session = $event->getRequest()->getSession();
$readPreference = $this->session->getFlashBag()->get('READ_PREFERENCE', array(\MongoClient::RP_SECONDARY_PREFERRED));
$this->container->get('doctrine_mongodb.odm.default_connection')->getMongo()->setReadPreference($readPreference[0]);
}
}
?>
Feature: Reports Web Service
Scenario: Valid CRUD requests
Given body of request:
"""
{
"name": "My Special Report",
"description": "The description of my special report"
}
"""
When I make a POST request to "/reports/"
Then the status code should be 200
When I make a GET request to "/reports/5453ce5ee02222341b0000ea/"
Then the status code should be 200
Then the response should be:
"""
[
{
"id" : "5453ce5ee02222341b0000ea",
"user" : { "id": "5453ce5de0945657b00000a" },
"name" : "Sam Witwicky",
"slug" : "sam-witwicky",
"type" : "custom",
"description" : "Cool human",
"category" : "Humans",
"updated" : "2015-02-24T03:00:57.802Z",
"created" : "2015-02-24T03:00:57.802Z",
"is_runnable" : true,
"filter_groups" : [
{
"id" : "5453ce5ee0909e9f1b0000eb",
"filters" : [
{
"id" : "5453ce5ee0909e9f1b0000ed",
"operator" : ">=",
"default_value" : "2012-01-01",
"column" : { "id": "5453ce5de0909e9f1b000028" }
},
{
"id" : "5453ce5ee0909e9f1b0000ec",
"operator" : "<=",
"default_value" : "2013-01-01",
"column" : { "id": "5453ce5de0909e9f1b000028" }
}
]
}
],
"report_columns" : [
{
"id": "5453ce5ee0909e9f1b0000f1",
"format" : "string",
"sort_sequence" : 0,
"sort_direction" : "asc",
"position" : 0,
"column" : { "id": "5453ce5de0909e9f1b000019" }
},
{
"id": "5453ce5ee0909e9f1b0000f0",
"format" : "date",
"sort_sequence" : 1,
"sort_direction" : "asc",
"position" : 1,
"column" : { "id": "5453ce5de0909e9f1b000028" }
},
{
"id": "5453ce5ee0909e9f1b0000ef",
"format" : "number",
"sort_sequence" : 2,
"sort_direction" : "asc",
"position" : 2,
"column" : { "id": "5453ce5de0909e9f1b000052" }
},
{
"id": "5453ce5ee0909e9f1b0000ee",
"format" : "number",
"sort_sequence" : 3,
"sort_direction" : "asc",
"position" : 3,
"column" : { "id": "5453ce5de0909e9f1b00005a" }
}
],
"is_deleted" : false
}
}
]
"""
{
"_id" : ObjectId("5453ce5ee02222341b0000ea"),
"user" : DBRef("User", "5453ce5de0945657b00000a"),
"name" : "Sam Witwicky",
"slug" : "sam-witwicky",
"type" : "custom",
"description" : "Cool human",
"category" : "Humans",
"updated" : ISODate("2015-02-24T03:00:57.802Z"),
"created" : ISODate("2015-02-24T03:00:57.802Z"),
"is_runnable" : true,
"filter_groups" : [
{
"_id" : ObjectId("5453ce5ee0909e9f1b0000eb"),
"filters" : [
{
"operator" : ">=",
"default_value" : "2012-01-01",
"column" : DBRef("Column", ObjectId("5453ce5de0909e9f1b000028")),
"_id" : ObjectId("5453ce5ee0909e9f1b0000ed")
},
{
"operator" : "<=",
"default_value" : "2013-01-01",
"column" : DBRef("Column", ObjectId("5453ce5de0909e9f1b000028")),
"_id" : ObjectId("5453ce5ee0909e9f1b0000ec")
}
]
}
],
"report_columns" : [
{
"format" : "string",
"sort_sequence" : 0,
"sort_direction" : "asc",
"position" : 0,
"column" : DBRef("Column", ObjectId("5453ce5de0909e9f1b000019")),
"_id" : ObjectId("5453ce5ee0909e9f1b0000f1")
},
{
"format" : "date",
"sort_sequence" : 1,
"sort_direction" : "asc",
"position" : 1,
"column" : DBRef("Column", ObjectId("5453ce5de0909e9f1b000028")),
"_id" : ObjectId("5453ce5ee0909e9f1b0000f0")
},
{
"format" : "number",
"sort_sequence" : 2,
"sort_direction" : "asc",
"position" : 2,
"column" : DBRef("Column", ObjectId("5453ce5de0909e9f1b000052")),
"_id" : ObjectId("5453ce5ee0909e9f1b0000ef")
},
{
"format" : "number",
"sort_sequence" : 3,
"sort_direction" : "asc",
"position" : 3,
"column" : DBRef("Column", ObjectId("5453ce5de0909e9f1b00005a")),
"_id" : ObjectId("5453ce5ee0909e9f1b0000ee")
}
],
"is_deleted" : false
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment