Skip to content

Commit

Permalink
Split long Telegram messages
Browse files Browse the repository at this point in the history
  • Loading branch information
aserpi committed Jan 14, 2018
1 parent 1e0e165 commit 00e3119
Showing 1 changed file with 32 additions and 10 deletions.
42 changes: 32 additions & 10 deletions app/models/agents/telegram_agent.rb
Expand Up @@ -36,6 +36,7 @@ class TelegramAgent < Agent
* `caption`: caption for a media content, 0-200 characters
* `disable_notification`: send a message silently in a channel
* `disable_web_page_preview`: disable link previews for links in a text message
* `long_message`: split or truncate long text messages or captions
* `parse_mode`: parse policy of a text message
See the official [Telegram Bot API documentation](https://core.telegram.org/bots/api#available-methods) for detailed info.
Expand All @@ -53,6 +54,7 @@ def default_options
form_configurable :caption
form_configurable :disable_notification, type: :array, values: ['', 'true', 'false']
form_configurable :disable_web_page_preview, type: :array, values: ['', 'true', 'false']
form_configurable :long_message, type: :array, values: ['', 'split', 'truncate']
form_configurable :parse_mode, type: :array, values: ['', 'html', 'markdown']

def validate_auth_token
Expand All @@ -68,10 +70,11 @@ def complete_chat_id
def validate_options
errors.add(:base, 'auth_token is required') unless options['auth_token'].present?
errors.add(:base, 'chat_id is required') unless options['chat_id'].present?
errors.add(:base, 'caption should be 200 characters or less') if interpolated['caption'].present? and interpolated['caption'].length > 200
errors.add(:base, "disable_notification has invalid value: should be 'true' or 'false'") if interpolated['disable_notification'].present? and !%w(true false).include?(interpolated['disable_notification'])
errors.add(:base, "disable_web_page_preview has invalid value: should be 'true' or 'false'") if interpolated['disable_web_page_preview'].present? and !%w(true false).include?(interpolated['disable_web_page_preview'])
errors.add(:base, "parse_mode has invalid value: should be 'html' or 'markdown'") if interpolated['parse_mode'].present? and !%w(html markdown).include?(interpolated['parse_mode'])
errors.add(:base, 'caption should be 200 characters ol less') if interpolated['caption'].present? && interpolated['caption'].length > 200 && (!interpolated['long_message'].present? || interpolated['long_message'] != 'split')
errors.add(:base, "disable_notification has invalid value: should be 'true' or 'false'") if interpolated['disable_notification'].present? && !%w(true false).include?(interpolated['disable_notification'])
errors.add(:base, "disable_web_page_preview has invalid value: should be 'true' or 'false'") if interpolated['disable_web_page_preview'].present? && !%w(true false).include?(interpolated['disable_web_page_preview'])
errors.add(:base, "long_message has invalid value: should be 'split' or 'truncate'") if interpolated['long_message'].present? && !%w(split truncate).include?(interpolated['long_message'])
errors.add(:base, "parse_mode has invalid value: should be 'html' or 'markdown'") if interpolated['parse_mode'].present? && !%w(html markdown).include?(interpolated['parse_mode'])
end

def working?
Expand All @@ -95,12 +98,13 @@ def receive(incoming_events)
}.freeze

def configure_params(params)
params[:chat_id] = interpolated['chat_id']
params[:disable_notification] = interpolated['disable_notification'] if interpolated['disable_notification'].present?
if params.has_key?(:text)
params[:disable_web_page_preview] = interpolated['disable_web_page_preview'] if interpolated['disable_web_page_preview'].present?
params[:parse_mode] = interpolated['parse_mode'] if interpolated['parse_mode'].present?
else
params[:caption] = interpolated['caption'][0..199] if interpolated['caption'].present?
params[:caption] = interpolated['caption'] if interpolated['caption'].present?
end

params
Expand All @@ -123,25 +127,43 @@ def load_file(url)

def receive_event(event)
interpolate_with event do
messages_send = TELEGRAM_ACTIONS.count do |field, method|
messages_send = TELEGRAM_ACTIONS.count do |field, _method|
payload = load_field event, field
next unless payload
send_telegram_message method, configure_params(field => payload)
send_telegram_messages field, configure_params(field => payload)
unlink_file payload if payload.is_a? Tempfile
true
end
error("No valid key found in event #{event.payload.inspect}") if messages_send.zero?
end
end

def send_telegram_message(method, params)
params[:chat_id] = interpolated['chat_id']
response = HTTMultiParty.post telegram_bot_uri(method), query: params
def send_message(field, params)
response = HTTMultiParty.post telegram_bot_uri(TELEGRAM_ACTIONS[field]), query: params
unless response['ok']
error(response)
end
end

def send_telegram_messages(field, params)
if !interpolated['long_message'].present? || interpolated['long_message'] != 'split'
params[:caption] = params[:caption][0..199] if params[:caption]
params[:text] = params[:text][0..4095] if params[:text]
send_message field, params
elsif field == :text
params[:text].scan(/\G(?:\w{4096}|.{1,4096}(?<=\s)|.{1,4096}(?=\b|\z))/m) do |message|
send_message field, configure_params(field => message.strip) unless message.strip.blank?
end
else
caption_array = params[:caption].scan(/\G(?:\w{200}|.{1,200}(?<=\s)|.{1,200}(?=\b|\z))/m)
params[:caption] = caption_array.first.strip
send_message field, params
caption_array.drop(1).each do |caption|
send_message(:text, configure_params(text: caption.strip)) unless caption.strip.blank?
end
end
end

def telegram_bot_uri(method)
"https://api.telegram.org/bot#{interpolated['auth_token']}/#{method}"
end
Expand Down

0 comments on commit 00e3119

Please sign in to comment.