-
Notifications
You must be signed in to change notification settings - Fork 20
Open
Labels
enhancementNew feature or requestNew feature or request
Description
Since any note should belong to a folder, any note can have an aliase, and any note has an access control model, these features in common should be abstracted away in Rails. Some common approaches:
1. Polymorphic Models
Folder Association
Define a Folder model, and make the association polymorphic if multiple models need to belong to folders:
# app/models/folder.rb
class Folder < ApplicationRecord
has_many :folderables, as: :folderable, dependent: :destroy
end
# app/models/concerns/folderable.rb
module Folderable
extend ActiveSupport::Concern
included do
belongs_to :folderable, polymorphic: true
end
endAlias
An alias can also be modeled using a polymorphic association:
# app/models/alias.rb
class Alias < ApplicationRecord
belongs_to :aliasable, polymorphic: true
end
# app/models/concerns/aliasable.rb
module Aliasable
extend ActiveSupport::Concern
included do
has_one :alias, as: :aliasable, dependent: :destroy
accepts_nested_attributes_for :alias
end
endAccess Control
You can use a role-based model or a simple ownership model to handle access control:
# app/models/access_control.rb
class AccessControl < ApplicationRecord
belongs_to :access_controllable, polymorphic: true
enum access_level: { public: 0, private: 1, restricted: 2 } # Example levels
end
# app/models/concerns/access_controllable.rb
module AccessControllable
extend ActiveSupport::Concern
included do
has_one :access_control, as: :access_controllable, dependent: :destroy
accepts_nested_attributes_for :access_control
end
end2. Applying the Concerns
Use these concerns in your Note model:
# app/models/note.rb
class Note < ApplicationRecord
include Folderable
include Aliasable
include AccessControllable
# Other note-specific logic...
end3. Database Migrations
Run migrations to add polymorphic fields and other attributes:
class CreateFolders < ActiveRecord::Migration[6.1]
def change
create_table :folders do |t|
t.string :name
t.timestamps
end
end
end
class CreateAliases < ActiveRecord::Migration[6.1]
def change
create_table :aliases do |t|
t.string :name
t.references :aliasable, polymorphic: true, index: true
t.timestamps
end
end
end
class CreateAccessControls < ActiveRecord::Migration[6.1]
def change
create_table :access_controls do |t|
t.references :access_controllable, polymorphic: true, index: true
t.integer :access_level, default: 0
t.timestamps
end
end
end4. Usage
Create a note with all these common features:
@folder = Folder.create(name: "Personal Notes")
@note = Note.create(
title: "My Note",
folder: @folder,
alias_attributes: { name: "Shortcut Name" },
access_control_attributes: { access_level: :restricted }
)Benefits
- Reusability: The concerns can be reused in other models like
ArticleorTask. - Decoupling: Separates common logic from the
Notemodel. - Extensibility: You can easily add new features like tagging or versioning.
Reactions are currently unavailable
Metadata
Metadata
Assignees
Labels
enhancementNew feature or requestNew feature or request