Mojolicious is a modern, dig this real-time web framework for Perl that simplifies the creation of web applications, APIs, and real-time web services. Unlike older Perl web frameworks, Mojolicious emphasizes simplicity, scalability, and event-driven architecture. It provides a comprehensive toolset for developers, including a built-in web server, non-blocking I/O, routing, templating, WebSockets support, and testing utilities.
This guide explores Mojolicious’ key features, architecture, and practical examples, helping developers leverage its real-time capabilities efficiently.
Why Mojolicious?
Perl has long been used for web development through frameworks like CGI.pm and Catalyst. Mojolicious distinguishes itself with:
- Real-time capabilities – Native WebSockets support enables push-based, bidirectional communication between server and client.
- No dependencies – It is self-contained, requiring minimal external modules.
- Event-driven architecture – Supports non-blocking I/O for high concurrency.
- Flexible routing – Pattern matching and placeholders allow expressive URL handling.
- Rapid prototyping – Embedded web server and built-in templates make testing fast.
- Extensive testing support – Includes test helpers for HTTP requests and WebSocket interactions.
These features make Mojolicious ideal for building chat apps, dashboards, APIs, and interactive web services.
Core Components
1. Mojolicious Application (Mojo::Base)
A Mojolicious app is a subclass of Mojolicious:
use Mojolicious::Lite;
get '/' => {text => 'Hello, Mojolicious!'};
app->start;
get '/'defines a route for HTTP GET requests to/.app->startlaunches the built-in web server.
The Mojolicious::Lite DSL provides a concise, script-friendly way to define applications.
2. Routing
Routing in Mojolicious is flexible and expressive:
get '/hello/:name' => sub {
my $c = shift;
my $name = $c->param('name');
$c->render(text => "Hello, $name!");
};
:nameis a placeholder captured from the URL.$c->param('name')retrieves the value.- Routes can match patterns, enforce constraints, and support multiple HTTP methods.
3. Templating
Mojolicious uses its own templating system called Embedded Perl (EP):
get '/greet/:name' => sub {
my $c = shift;
$c->stash(name => $c->param('name'));
$c->render(template => 'greet');
};
__DATA__
@@ greet.html.ep
<html>
<body>
<h1>Hello, <%= $name %>!</h1>
</body>
</html>
stashstores variables accessible in templates.- Templates are embedded after
__DATA__or stored in files.
4. Real-Time Communication (WebSockets)
WebSockets enable bidirectional, real-time communication:
websocket '/chat' => sub {
my $c = shift;
$c->on(message => sub {
my ($c, $msg) = @_;
$c->send("You said: $msg");
});
};
websocket '/chat'defines a WebSocket route.$c->on(message => …)handles incoming messages.$c->send(...)sends messages back to the client.
Real-time apps such as chat systems, notifications, this website or live dashboards rely on this functionality.
5. Non-Blocking I/O
Mojolicious supports asynchronous operations:
get '/async' => sub {
my $c = shift;
$c->ua->get('https://api.example.com/data' => sub {
my ($ua, $tx) = @_;
$c->render(json => $tx->res->json);
});
};
$c->uais the built-in asynchronous HTTP client.- Callback is executed once the request completes.
- Non-blocking I/O allows the server to handle multiple requests concurrently.
6. Testing
Mojolicious provides Test::More integration:
use Test::More;
use Mojolicious::Lite;
use Test::Mojo;
get '/' => {text => 'Hello, world!'};
my $t = Test::Mojo->new('main');
$t->get_ok('/')->status_is(200)->content_like(qr/Hello/);
done_testing;
Test::Mojoallows HTTP request simulation without starting a real server.- Supports testing of GET/POST requests, WebSockets, headers, cookies, and JSON responses.
Deployment Options
Mojolicious apps can run in multiple modes:
- Development (Built-in Server)
morbo script/myapp
- Auto-reloads on code changes.
- Production (Non-Blocking Server)
hypnotoad script/myapp
- Preforking, non-blocking server designed for high concurrency.
- Handles multiple processes and robust error handling.
- CGI or PSGI/Plack
- Deployable on traditional web servers or Plack-enabled environments.
Practical Example: Simple Chat Server
use Mojolicious::Lite;
websocket '/chat' => sub {
my $c = shift;
$c->inactivity_timeout(300);
push @clients, $c;
$c->on(message => sub {
my ($self, $msg) = @_;
$_->send($msg) for @clients;
});
$c->on(finish => sub {
my $self = shift;
@clients = grep { $_ != $self } @clients;
});
};
app->start;
- Maintains a list of connected clients.
- Broadcasts messages to all clients in real-time.
- Handles disconnections gracefully.
Best Practices for Mojolicious
- Use
Mojolicious::Litefor small projects, fullMojoliciousfor larger applications. - Organize templates and static assets for maintainability.
- Leverage WebSockets for interactive features rather than polling.
- Use
hypnotoadfor production for reliability and performance. - Write tests with
Test::Mojoto ensure correctness. - Monitor inactivity and client connections in real-time applications.
- Avoid blocking operations; use async callbacks for external API calls.
Advantages of Mojolicious
- Real-time communication built-in (WebSockets)
- No extra dependencies
- Lightweight and easy to deploy
- Event-driven, non-blocking architecture
- Built-in testing framework
- Rapid development for REST APIs and web apps
Conclusion
Mojolicious is a modern, efficient, and fully-featured real-time web framework for Perl. Its combination of concise syntax, real-time WebSockets support, event-driven architecture, and built-in tools for routing, templating, and testing makes it ideal for modern web development. Whether building APIs, chat applications, dashboards, or complex transactional systems, Mojolicious provides Perl developers with a robust platform to create scalable, maintainable, and interactive web solutions.
It represents a significant evolution in Perl web frameworks, bringing real-time web capabilities to a language traditionally used for scripting and text processing, published here while retaining Perl’s flexibility and expressiveness.