At my day job I've been using NextJS lately. In my spare time I've played with SvelteKit. One thing both of these have in common is file-system-based routing. If you've watched my GitHub repos over the last couple of years you'll know I played around with a file-system-based routing system once, though on a much simpler route. But why?

When working on Myth:work, it was an experiment to see if we could find some way simpler that would provide the tools we needed but remove as many of the barriers to building a site. And maybe even bring back some of the fun of rapid building for the fun of it.

In a reboot of a personal project I'm working on, I've started exploring how we can make a similar feeling, but within CodeIgniter. I'm currently calling it "View First Development". There's one big caveat here - this only works for pages that have something to display. It doesn't work for API routes, as you would imagine.

Here's how it works:

  • Step Zero - forget the controllers. Seriously. You don't need them.
  • One - create a view for the page you're working on. This will extend a layout so you get a consistent page going.
  • Two - create a route that does nothing but display the page. If the route has any placeholders, pass them to the view.
  • Use View Cells to handle dynamic data within the views. These become cacheable widgets or components, however, you prefer to think of them.
  • That's it.

An example?

Let's do a store page that displays a page of products.

  1. The route:
    $routes->get('products/(:segment)', function() {
       return view('product_list', ['category' => service('request')->getURI()->getSegment(0)]);

Not the prettiest thing. On the plus side, I've got a PR in to simplify this. Once 4.3 is released you would be able to do this instead:

    $routes->view('products/(:segment)', 'product_list');

The segments are available within the view in a $segments array.

  1. The View
    <?= $this->extends('master') ?>
   <?= $this->section('main') ?>
       <h1>Products: <?= $category ?></h1>

        <?= view_cell('App\Cells\Products::list', ['category' => $category]) ?>
   <?= $this->endSection() ?>
  1. The Cell

    namespace App\Cells;

    class Products

        public function list(array $params)
            $model = model('ProductModel');

             return view('products/list', [
                'products' => $model
                    ->where('category', $params['category'])

The 'products/list' view would take care of displaying the products in whatever format you wanted.

Going Interactive

You can get an experience very similar to an SPA by using light Javascript frameworks like HTMX and AlipineJS. Using HTMX you can easily make your products table interactive by simply hitting the server and returning HTML. You can also "boost" main navigation where it does an AJAX call and replaces the page must faster than it normally would, all with animations that can work across page loads.

You could make your cell views interactive with these tools very simply.

But why?

What is about this way of development that has me excited? It allows solo devs, or devs that haven't mastered frontend development just yet, a way to build interactive websites much faster, and with significantly less complexity, than loading up a front-end site built with React, Vue, or any of the other fantastic frameworks out there.

Any Future For This?

I'm going all in on this. I'm currently really enjoying developing this way but I think we can go even farther.

I'm starting to work on a completely revamped View Cells layer that makes Cells more powerful and easier to work with. That's setting the stage for Live Cells - view cells that become interactive without any additional Javascript requirements from you. If you've heard of Laravel Livewire, or Pheonix LiveView, or Symfony's Live Components, you'll have an idea where it's heading.

I'm talking with the team about how much of this will make it to core. So far, the response is fairly positive, but we're still talking. We'll see how it progresses. Even if it doesn't make it to core, it will be a package you can pull in and use in your own projects.

Your Thoughts

What do you think? Is this direction appealing to you? Are there ways you'd like to see if develop?

Oh - and what would a cool name for this be? :)