sjmog / ralyxa

A Ruby framework for interacting with Amazon Alexa.
MIT License
180 stars 24 forks source link

Multiple skills #18

Open paveltyk opened 5 years ago

paveltyk commented 5 years ago

Hi, Sam.

Thanks for a great library. I find it well written. The dependency injection pattern you've used makes it really easy to extend.

I run multiple skills in the scope of a single ruby project. I had to tweak Ralyxa::Skill class a bit to achieve the goal. I wonder if you'd be interested in PR that will remain current "singleton" Skill approach, whereas it will also allow instantiating multiple Skills with isolated Intents. Here is an excerpt from the patch. I will provide a PR later if you like the idea/approach.

module Ralyxa
  class Skill
    # Overriden Skill class allows to define multiple skills

    def initialize(handlers = nil)
      @handlers = handlers || {}
    end

    def handle(request, alexa_request_wrapper = Ralyxa::RequestEntities::Request)
      wrapped_request = alexa_request_wrapper.new(request)
      handler = @handlers[wrapped_request.intent_name]

      handler ? handler.new(wrapped_request).handle : warn(handler_not_found(wrapped_request))
    end

    def register_intent_handler(intent_name, handler_base_class = Ralyxa::Handler, &block)
      handler = self.class.build_handler(handler_base_class, &block)

      @handlers[intent_name] = handler
    end

    class << self
      def build_handler(handler_base_class, &block)
        Class.new(handler_base_class).tap do |handler|
          handler.send(:define_method, :handle, &block)
        end
      end
    end

    private

    def handler_not_found(request)
      <<~HEREDOC
        \e[33m
        WARNING: An intent declaration for intent "#{request.intent_name}" was not found.

        To define it, add an intent declaration to your Skill.

        You probably want something like:

        skill = Ralyxa::Skill.new
        skill.register_intent_handler('#{request.intent_name}') do
          respond("Hello World!")
        end
        \e[0m
      HEREDOC
    end
  end
end
digerata commented 5 years ago

@paveltyk I'd be curious to check out what you did to make it work. I have use of multiple skills per server, as well.

paveltyk commented 5 years ago

@digerata Yes. I've described the approach above. Put it somewhere in your initializers maybe?