Hey Stackoverflow Community,
I'm new to Ruby and working on a small project for a course assignment. I've to create a mobile bot that uses the Google Translate API and returns the translated text.
I'm stuck trying to figure out how to write the code for the bot to get the inputted text and output the translation.
Could anyone have a look, please? Would really appreciate it
def transl8 (input,lang) #method to translate incoming text
# Translates some text into Russian
# Instantiates a client
translate = Google::Cloud::Translate.new project: project-217401
puts input + "Looks like you're speak in #{detection.language}"
puts "Confidence: #{detection.confidence}"
translation = translate.translate input, to: lang
return "In #{lang} that's" + translation
end
def transl8 (input,lang) #method to translate incoming text
detection = $translate.detect input
puts input + "Looks like you're speak in #{detection.language}"
puts "Confidence: #{detection.confidence}"
translation = $translate.translate input, to: lang
return "In #{lang} that's" + translation
end
def listlang #method to show language code
language_code = "en"
languages = $translate.languages
puts "Supported languages:"
languages.each do |language|
puts "#{language.code} #{language.name}"
end
end
configure :development do
require 'dotenv'
Dotenv.load
end
#Translate End-point
https://translation.googleapis.com/language/translate/v2 endpoint
get "/incoming/sms/" do
"Hey! I'm AllSpeak, a translator bot. The list of supported languages are
below. Just ask by typing (TEXT) (space) (Language Code)"
incoming_text = params['Body']
text_to_translate = incoming_text.split(' ')[0]
lang_requested = incoming_text.split(' ')[1]
twiml_body = transl8(text_to_translate, lang_requested)
#return twiml here with twiml_body
end
#Look into Including method to set default language for commonly used
phrases
puts listlang
transl8 (text)
# Build a twilio response object
twiml = Twilio::TwiML::MessagingResponse.new do |r|
r.message do |m|
end
end
Regarding the Translation API Code:
For listlang:
You're missing an end on the do loop and you're not setting the project_id variable
For transl8:
You're not initializing the detection variable
Sample code:
#!/usr/bin/ruby
require "google/cloud/translate"
$translate = Google::Cloud::Translate.new project: "slatebot-217401"
def transl8 (input,lang) #method to translate incoming text
detection = $translate.detect input
puts input + "Looks like you're speak in #{detection.language}"
puts "Confidence: #{detection.confidence}"
translation = $translate.translate input, to: lang
return "In #{lang} that's" + translation
end
def listlang #method to show language code
language_code = "en"
languages = $translate.languages
puts "Supported languages:"
languages.each do |language|
puts "#{language.code} #{language.name}"
end
end
Jarod from Twilio. I noticed your question and wanted to suggest you parse the users SMS that would be incoming to your "incoming/sms". Once you have configured your phone number to make a GET request to "incoming/sms" Twilio will start sending incoming SMS to that URL. When Twilio does this it will also pass you a bunch of information in the http request. The incoming SMS body is passed as the Body in the request. So you could do something like this
get '/incoming/sms' do
incoming_text = params['Body']
text_to_translate = incoming_text.split(' ')[0]
lang_requested = incoming_text.split(' ')[1]
twiml_body = transl8(text_to_translate, lang_requested)
#return twiml here with twiml_body
end
Does that make sense? Looks like your twiml method is mostly ready to go so just insert that at the end of your response and you should be good to go! Fun app. Excited to see it finished!
I'm trying to write a bot using ruby and the twitter gem.
Here is my code :
#!/usr/bin/env ruby
require 'twitter'
#client = Twitter::REST::Client.new do |config|
config.consumer_key = "xxx"
config.consumer_secret = "xxx"
config.access_token = "xxx"
config.access_token_secret = "xxx"
end
#last_tweet = #client.search("#Hashtag").first
while true
puts "Bot is searching"
puts #last_tweet.text
if #last_tweet.id != #client.search("#Hashtag").first.id
puts #last_tweet.id
puts "bot found another tweet. retweet!"
sleep 1
#client.retweet #last_tweet
#last_tweet = #client.search("#Hashtag").first
puts "the last tweet is now : #{#last_tweet.text}"
end
sleep 5
end
The goal is to simply retweet any tweet with "#hashtag".
Now, the bot is behaving very strangely. For some reasons it's sometimes randomly seem to RT the same tweet twice, causing it to crash.
I tried for hours, I even copied this gist : https://gist.github.com/nilsding/834c2fe8829d29b79e23
Which have the exact same issue.
How can I make it not retweet the same tweet ?
I've already checked this question but can't understand how to apply it to my simple ruby file.
I am looking for an instance method from the ruby-gmail gem that would allow me to read either:
the body
or
subject
of a Gmail message.
After reviewing the documentation, found here, I couldn't find anything!?
There is a .message instance method found in the Gmail::Message class section; but it only returns, for lack of a better term, email "mumbo-jumbo," for the body.
My attempt:
#!/usr/local/bin/ruby
require 'gmail'
gmail = Gmail.connect('username', 'password')
emails = gmail.inbox.emails(:from => 'someone#mail.com')
emails.each do |email|
email.read
email.message
end
Now:
email.read does not work
email.message returns that, "mumbo-jumbo," mentioned above
Somebody else asked this question on SO but didn't get an answer.
This probably isn't exactly the answer to your question, but I will tell you what I have done in the past. I tried using the ruby-gmail gem but it didn't do what I wanted it to do in terms of reading a message. Or, at least, I couldn't get it to work. Instead I use the built-in Net::IMAP class to log in and get a message.
require 'net/imap'
imap = Net::IMAP.new('imap.gmail.com',993,true)
imap.login('<username>','<password>')
imap.select('INBOX')
subject_id = search_mail(imap, 'SUBJECT', '<mail_subject>')
subject_message = imap.fetch(subject_id,'RFC822')[0].attr['RFC822']
mail = Mail.read_from_string subject_message
body_message = mail.html_part.body
From here your message is stored in body_message and is HTML. If you want the entire email body you will probably need to learn how to use Nokogiri to parse it. If you just want a small bit of the message where you know some of the surrounding characters you can use a regex to find the part you are interested in.
I did find one page associated with the ruby-gmail gem that talks about using ruby-gmail to read a Gmail message. I made a cursory attempt at testing it tonight but apparently Google upped the security on my account and I couldn't get in using irb without tinkering with my Gmail configuration (according to the warning email I received). So I was unable to verify what is stated on that page, but as I mentioned my past attempts were unfruitful whereas Net::IMAP works for me.
EDIT:
I found this, which is pretty cool. You will need to add in
require 'cgi'
to your class.
I was able to implement it in this way. After I have my body_message, call the html2text method from that linked page (which I modified slightly and included below since you have to convert body_message to a string):
plain_text = html2text(body_message)
puts plain_text #Prints nicely formatted plain text to the terminal
Here is the slightly modified method:
def html2text(html)
text = html.to_s.
gsub(/( |\n|\s)+/im, ' ').squeeze(' ').strip.
gsub(/<([^\s]+)[^>]*(src|href)=\s*(.?)([^>\s]*)\3[^>]*>\4<\/\1>/i,
'\4')
links = []
linkregex = /<[^>]*(src|href)=\s*(.?)([^>\s]*)\2[^>]*>\s*/i
while linkregex.match(text)
links << $~[3]
text.sub!(linkregex, "[#{links.size}]")
end
text = CGI.unescapeHTML(
text.
gsub(/<(script|style)[^>]*>.*<\/\1>/im, '').
gsub(/<!--.*-->/m, '').
gsub(/<hr(| [^>]*)>/i, "___\n").
gsub(/<li(| [^>]*)>/i, "\n* ").
gsub(/<blockquote(| [^>]*)>/i, '> ').
gsub(/<(br)(| [^>]*)>/i, "\n").
gsub(/<(\/h[\d]+|p)(| [^>]*)>/i, "\n\n").
gsub(/<[^>]*>/, '')
).lstrip.gsub(/\n[ ]+/, "\n") + "\n"
for i in (0...links.size).to_a
text = text + "\n [#{i+1}] <#{CGI.unescapeHTML(links[i])}>" unless
links[i].nil?
end
links = nil
text
end
You also mentioned in your original question that you got mumbo-jumbo with this step:
email.message *returns mumbo-jumbo*
If the mumbo-jumbo is HTML, you can probably just use your existing code with this html2text method instead of switching over to Net::IMAP as I had discussed when I posted my original answer.
Nevermind, it's:
email.subject
email.body
silly me
ok, so how do I get the body in "readable" text? without all the encoding stuff and html?
Subject, text body and HTML body:
email.subject
if email.message.multipart?
text_body = email.message.text_part.body.decoded
html_body = email.message.html_part.body.decoded
else
# Only multipart messages contain a HTML body
text_body = email.message.body.decoded
html_body = text
end
Attachments:
email.message.attachments.each do |attachment|
path = "/tmp/#{attachment.filename}"
File.write(path, attachment.decoded)
# The MIME type might be useful
content_type = attachment.mime_type
end
require 'gmail'
gmail = Gmail.connect('username', 'password')
emails = gmail.inbox.emails(:from => 'someone#mail.com')
emails.each do |email|
puts email.subject
puts email.text_part.body.decoded
end
I wrote this auto-reply bot with ruby, it is supposed to autoreply with cleverbot messages when im away:
require "cleverbot"
require "cinch"
$client = Cleverbot::Client.new
def get_answer(text)
reply = $client.write text
return reply
end
bot = Cinch::Bot.new do
configure do |c|
c.nick = "mybotsnickname"
c.server = "my.irc.testserver"
c.channels = ["#mychannel"]
end
on :message do |m|
m.reply m.user
m.reply get_answer(m.message)
end
end
bot.start
It works fine but the session id changes every message. What do i have to change to keep it? best case scenario is every user writing me gets a different session id at cleverbot so they have individual conversations.
I'm pretty new to ruby.
I used: https://github.com/benmanns/cleverbot
and https://github.com/cinchrb/cinch
Comparing this to the structure of my cinch bot, I'd try the following:
1) Make get_answer a helper block and place it inside the bot = Cinch::Bot.new block:
helpers do
def get_answer(text)
reply = $client.write text
return reply
end
end
2) Replace
on :message do |m|
with
on :message do |m, text|
3) Replace
m.reply get_answer(m.message)
with
m.reply get_answer(text)
I suspect this should work. But I'm a relatively new to Ruby as well.
so I'm trying to set up a script to grab tweets so I can use them in my app. Currently I'm using Ruby 2.0.0 and the 1.1 Twitter API REST. Currently I'm not worried about storing the tweets in a database or anything I'm just simply trying to get the correct tweets into terminal. Here is my current code.
require 'twitter'
client = Twitter::REST::Client.new do |config|
config.consumer_key = "XXXXXXXXXXXXXXXXXX"
config.consumer_secret = "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
config.access_token = "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
config.access_token_secret = "XXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
end
topics = ["#BreakingBad", "#Gameofthones"]
client.filter(:track => topics.join(",")) do |tweet|
puts tweet.text
endtag = options[:search]
My problem is that when I run the script I get flooded with just a mass of tweets in all different languages. Any help would be great. Thanks.