Search code examples
ruby-on-railsrubyactiverecordrails-generators

How do I attach my rails custom generator to the model one?


Currently, I created an independent generator. When I run rails g query, it works and creates my files well.

Here that code:

# lib/generators/rails/query_generator.rb

require_relative '../my_lib/named_base'

module Rails
  module Generators
    class QueryGenerator < MyLib::Generators::NamedBase
      source_root File.expand_path('templates', __dir__)

      check_class_collision suffix: 'Query'

      def create_model_query
        return if class_name.blank?

        template_file = File.join('app/queries', class_path, "#{file_name}_query.rb")
        template 'query.rb.erb', template_file
      end
    end
  end
end

Now, I want to run the generator when the people run rails g model but I can't achieve it. I try to override the generator model class and use a hook_for to call it but it isn't working. Here the code:

# lib/generators/rails/model_generator.rb

require "rails/generators"
require "rails/generators/rails/model/model_generator"
require_relative './query_generator'

module Rails
  module Generators
    class ModelGenerator < ::Rails::Generators::ModelGenerator
      hook_for :orm, as: :model, in: :rails do |instance, model|
        instance.invoke Rails::Generators::QueryGenerator, [ instance.name ]
      end
    end
  end
end

I hope you can help me. Thanks!


Solution

  • Finally, I found the solution! With the help of Railtie, I could achieve the expected behaviour hooking from the rails model generator.

    # lib/my_gem.rb
    require ...
    require 'my_gem/railtie' if defined?(Rails)
     
    # lib/my_gem/railtie.rb
    
    require 'rails/railtie'
    
    module ActiveModel
      class Railtie < Rails::Railtie
        generators do |app|
          Rails::Generators.configure! app.config.generators
          require_relative '../generators/model_generator'
        end
      end
    end
    
    # lib/generators/model_generator.rb
    
    require 'rails/generators'
    require 'rails/generators/rails/model/model_generator'
    require_relative 'rails/query_generator'
    
    module Rails
      module Generators
        class ModelGenerator
          hook_for :query, type: :boolean, default: true
        end
      end
    end