Blueprint
  • Blueprint Developer Guide
  • Quick Start
    • Getting Started
    • My First Application
      • Creating Your Application
      • Controllers
      • Routers & Routes
      • Services
      • Resources & Resource Controllers
      • Validating & Sanitizing Input
      • Unit Testing Your Application
      • Policies
  • Developer Guide
    • The Object Model
      • Introduction
      • Classes and Instances
      • Computed Properties
      • Aggregated Properties
      • Mixins
    • Routers and Controllers
      • Introduction
      • Routers
      • Controllers
      • Resources
    • Models
    • The Server
    • Policy Framework
    • Services
    • Messaging Framework
    • Configuration Management
    • Application and Resources
      • Lookup Operation
      • Views
      • Assets
    • Blueprint Modules
    • Blueprint Cluster
      • What is a Blueprint Cluster?
      • Running a Blueprint Cluster
      • Technical Details
    • Testing Framework
    • Command-line Interface (Coming Soon)
Powered by GitBook
On this page
  • Defining Your Router
  • Binding Your Route to an Action
  • Integrating with EmberJS
  1. Quick Start
  2. My First Application

Routers & Routes

PreviousControllersNextServices

Last updated 6 years ago

We have with a single action that returns a list of rentals. The controller and its actions by itself cannot handle requests. It is not until we bind a controller's action with a route are we able to handle requests from client.

The route serves as the public facing access point to the Blueprint application. The route is consists of an HTTP verb (e.g., GET, DELETE, POST, and PUT) and a path (e.g., /a/b/c). In the super-rentals example, there is the single route GET /api/rentals. Because we want our Blueprint application to serve as the API service for the super-rentals example, we need our application to define the same route as expect by the EmberJS application.

Defining Your Router

All routes are defined in a router. For our work, we are are going to define our route in the router named rental. There are several approaches we can use when defining a router, which depends on how much reuse we want across a routes paths. The first approach is we can define all routes in a single router with nested definitions. For example:

module.exports = {
  '/a': {
    '/b': {
      // add actions here
    }
  }
}

This approach works well if you are not modularizing your router definition such that a single router focuses on a single aspect of the application. Instead, you have a single monolithic router that defines every route in your application.

As you scale your application to contain routes for many facets of the application, you will find this approach becomes hard to maintain. Moreover, it will be hard to defined inside a since the mounted router may define more routes than you want to expose publicly from your Blueprint application.

The second approach is to modularize your routes across different routers. This approach, however, makes it hard to reuse parts of the routes path across different router definitions. To address this problem, you can place different routers that share common base paths in the same subdirectory structure. The names of the subdirectories will constitute the base paths for the routes defined in each router.

Since we want to plan for growth, and showcase how routers in subdirectories work, we will opt for the second approach of defining routers inside of subdirectories.

As mentioned before, the super-rentals example has a single route GET /api/rentals. Let's assume that if we want to define other routes, they will have the base path /api. We therefore want to define our routers in the subdirectory named api. Let's start with the single router named rental.

app/routers/api/rental.js
const {Router} = require ('@onehilltech/blueprint');

module.exports = Router.extend ({
  specification: {
    '/rentals': {
    
    }
  }
});

As you will notice about, we define a router with the single path /rentals. We do not include /api in the path definition because this router is located in the api subdirectory. This means that routes defined in routers located in the api subdirectory will be prefixed with /api. If we placed this same router in the subdirectory named v1, which is a subdirectory of api, then the base path will be /api/v1.

Defining routers in subdirectories is the recommended approach to versioning routes in your Blueprint application.

Binding Your Route to an Action

We have defined the route for the application, but we need the route to perform an action when the client makes a request to /api/rentals. As previously discussed, the HTTP verb we need to respond to is the GET verb. We already have implemented the action that returns a list of rentals. Let's bind this path to that specific action.

Update the /rental path in the router specification with the code below.

app/routers/api/rental.js
const { Router } = require ('@onehilltech/blueprint');

module.exports = Router.extend ({
  specification: {
    '/rentals': {
      // This statement will bind this route to the get action in the 
      // rental controller. Now, GET /api/rentals can handle client requests.
      get: {action: 'rental@get'}
    }
  }
});

Integrating with EmberJS

app/adapters/application.js
import DS from 'ember-data';

export default DS.JSONAPIAdapter.extend ({
  host: 'http://localhost:5000',
  namespace: 'api'
});

Voila!

There is nothing more that you need to write.

Now, when you use the EmberJS application, you should notice the Blueprint application handling request from the client.

Now, you should be able to go to the url in your favorite browser, and it will display the list of rentals we defined in the .

Since we are basing this tutorial on the , it is only fitting that we show you how to integrate the Blueprint application with the EmberJS super-rental application. There is minimal work needed to replace mirage with this Blueprint application. The main approach is to leverage the power of and in , which allows an EmberJS application to integrate with virtually any backend api service, including Blueprint.

Getting started, we made our life easy by returning data from our route in the because the super-rental application has configured to handle JSON-API by default. We just have to instruct the application to retrieve the data from the Blueprint application instead of from mirage. We do this by implementing an application adapter that defines where the data is located.

You may have to if you do not see the Blueprint application handling requests from the EmberJS application.

super-rental tutorial in EmberJS
adapters
serializers
ember-data
JSON-API specification
ember-data
disable mirage in your EmberJS application configuration
implemented a controller
Blueprint module
http://localhost:5000/api/rentals
mount a router
rental.get action