Simple way to add tags to a Rails model without plugins


How do I implement tags in Rails without plugins?

I have a Rails application, similar to a blog, and I would like add some tags to the posts.

I see that there are some plugins / gems for tagging:

However they all seem cumbersome for my use case (e.g. they include many Rails migrations).

How can I implement tagging in Rails from scratch?


You can add tags to a Rails model (e.g. Post) using PostgreSQL arrays.

First you need to add a new column for tags to your model:

class AddTagsToPosts < ActiveRecord::Migration[7.0]
  def change
    add_column :posts, :tags, :string, array: true, null: false, default: []
    add_index :posts, :tags, using: :gin

This adds an array column for tags to the posts table in the database. It also adds an index in order to filter by tag.

Then in your Post model:

class Post < ApplicationRecord
  before_validation :normalize_tags
  def tag_list= list
    self.tags = list.split(',').map(&:strip)
  def tag_list
    self.tags.join(', ')
  def normalize_tags!(&:parameterize)

We do two different things here:

  • Tag normalization (e.g. convert “My awesome tag!” to “my-awesome-tag“)
  • Define an additional attribute setter and getter in order to deal with tags like comma-separated strings (this can be useful later in the view in order to use a simple text field)

Then in the controller you have:

def post_params
  params.require(:post).permit(:title, :body, :tag_list)

And in the form view:

<%= f.text_field :tag_list %>

Finally you can access tags normally as an array:

@post.tags.each { |t| puts t }