#!/usr/bin/env ruby # encoding: utf-8 require 'twitter_ebooks' require 'csv' $debug = true module Ebooks::CLI APP_PATH = Dir.pwd # XXX do some recursive thing instead def self.new(reponame) usage = < Creates a new skeleton repository defining a template bot in the current working directory specified by . STR if reponame.nil? log usage exit end path = "./#{reponame}" if File.exists?(path) log "#{path} already exists. Please remove if you want to recreate." exit end FileUtils.cp_r(SKELETON_PATH, path) File.open(File.join(path, 'bots.rb'), 'w') do |f| template = File.read(File.join(SKELETON_PATH, 'bots.rb')) f.write(template.gsub("{{BOT_NAME}}", reponame)) end log "New twitter_ebooks app created at #{reponame}" end def self.consume(pathes) usage = < [corpus_path2] [...] Processes some number of text files or json tweet corpuses into usable models. These will be output at model/.model STR if pathes.empty? log usage exit end pathes.each do |path| filename = File.basename(path) shortname = filename.split('.')[0..-2].join('.') outpath = File.join(APP_PATH, 'model', "#{shortname}.model") Model.consume(path).save(outpath) log "Corpus consumed to #{outpath}" end end def self.consume_all(name, paths) usage = < [corpus_path2] [...] Processes some number of text files or json tweet corpuses into one usable model. It will be output at model/.model STR if paths.empty? log usage exit end outpath = File.join(APP_PATH, 'model', "#{name}.model") #pathes.each do |path| # filename = File.basename(path) # shortname = filename.split('.')[0..-2].join('.') # # outpath = File.join(APP_PATH, 'model', "#{shortname}.model") # Model.consume(path).save(outpath) # log "Corpus consumed to #{outpath}" #end Model.consume_all(paths).save(outpath) log "Corpuses consumed to #{outpath}" end def self.gen(model_path, input) usage = < [input] Make a test tweet from the processed model at . Will respond to input if provided. STR if model_path.nil? log usage exit end model = Model.load(model_path) if input && !input.empty? puts "@cmd " + model.make_response(input, 135) else puts model.make_statement end end def self.score(model_path, input) usage = < Scores "interest" in some text input according to how well unique keywords match the model. STR if model_path.nil? || input.nil? log usage exit end model = Model.load(model_path) model.score_interest(input) end def self.archive(username, outpath) usage = < Downloads a json corpus of the 's tweets to . Due to API limitations, this can only receive up to ~3000 tweets into the past. STR if username.nil? || outpath.nil? log usage exit end Archive.new(username, outpath).sync end def self.tweet(modelpath, botname) usage = < Sends a public tweet from the specified bot using text from the processed model at . STR if modelpath.nil? || botname.nil? log usage exit end load File.join(APP_PATH, 'bots.rb') model = Model.load(modelpath) statement = model.make_statement log "@#{botname}: #{statement}" bot = Bot.get(botname) bot.configure bot.tweet(statement) end def self.auth consumer_key, consumer_secret = find_consumer require 'oauth' consumer = OAuth::Consumer.new( consumer_key, consumer_secret, site: 'https://twitter.com/', scheme: :header ) request_token = consumer.get_request_token auth_url = request_token.authorize_url() pin = nil loop do log auth_url log "Go to the above url and follow the prompts, then enter the PIN code here." print "> " pin = STDIN.gets.chomp break unless pin.empty? end access_token = request_token.get_access_token(oauth_verifier: pin) log "Account authorized successfully.\n" + " access token: #{access_token.token}\n" + " access token secret: #{access_token.secret}" end def self.c load_bots require 'pry'; pry end # Non-command methods def self.find_consumer if ENV['CONSUMER_KEY'] && ENV['CONSUMER_SECRET'] log "Using consumer details from environment variables:\n" + " consumer key: #{ENV['CONSUMER_KEY']}\n" + " consumer secret: #{ENV['CONSUMER_SECRET']}" return [ENV['CONSUMER_KEY'], ENV['CONSUMER_SECRET']] end load_bots consumer_key = nil consumer_secret = nil Ebooks::Bot.all.each do |bot| if bot.consumer_key && bot.consumer_secret consumer_key = bot.consumer_key consumer_secret = bot.consumer_secret log "Using consumer details from @#{bot.username}:\n" + " consumer key: #{bot.consumer_key}\n" + " consumer secret: #{bot.consumer_secret}\n" return consumer_key, consumer_secret end end if consumer_key.nil? || consumer_secret.nil? log "Couldn't find any consumer details to auth an account with.\n" + "Please either configure a bot with consumer_key and consumer_secret\n" + "or provide the CONSUMER_KEY and CONSUMER_SECRET environment variables." exit end end def self.load_bots load 'bots.rb' if Ebooks::Bot.all.empty? puts "Couldn't find any bots! Please make sure bots.rb instantiates at least one bot." end end def self.command(args) usage = < ebooks consume [corpus_path2] [...] ebooks consume-all [corpus_path2] [...] ebooks gen [input] ebooks score ebooks archive <@user> ebooks tweet STR if args.length == 0 log usage exit end case args[0] when "new" then new(args[1]) when "consume" then consume(args[1..-1]) when "consume-all" then consume_all(args[1], args[2..-1]) when "gen" then gen(args[1], args[2..-1].join(' ')) when "score" then score(args[1], args[2..-1].join(' ')) when "archive" then archive(args[1], args[2]) when "tweet" then tweet(args[1], args[2]) when "jsonify" then jsonify(args[1..-1]) when "auth" then auth when "c" then c else log usage exit 1 end end end Ebooks::CLI.command(ARGV)