Skip to content

Instantly share code, notes, and snippets.

@lukemorton
Created December 6, 2012 13:43
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save lukemorton/4224525 to your computer and use it in GitHub Desktop.
Save lukemorton/4224525 to your computer and use it in GitHub Desktop.
Application contract

Application contract

An application must keep to the following rules if it is to stay sane.

ActionController (POST Controller::action_*())

  • Must call one and only one UseCase
  • Must redirect to ViewController

ViewController (GET Controller::action_*())

  • Must call one and only one Data
  • Must set response via Controller::$response::body()

SubViewController (View::__construct())

  • Must only accept an array('view' => ViewModel) as it's second parameter

ViewModel (ViewModel::__construct())

  • Must only accept an array of scalar values, iterables and View objects

Data (Data::retrieve())

  • Must accept an array of data and dependencies
  • Must return an array (or iterable) of scalar values or iterables

UseCase (UseCase::execute())

  • Must accept an array of data and dependencies
  • Must throw exception on validation failure which has method ::errors() to retrieve an array of array('field', 'error')
  • Can return scalar value indicating an ID of a created object (for redirection purposes)
<?php
class EventController {
public function action_create()
{
$data = $this->session()->get('event-create', array());
$this->response->body(new View('event-create', array(
'view' => new EventCreateViewModel($data),
)));
}
public function action_create_post()
{
try
{
$id = EventCreateUseCase::execute(array(
'mapper' => $this->container()->mapper('Events'),
'event' => $this->request->post(),
'user_id' => $this->session()->get('user_id'),
));
}
catch (ValidationException $e)
{
$this->session()->store('event-create', array(
'event' => $this->request->post(),
'errors' => $e->errors(),
));
$this->redirect(Route::url('event-create'));
}
$this->redirect(Route::url('event-view', compact('id')));
}
public function action_edit()
{
$data = EventData::retrieve(array(
'mapper' => $this->container()->mapper('Events'),
'id' => $this->request->param('id'),
'user_id' => $this->session()->get('user_id'),
));
$data['editions'] = $this->session()->get('event-edit', array());
$this->response->body(new View('event-edit', array(
'view' => new EventEditViewModel($data),
)));
}
public function action_edit_post()
{
$id = $this->request->param('id');
try
{
EventEditUseCase::execute(array(
'mapper' => $this->container()->mapper('Events'),
'event' => $this->request->post(),
'user_id' => $this->session()->get('user_id'),
));
}
catch (ValidationException $e)
{
$this->session()->store('event-edit', array(
'event' => $this->request->post(),
'errors' => $e->errors(),
));
$this->redirect(Route::url('event-edit', compact('id')));
}
$this->redirect(Route::url('event-view', compact('id')));
}
protected function action_view($tab_callback)
{
try
{
$data = EventData::retrieve(array(
'mapper' => $this->container()->mapper('Events'),
'id' => $this->request->param('id'),
));
}
catch (NotFoundException $e)
{
throw new HTTPException404;
}
$data['actionbar'] = new View('event-action-bar', array(
'view' => new EventActionBarViewModel($data),
));
$data['tab'] = $tab_callback($data);
$this->response->body(new View('event', array(
'view' => new EventViewModel($data),
)));
}
public function action_timeslots()
{
$this->action_view(function ($data)
{
return new View('event-timeslots', array(
'view' => new EventTimeslotsViewModel($data),
));
});
}
public function action_media()
{
$this->action_view(function ($data)
{
return new View('event-media', array(
'view' => new EventMediaViewModel($data),
));
});
}
protected function action_requests($tab_callback)
{
$this->action_view(function ($data) use ($tab_callback)
{
$data['request_tab'] = $tab_callback($data);
return new View('event-requests', array(
'view' => new EventRequestsViewModel($data),
));
});
}
public function action_outgoing_requests()
{
$this->action_requests(function ($data)
{
return new View('event-outgoing-requests', array(
'view' => new EventOutgoingRequestsViewModel($data),
));
});
}
public function action_incoming_requests()
{
$this->action_requests(function ($data)
{
return new View('event-incoming-requests', array(
'view' => new EventIncomingRequestsViewModel($data),
));
});
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment