---
title: "Restful architecture does not mean one to one mapping"
description:
  "REST style does not mean that we need to have a controller for every model.
  We can mix and match."
canonical_url: "https://www.bigbinary.com/blog/restful-architecture-does-not-mean-one-to-one-mapping-with-model"
markdown_url: "https://www.bigbinary.com/blog/restful-architecture-does-not-mean-one-to-one-mapping-with-model.md"
---

# Restful architecture does not mean one to one mapping

REST style does not mean that we need to have a controller for every model. We
can mix and match.

- Author: Neeraj Singh
- Published: February 17, 2009
- Categories: Rails

Rails makes it easy to adapt Restful architecture. All you have to do is
following.

```ruby
map.resources :pictures
```

I started putting all pictures related activities in `pictures_controller.rb` .
In the beginning it was simple.

Slowly the application evolved. The application started handling two different
types of pictures. There would be pictures for events and then there would be
pictures of users using the system.

One can add comments to the event pictures but one can't add comment to user
pictures. Slowly the requirement for event pictures grew vastly different from
user pictures.

Sounds familiar. Right. Initially controller takes on a few responsibilities but
slowly the controller starts taking a lot more responsibilities and then
controller becomes huge.

The pictures controller was really huge and was fast becoming a mess and
specially writing test was getting very difficult.

Time had come to create two different controllers: one for event pictures and
one for user pictures.

But wait. Lots of people would say that if we want to be restful then there has
to be one to one mapping between the model and the controller. Not true.

## Model != resource

Being restful does not mean that there has be a one to one mapping between the
model and the controller.

I am going to create a new controller called `user_pictures_controller.rb` which
will take on all the functionality related to users dealing with picture. And
this is going to be restful.

```ruby
map.resources :user_pictures
```

Above I have defined a resource called `user_pictures`. To keep it simple this
controller would do only three things.

- display all the pictures of the user ( index )
- allow user to upload pictures ( create )
- allow user to delete a picture ( destroy )

That's the general idea. In my application I have only three actions.

However in the interest of general discussion I am going to show all the seven
methods here. Also for simplicity create in this case means adding a record (I
am not showing multipart upload).

## Controller

Here is the code for controller.

```ruby

# user_pictures_controller.rb

class UserPicturesController < ApplicationController

  def index
    @pictures = Picture.all
  end

  def new
    render
  end

  def create
    @picture = Picture.new(params[:picture])
    if @picture.save
      flash[:notice] = 'Picture was successfully created.'
      redirect_to user_picture_path(:id => @picture.id)
    else
      render :action => "new"
    end
  end

  def show
    @picture = Picture.find(params[:id])
  end

  def edit
    @picture = Picture.find(params[:id])
  end

  def update
    @picture = Picture.find(params[:id])
    if @picture.update_attributes(params[:picture])
      flash[:notice] = 'Picture was successfully updated.'
      redirect_to user_picture_path(:id => @picture.id)
    else
      render :action => "edit"
    end
  end

  def destroy
    @picture = Picture.find(params[:id])
    @picture.destroy

    redirect_to user_pictures_path
  end

end
```

## View

```ruby
# index.html.erb
<h1>Listing pictures</h1>

<table>
  <tr>
    <th>Name</th>
    <th>Quality</th>
  </tr>

<% for picture in @pictures %>
  <tr>
    <td><%=h picture.name %></td>
    <td><%=h picture.quality %></td>
    <td><%= link_to 'Show', user_picture_path(picture) %></td>
    <td><%= link_to 'Edit', edit_user_picture_path(picture) %></td>
    <td>  <%= link_to 'Destroy',  user_picture_path(picture),
                                :confirm => 'Are you sure?',
                                :method => :delete %>

    </td>
  </tr>
<% end %>
</table>


<%= link_to 'New picture', new_user_picture_path %>
```

```ruby
# edit.html.erb
<h1>Editing picture</h1>

<% form_for(:picture,
            :url => user_picture_path(@picture),
            :html => {:method => :put}) do |f| %>
  <%= f.error_messages %>

  <p>
    <%= f.label :name %><br />
    <%= f.text_field :name %>
  </p>
  <p>
    <%= f.label :quality %><br />
    <%= f.text_field :quality %>
  </p>
  <p>
    <%= f.submit "Update" %>
  </p>
<% end %>

<%= link_to 'Show', user_picture_path(@picture) %> |
<%= link_to 'All', user_pictures_path %>
```

```ruby
# new.html.erb
<h1>New picture</h1>

<% form_for(:picture, :url => user_pictures_path, :html => {:method => :post}) do |f| %>
  <%= f.error_messages %>

  <p>
    <%= f.label :name %><br />
    <%= f.text_field :name %>
  </p>
  <p>
    <%= f.label :quality %><br />
    <%= f.text_field :quality %>
  </p>
  <p>
    <%= f.submit "Create" %>
  </p>
<% end %>

<%= link_to 'All', user_pictures_path %>

```

```ruby
# show.html.erb
<p>
  <b>Name:</b>
  <%=h @picture.name %>
</p>

<p>
  <b>Quality:</b>
  <%=h @picture.quality %>
</p>

<%= link_to 'Edit', edit_user_picture_path(:id => @picture) %> |
<%= link_to 'All', user_pictures_path %>
```

## Another use case

Let's talk about another example. Let's say that we have a model called
`Project` and besides the regular functionality of creating, deleting, updating
and listing projects, one needs two more actions called enable and disable
project.

Well the projects controller can easily handle two more actions called "enable"
and "disable". However it is a good idea to create another controller called
`project_status_controller` . This controller should have only two actions -
`create` and `destroy`. `destroy` in this case would mean disabling the project
and `create` would mean enabling the project.

I know it looks counter intuitive. Actions 'enable' and 'disable' seem simpler
than "create" and "destroy". I agree in the beginning adding more actions to
pictures controller looks easy. However if we go down that path then it is a
slippery slope and we do not know when to stop.

Compare that with the RESTful design of having only seven action : `index`,
`show`, `new`, `edit`, `create`, `update`, `destroy`. This limits what a
controller can do and that's a good thing. This ensures that a controller does
not take up too many responsibilities.

Creating another controller allows all the business logic which is not related
to one of those seven actions to be somewhere else.

## One last example

Now that we have the ability to "enable" and "disable" pictures how about
showing "only active", "only inactive" and "all" pictures.

In order to accomplish it once again we can add more actions to the pictures
controller.

However it is much better to have two new controllers.

```ruby
class Pictures::ActiveController < ApplicationController
end

class Pictures::InactiveController < ApplicationController
end
```

Some of you must be thinking what's the point of having a controller for the
sake of having only one action. Well the point is having code that can be
changed easily and with confidence.

## Conclusion

In this blog I tried to show that it is not necessary to have one to one mapping
between model and controllers to be restful. It is always a good idea to create
a separate controller when the existing controller is burdened with too much
work.

## Links

- [Human page](https://www.bigbinary.com/blog/restful-architecture-does-not-mean-one-to-one-mapping-with-model)
