NAME
Kelp::Response - Format an HTTP response
SYNOPSIS
Examples of route definitions make a lot more sense when showing how to use this module. Note that in the below examples $self->res
is an instance of Kelp::Response
:
# Render simple text
sub text {
my $self = shift;
$self->res->text->render("It works!");
}
# Render advanced HTML
sub html {
my $self = shift;
$self->res->html->render("<h1>It works!</h1>");
}
# Render a mysterious JSON structure
sub json {
my $self = shift;
$self->res->json->render({ why => 'no' });
}
# Render the stock 404
sub missing {
my $self = shift;
$self->res->render_404;
}
# Render a template
sub view {
my $self = shift;
$self->res->template('view.tt', { name => 'Rick James' } );
}
DESCRIPTION
The PSGI specification requires that each route returns an array with status code, headers and body. Plack::Response
already provides many useful methods that deal with that. This module extends Plack::Response
to add the tools we need to write graceful PSGI compliant responses. Some methods return $self
, which makes them easy to chain.
ATTRIBUTES
render
This method tries to act smart, without being a control freak. It will fill out the blanks, unless they were previously filled out by someone else. Here is what is does:
If the response code was not previously set, this method will set it to 200.
If no content-type is previously set,
render
will set is based on the type of the data rendered. If it's a reference, then the content-type will be set toapplication/json
, otherwise it will be set totext/html
.# Will set the content-type to json $res->render( { numbers => [ 1, 2, 3 ] } );
Last, the data will be encoded with the charset specified by the app.
set_content_type
Sets the content type of the response and returns $self
.
# Inside a route definition
$self->res->set_content_type('image/png');
text, html, json, xml
These methods are shortcuts for set_content_type
with the corresponding type. All of them set the content-type header and return $self
so they can be chained.
$self->res->text->render("word");
$self->res->html->render("<p>word</p>");
$self->res->json->render({ word => \1 });
set_header
Sets response headers. This is a wrapper around "header" in Plack::Response, which returns $self
to allow for chaining.
$self->res->set_header('X-Something' => 'Value')->text->render("Hello");
no_cache
A convenience method that sets several response headers instructing most browsers to not cache the response.
$self->res->no_cache->json->render({ epoch => time });
The above response will contain headers that disable caching.
set_code
Set the response code.
$self->res->set_code(401)->render("Access denied");
render_404
A convenience method that sets code 404 and returns "File Not Found".
sub some_route {
if ( not $self->req->param('ok') ) {
return $self->res->render_404;
}
}
If your application's tone is overly friendly or humorous, you will want to create a custom 404 page. The best way to do this is to subclass this module into your own class, for example MyApp::Response
. Then override the render_404
method.
package MyApp::Response;
use parent 'Kelp::Response';
sub render_404 {
my $self = shift;
$self->set_code(404)->template('errors/404.tt');
}
You'll have to override the "response" in Kelp method in your main module too, in order to instruct it to use your new class:
package MyApp;
use parent 'Kelp';
sub response {
my $self = shift;
return MyApp::Response->new( app => $self );
}
render_500
Renders the stock "500 - Server Error" message. See "render_404" for examples on how to customize it.
template
This method renders a template. The template should be previously configured by you and included via a module. See Kelp::Module::Template for a template module.
sub some_route {
my $self = shift;
$self->res->template('home.tt', { login => 'user' });
}