Website routing made simple and easy
Tags: productivity, beginners, webdev, clojure
Published: 2018-04-22 20:34:19

---
title: Website routing made simple and easy
published: true
description: Website routing can be easy and simple at the same time, here's how
tags: productivity, beginner, webdev, clojure
---

I was kidding myself for a long time. I thought of myself as  an engineer, I was making complex billion user web apps, I was ENGINEERING the front end and the back end, of course I was. Except I wasn't.

I make websites.

When I finally came around and saw myself how other people see me, I reached website maker enlightenment. I stopped using complex js frameworks, complex backend api tech, I quit graphql, I quit REST APIs, I quit doing stupid stuff, and I started finishing projects.

I want you to finish your projects too, and the first step is to dump those complex frontend frameworks, and maybe embrace the simplicity of clojure.

### How exactly is routing made simple or easy. WTF does that even mean?

I'll show you. Here's a route all by itself

```clojure
[:get "/" `home]
```

Here's two routes

```clojure
[[:get "/" `home]
 [:get "/@:name" `profile]]
```

This is a route in coast on clojure

```clojure
(ns your-project
  (:require [coast.delta :as coast]))

(defn home [request]
  {:status 200
   :headers {"Content-Type" "text/html"}
   :body "Hello world!"})

(def routes [[:get "/" `home]])

(def app (coast/app routes))

(app {:request-method :get :uri "/"}) ; => Hello world!
```

Routes in coast are a vector of vectors, the routes that are on top get matched first.

```clojure
(defn hello [request]
  {:status 200
   :headers {"Content-Type" "text/html"}
   :body "hello world!"})

(defn goodbye [request]
  {:status 200
   :headers {"Content-Type" "text/html"}
   :body "goodbye, cruel world!"})

(def routes [[:get "/" `hello]
             [:get "/" `goodbye]])

(def app (coast/app routes))

(app {:request-method :get :uri "/"}) ; => hello world!
```

If you don't want to write vectors all day, you can use coast's route functions

```clojure
(ns routes
  (:require [coast.router :refer [get post put delete wrap-routes]])
  (:refer-clojure :exclude [get]))

(defn home [request]
  "welcome!")

(defn profile [request]
  (str "hello, " (get-in request [:params :name])))

(def routes (-> (get "/" `home)
                (get "/@:name" `profile)))

(def app (coast/app routes))
```

Here's a more complete example for something like auth with [buddy](https://github.com/funcool/buddy)

```clojure
(ns routes
  (:require [coast.router :refer [get post put delete wrap-routes]]
            [coast.responses :as res]
            [controllers.home :as c.home]
            [controllers.users :as c.users]
            [buddy.auth])
  (:refer-clojure :exclude [get]))

(defn wrap-auth [handler]
  (fn [request]
    (if (buddy.auth/authenticated? request)
      (handler request)
      (res/forbidden
        "I'm sorry dave, I can't let you do that."))))

(def auth (-> (get "/users/:id" `c.users/show)
              (wrap-routes middleware/wrap-auth)))

(def public (get "/" `c.home/index))

(def routes (concat public auth))
```

Routing in [coast on clojure](https://github.com/swlkr/coast) is meant to be easy and meant to be easy to understand. Hopefully I've given you a glimpse into just one aspect of how making websites, not complex over-engineered front end heavy web apps can be made simple and easy.

—

If you're picking up what I'm putting down, give [coast on clojure](https://github.com/swlkr/coast) a try!