Note: Numbers in square brackets correspond to the Component Interaction Flows
- Whenbot Gem Responsibilities
- Whenbot UI Responsibilities
- Channel Responsibilities
- Service Class Responsibilities
- Trigger Responsibilities
- Action Responsibilities
- Other Components (Responsibilities)
- Scheduler
- Authentication / OAuth Module
- Generators / Rake Tasks
- Setup Tasks
- Keeps track of all registered Channels
- Adds each registered Channel to its internal list
- This list will be used:
- For displaying the Channel list
- To find the Channel's Triggers and Actions
- This list will be used:
- Determines if a Channel has any Triggers (via metaprogramming)
- Gets a list of Triggers from a specified channel (via metaprogramming)
- Determines if a Channel has any Actions (via metaprogramming) [18]
- Gets a list of Actions for a specified Channel (via metaprogramming) [17]
- Authentication [7, 21]
- Check if a Trigger / Action has authentication credentials stored in the database
- Q: Shouldn't the Trigger / Action do this?
- Store authentication credentials in the database, and encrypt fields as needed
- Retrieve and decrypt authentication credentials from the database
- Return if a specified Trigger has authentication credentials in the database
- Test authentication credentials by trying to connect to the webservice before storage (should this be the Channel's responsibility?)
- Authentication Questions:
- Should the individual Channels handle most of this?
- How will Trigger / Action authors test their authentication schemes?
- Should we just have the User store their credentials in ENV, and we get it via a hash?
- I.e. The user would set
options[:auth_hash][:provider], options[:auth_hash][:oauth_token]
, etc., perhaps viaconfig
or something. - The User should be encouraged to store these as environment variables on their system, for now.
- Then, we can add in storing it in the database later.
- This would likely make it easier for initial Trigger / Action development as well.
- We can store credentials in the database in a future iteration
- I.e. The user would set
- Storage of Tasks in the database
- Task Table Fields:
trigger_channel:string
trigger:string
trigger_parameters:text
is_polling_trigger:boolean
action_channel:string
action:string
action_params:text
extras:text
- Requests the Trigger to register its Webhook, when appropriate
- Accepts Webhook callbacks
- Relays webhook callback data to the appropriate Trigger * We should consider moving this to middleware (e.g. Sinatra) actually, to avoid a lot of the Rails stack, which we don't really need here.
- Stores / retrieving Webhook registration details (?) (Should the Trigger do this?)
- Requests appropriate Triggers to perform their polls on regular intervals
* Done by loading all Tasks that have
is_polling_trigger
set totrue
- List all Triggers on a single page for the user
- Check if a Trigger has authentication credentials stored in the database (via Gem)
- Determine (via Gem) if a particular Channel uses OAuth or basic_http_auth for authentication
- Should this be via an option flag, a query / call to the Channel (or should this be based on action?), or perhaps a table field (if we're storing the credentials in the database)?
- Display the OAuth / basic_http_auth inputs to gather authentication credentials from the User for storage * Update: As noted above, for the initial version, it may be better to just have a hash of settings, set by the User via config. This is a private, single-user app; so it's not necessary to have a table of credentials. Although, one added benefit would be that we could encrypt the info easily if it was stored in the database. It can be encrypted for storage in the environment as well, but that's more of a pain for the User.
- Display a list of Trigger Channels to the User [4]
- Displays the list of Triggers (for a selected Trigger Channel) to the User [10]
- Generates and displays the appropriate form fields to ask for the Parameters required for a specific Trigger [15]
- Displays a list of Action Channels to the User [19]
- Generates and displays the appropriate UI and form fields to ask for the Parameters required for a specific Action [15]
- Registers with Whenbot Gem, to make it aware of its presence
- Via
config
. - Or, if we want to get fancy, we can automate this with an
#include module
->included do
approach.- Note: For the beginners, it may make it easier to understand what's going on if they just use a
config
block.
- Note: For the beginners, it may make it easier to understand what's going on if they just use a
- Via
- Needs to keep standard
Triggers
andActions
module names, so that the Whenbot Gem can detect any Triggers and Actions.
- Handles the WebService interactions
- What classname should we use for this? Does it need to be standard?
- E.g.
class Service
,class Client
, orclass GmailService
,class GmailClient
1. Connects to the web service
2. Sets up any webhooks, based on the given Trigger and Parameters
3. Polls the service upon request, for the given Triggers and Paramerts
- Gives a display name to be shown by the Gem UI
- Gives a description to be shown by the Gem UI
- Provides a list of Parameters to be gathered from the user when this Trigger is selected. [14]
- Creating a poll request when asked, to see anything has happened that should set off a Trigger
- Check webhook / poll result data to see if the Trigger should be fired
- Gives a display name to be shown by the Gem UI
- Gives a description to be shown by the Gem UI
- Provides a list of Parameters to be gathered from the user when this Action is selected. [26]
- Performs Action, with given parameters, upon request.
- Handles scheduling of polls
- Really, this is just a method that gets called by a cron job, which in turn calls each Trigger that has to poll for its data.
- Should we get the individual Channel authors to handle this stuff?
- Using config?
- Each user can get their own API key, or store their credentials in their environment, for access via ENV (or elsewhere, if they prefer)
- The Channels will need to be able to authentication to the service on connection
- So, there could be GmailChannel::Service::AUTH hash... or something?
- Can be called by something like
rails generate whenbot:install
- We should generate / update any needed files
- Routes (if relaying via Rails):
match 'webhooks/:channel/callback', to: 'webhooks#callback'
- Or, a Sinatra app may be better. Push to v2?
- controller file(s)
/app/controllers/webhooks
, along with thecallback
method
- Routes (if relaying via Rails):
- Database setup
In order for a user to get started with using Whenbot, they have to do the following:
- Add the Whenbot Gem to their Gemfile: ``gem 'whenbot'`
- Run
bundle install
- Run
rails generate whenbot:install
. This command will: * setup the database tables * Add any needed routes * Create controllers and view code as needed - Add any Channels they would like to use to their Gemfile
* E.g.
gem `whenbot-gmail'
- Run
bundle install
- Add the following to
config/initializers/whenbot.rb
:
# Assuming we're adding the GmailChannel here
Whenbot.config do |config|
config.add_channel Whenbot::GmailChannel
end