Skip to content

Instantly share code, notes, and snippets.

@phillipsharring
Last active February 13, 2018 12:37
Show Gist options
  • Save phillipsharring/53bc22d001db979481e4 to your computer and use it in GitHub Desktop.
Save phillipsharring/53bc22d001db979481e4 to your computer and use it in GitHub Desktop.
Database Driven Routes in Laravel 5.1
Make a migration to add the routes table to your database.
Use the Schema::create statement in create_routes_table.php
Values will be like so:
+----+----------------+------------------------------+-----------------------------------+
| id | uri | action | params |
+----+----------------+------------------------------+-----------------------------------+
| 1 | about | PagesController@show | "a:1:{s:5:""pages"";i:1;}" |
| 2 | about-us | PagesController@redirect | "a:1:{s:2:""to"";s:5:""about"";}" |
| 3 | something-else | ArbitraryController@redirect | "a:1:{s:3:""foo"";s:3:""bar"";}" |
+----+----------------+------------------------------+-----------------------------------+
Now, your.com/about will show the about page. Presumably PagesController@show will pull
the content from a database using a Page model.
And your.com/about-us will redirect. PagesController@redirect would simply redirect to
an arbitrary URI.
The your.com/something-else link would go somewhere else and do something different.
Use it for pretty URLs, your CMS, short links, you name it. Use your imagination.
It's not perfect. I haven't figured out if/how route model binding works here. I don't think
it can, honestly, so your controllers would have to act accordingly. Alternatively, you could
flesh out the map function with some logic to do the bindings there. Finally, I'm not sure
if this is a good place to put it. Suggestions/improvements welcome. I'm learning; It's something.
<?php
// ...
Schema::create('routes', function (Blueprint $table) {
$table->increments('id');
$table->string('uri');
$table->string('action');
$table->string('params');
});
<?php
// ...
/**
* Define the routes for the application.
*
* @param \Illuminate\Routing\Router $router
* @return void
*/
public function map(Router $router)
{
$router->group(['namespace' => $this->namespace], function ($router) {
require app_path('Http/routes.php');
if (!$this->app->runningInConsole()) {
$uri = substr($this->app->request->getRequestUri(), 1);
$dbRoute = Route::where('uri', '=', $uri)->first();
if ($dbRoute) {
$router->get($uri, function() use ($dbRoute) {
$segments = explode('@', $dbRoute->action);
$controller = $segments[0];
$method = $segments[1];
$obj = $this->app->make($this->namespace . '\\' . $controller);
$params = (!empty($dbRoute->params)) ? unserialize($dbRoute->params) : [];
return call_user_func_array([$obj, $method], $params);
});
}
}
});
}
@eness
Copy link

eness commented Sep 13, 2017

How about that? (Laravel 5+)

<?
// ..
if ($dbRoute) {
    return \App::call($this->namespace . '\\' . $dbRoute->action, unserialize($dbRoute->params));
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment