Skip to content

A rails gem for a more "Stateless" tagging experience

License

Notifications You must be signed in to change notification settings

wework/freeze-tag

Repository files navigation

FreezeTag

Howdy,

The de facto tagging library for almost every Ruby on Rails project has been Acts As Taggable On Gem which provides a simple interface for polymorphic tagging of your models.

As excellent and useful as ActsAsTaggable is, this library is attempt to reconcile some shortcomings:

  1. Freeze tag allows for a more "stateless" approach to tagging.

Tags are never deleted, instead they have an "expired_at" column, which can be updated to make them inactive.

  1. The associations are more simple.

Tags are held in a single table which holds the content of the tag (its name) and the association back to the model instance its attached to. This has some advantages including simpler querying, joining, etc., but obviously drawbacks as well.

Installation

Add this line to your application's Gemfile:

gem 'freeze_tag'

And then execute:

$ bundle

Create the tables:

  1. Run the installer:
$ rails g freeze_tag:install

This adds a migration to create your "freeze_tags" table

  1. Confirm your implementation.

Since Freeze tags creates a polymorphic association between tags and models, its necessary to confirm the type of primary keys the models in your application use. Open the migration and choose the correct option for you.

  1. Run the migration
rake db:migrate
  1. Add:
include FreezeTag::Taggable

to the top of any model you'd like to start tagging.

  1. Case sensitivity, add:
def self.freeze_tag_case_sensitive
  true
end

To your model and all tags will be saved as lowercase

Tagging a record:

A single tag:

my_model_instance.freeze_tag(as: "Fancy")

Or apply multiple tags:

my_model_instance.freeze_tag(as: ["Fancy", "Schmancy"])

Or apply multiple tags and expire all other ones:

my_model_instance.freeze_tag(as: ["Fancy", "Schmancy"], expire_others: true)
Tagging a record, with list:

There may be times you want multiple lists of tags, i.e. users with skills, AND hobbies

All the same methods above work, simple pass a list as an argument.

my_model_instance.freeze_tag(as: "Web Design", list: "Skills")
Tagging while creating:

You can also use the same style/attributes to tag while creating instances

my_model_instance = MyModel.new(name: "MyModelName", freeze_tagged: [{
  as: ["Cool", "Beans"],
  list: "Ideas",
  expire_others: true
}])

my_model_instance.save

Accessing tags:

All the current "active" tags as a simple array of strings.

my_model_instance.freeze_tag_list
["Happy", "Go", "Lucky"]

All the tags as a simple array of strings.

my_model_instance.freeze_tag_list(only_active: false)
["Happy", "Go", "Lucky", "Sad"]

All the tags, in a list, as a simple array of strings.

my_model_instance.freeze_tag_list(list: "Skills")
["Web Design", "Illustration"]

Active Record association of all tags

my_model_instance.freeze_tags

Active Record association of all "active" tags

my_model_instance.active_freeze_tags

You can change queries to the above to filter by anything.

my_model_instance.freeze_tags.where(list: "Skills")
my_model_instance.active_freeze_tags.where(list: "Skills")

Retrieving records that have been tagged:

Currently tagged with (only unexpired)

MyModel.freeze_tagged(as: "Fancy")

Previously tagged with (only expired)

MyModel.previously_freeze_tagged(as: "Fancy")

Ever tagged with (expired and unexpired)

MyModel.ever_freeze_tagged(as: "Fancy")

All the above methods work with a "list" argument as well

MyModel.ever_freeze_tagged(as: "Fancy", list: "Skills")

Accessing the model directly.

FreezeTag::Tag

Will give you direct access to the freeze tags table in a very standard way.

Contributing

Bug reports and pull requests are welcome on GitHub at https://github.com/wework/freeze-tag. This project is intended to be a safe, welcoming space for collaboration, and contributors are expected to adhere to the Contributor Covenant code of conduct.

License

The gem is available as open source under the terms of the MIT License.

Code of Conduct

Everyone interacting in the FreezeTag project’s codebases, issue trackers, chat rooms and mailing lists is expected to follow the code of conduct.

Releases

No releases published

Packages

No packages published