Revel provides primitives that keep the web tier stateless for
predictable scaling. For example, session data is stored in the user
cookie, and the cache is backed by a memcached cluster, redis or in-memory.
Revel is built around composable middleware called filters,
which implement nearly all request-processing
functionality. Developers have the freedom to replace the default
filters with custom implementations (e.g. a custom router).
# get 'revel' framework and command
go get github.com/revel/cmd/revel
# get samples and run chat app
git clone https://github.com/revel/samples.git \
# Run revel application
revel run github.com/revel/samples/chat
# create a new app and run
revel new github.com/myaccount/my-app
This section gives you a taste of various parts of the framework:
More general functionality can be implemented with Filters.
Revel uses a declarative routing syntax. It collects all routes
for an app in a single file, with a simple syntax for matching
requests, extracting arguments from URIs, and specifying
route-specific arguments to the action. Here's a commented
# This file defines all application routes (Higher priority routes first)
GET /login Application.Login # A simple path
GET /hotels/ Hotels.Index # Matches with or without trailing slash
GET /hotels/:id Hotels.Show # Extract an embedded argument
WS /hotels/:id/feed Hotels.Feed # WebSockets.
POST /hotels/:id/:action Hotels.:action # Automatically route some actions.
GET /public/*filepath Static.Serve("public") # Assets served from /public/...
* /:controller/:action :controller.:action # Catch all; Automatic URL generation
Flash. The flash is a cookie that lives for one
request (errors, success messages, etc).
Session. The session is a cryptographically signed
cookie, exposed as a map[string]string.
Results. Redirections take advantage of reverse
routing. Template rendering makes your data available using the
name of the local variable!
Here's an example:
By convention, Revel manages to integrate
easily into the rest of the web app. Here is part of the template
rendered in the Register action shown above.
Revel found it automatically using the name of the action.
field is a simple helper function that returns a map
of validation errors and parameter values for the named field.
The app may inject any helper funcs that it wants.
The title variable is available in the template as if
it had been explicitly put in the RenderArgs. (It's used in
header.html in this case)
Interceptors are controller methods that are run before or after
requests, or in response to panics. By embedding a controller
into another, a developer can share interceptors and fields across
As an example, the database module may be used to open a
connection on initialization, made available through a global
handle. Additionally, embedding the db.Transactional type
adds a sql.Txn field plus interceptors that begin and commit
transactions (or rollback on panic).
Here's what the interceptor looks like (minus error handling):
Here is how it can be mixed in to an application controller:
Filters are the middleware of the application. They are simple
functions with a specific signature:
Even complicated "built-in" functionality like the interceptor
framework is implemented as a filter:
Revel provides a default stack of Filters which the developer can
override. This makes it easy for the developer to select exactly
the parts of the framework that they want to use.
Nearly all framework functionality is implemented in the filters,
and the filter stack is directly exposed to the developer as part
of the configuration. This makes Revel understandable and modular.
There are some areas that could benefit from some TLC.
ORM -- Presently Revel is BYOORM (bring-your-own-ORM). A
good ORM integration would make simple things simple.
Pluggable template loader -- Presently only Go templates
are supported by Revel (although the developer could use their own
library independently). Providing an interface that makes any
template language pluggable would be ideal.