Lesson 2
Controllers in Rails
Introduction to Controllers in Rails

Hello and welcome! Today, we'll dive into Controllers in Ruby on Rails. Controllers are pivotal in the framework used by Rails. They manage the flow between the model and the client, handle requests, and render appropriate responses. Let's dive into the lesson content!

Understanding Controllers

Controllers in Rails play a pivotal role in this architecture. They are essentially classes that handle HTTP requests and provide suitable responses. Controllers facilitate the flow of data between the model and the view, ensuring the appropriate data is presented to the user. They query data from the model, process user input, and render different types of responses such as HTML and JSON. Common tasks handled by controllers include CRUD (Create, Read, Update, Delete) operations, managing user authentication and authorization, and rendering different formats like HTML and JSON.

Controllers in Rails follow a specific naming convention where the name is pluralized. For example, a controller managing "Todo" items is named TodosController. Understanding these concepts provides a clearer picture of how controllers fit into the Rails framework. This convention allows us to be able to generate routes using resources keyword. E.g. resources :users generates all the routes involving the controller actions and expects a UsersController defined.

Creating a Basic Controller

Now that we've covered how controllers work and what their role is in Rails, let’s implement a basic controller for our ToDo app. We can generate a controller using the Rails command-line tool:

Bash
1rails generate controller Todos

This command will create a new TodosController and associated files in the app/controllers directory.

After generating the controller, you’ll find an app/controllers/todos_controller.rb file containing the controller code. Controllers in Rails follow a naming convention: the file name must match the class name. For example, todos_controller.rb corresponds to the class TodosController. If you deviate from this convention, Rails will not be able to automatically load the controller, leading to errors when handling requests.

Creating a Basic Action

With the controller created, we will need to implement functionality. We will define an action (a method within the controller that is mapped to a particular URL and HTTP method) to handle incoming requests:

Ruby
1class TodosController < ApplicationController 2 def index 3 # Action to be run 4 end 5end

This code defines a controller called TodosController, inherited from the ApplicationController. The ApplicationController is the base controller class in Rails from which all other controllers inherit, providing common functionality and shared behavior across the entire application.

As you can see, it defines the action index as the code to be run when the GET request has been received. Actions within controllers follow naming conventions such as:

  • index for listing multiple records (corresponding to GET)
  • show for displaying a single record (corresponding to GET)
  • create for creating a new record (corresponding to POST)
  • update for updating an existing record (corresponding to PUT/PATCH)
  • destroy for deleting a record (corresponding to DELETE)

It is also possible to create routes with custom action names beyond the common ones. However, if you do this, make sure that the action names in your controller match the custom routes defined in config/routes.rb. For example, if you define a custom action complete in your TodosController, you need to create a corresponding route in your routes file to ensure proper mapping.

Adding Functionality to the Action

While normally we would have some sort of back-end, for demonstrational purposes, we will directly define the data within the action. This helps demonstrate the functionality without needing to set up additional back-end components. In this example, the index action fetches all todo items directly within the controller:

Ruby
1class TodosController < ApplicationController 2 def index 3 todos = [ "Todo 1", "Todo 2", "Todo 3" ] 4 render json: { todos: todos }, status: :ok 5 end 6end

After retrieving the data for our todo list, we will need to render the response. A common response is to format the data into the JSON format using the render method. By calling render json: { todos: todos }, we tell Rails to render the response in JSON format, with a key called todos receiving the value of the variable todos we defined.

Additionally, you can set HTTP status codes in responses, using the status: [status] parameter. Common status codes include:

  • :ok (200) for successful responses.
  • :created (201) for successful resource creation.
  • :not_found (404) for resources that aren’t found.
Summary

In this lesson, we explored the role and purpose of controllers in Rails, created and configured a basic controller, and wrote actions to handle requests and render JSON responses. This knowledge will help you manage various HTTP requests and control the flow of data seamlessly in your Rails applications.

Enjoy this lesson? Now it's time to practice with Cosmo!
Practice is how you turn knowledge into actual skills.