textris 0.4.4 → 0.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 5b6a77853a55daea7e35e6c9531d82040a9d3338
4
- data.tar.gz: 2c5d6cf2a18d1d16b609c3b53d7042b6b411c1b1
3
+ metadata.gz: b5b1b356ff6632acadf4831ec739a67b94b41091
4
+ data.tar.gz: e3a85db82e310bc468db91927e9436f419973839
5
5
  SHA512:
6
- metadata.gz: 8b32e7a5aae9d7583db862173ed376236f771173ef1f8e9f3ab6e60f5a87e832a451a7856d801dd68daf2f123d8a5670088e58be2a9adf7d769cc3cf68398e6f
7
- data.tar.gz: 1c145dd35898dc2a0556b28efc6fc64a3297fc4df88f3c8ac514815c614ceb526bbf0581da4f86235999b41047f961482e066608bfe9f128dc9c3adb36935851
6
+ metadata.gz: 1a1189862b71010b4c3ea10c128fc5683d25030ad800b442324855185ff8127c1ae4fbd28a42607888bb3c16d11894db833549144555be6ba7ed4162893a63bd
7
+ data.tar.gz: 62828972a887951e081a5a9e310b765efe2546d75dd04fe9265ff1aae5ab81f50134d1c6e8c136f767ec269a406515b9f4b13414195e43d3e5544cd8a57ba780
data/README.md CHANGED
@@ -2,7 +2,7 @@
2
2
 
3
3
  [![Gem Version](https://img.shields.io/gem/v/textris.svg?style=flat-square&label=version)](https://rubygems.org/gems/textris)
4
4
  [![Downloads](https://img.shields.io/gem/dt/textris.svg?style=flat-square)](https://rubygems.org/gems/textris)
5
- [![Build Status](https://img.shields.io/circleci/project/visualitypl/textris/master.svg?style=flat-square&label=build)](https://circleci.com/gh/visualitypl/textris/tree/master)
5
+ [![Build Status](https://img.shields.io/travis/visualitypl/textris/master.svg?style=flat-square&label=build)](https://travis-ci.org/visualitypl/textris)
6
6
  [![Scrutinizer Code Quality](https://img.shields.io/scrutinizer/g/visualitypl/textris.svg?style=flat-square)](https://scrutinizer-ci.com/g/visualitypl/textris/?branch=master)
7
7
  [![Code Climate](https://img.shields.io/codeclimate/github/visualitypl/textris.svg?style=flat-square)](https://codeclimate.com/github/visualitypl/textris)
8
8
  [![Test Coverage](https://img.shields.io/codeclimate/coverage/github/visualitypl/textris.svg?style=flat-square)](https://codeclimate.com/github/visualitypl/textris)
@@ -67,6 +67,27 @@ class User < ActiveRecord::Base
67
67
  end
68
68
  ```
69
69
 
70
+ ### MMS
71
+
72
+ Media messages are supported if you are using the [Twilio](#twilio), [Log](#log) or [Mail](#configuring-the-mail-delivery) adapter. [Twilio currently supports sending MMS in the US and Canada](https://support.twilio.com/hc/en-us/articles/223181608-Can-I-send-or-receive-MMS-messages-).
73
+
74
+ Media messages aren't part of a template, but must be specified as an array of URLs when sending the message, like:
75
+
76
+ ```ruby
77
+ class UserMediaTexter < Textris::Base
78
+ default :from => "Our Team <+48 666-777-888>"
79
+
80
+ def welcome(user)
81
+ @user = user
82
+
83
+ text(
84
+ :to => @user.phone,
85
+ :media_urls => ["http://example.com/hilarious.gif"]
86
+ )
87
+ end
88
+ end
89
+ ```
90
+
70
91
  ### Background and scheduled
71
92
 
72
93
  #### ActiveJob integration
@@ -266,6 +287,7 @@ You can use the following interpolations in your mail templates:
266
287
  - `%{from_phone}`: phone number of the sender (e.g. `48666777888`)
267
288
  - `%{to_phone}`: phone number of the recipient (e.g. `48111222333`)
268
289
  - `%{content}`: message content (e.g. `Welcome to our system, Mr Jones!`)
290
+ - `%{media_urls}`: comma separated string of media URLs (e.g. `http://example.com/hilarious.gif`)
269
291
 
270
292
  You can add optional interpolation modifiers using the `%{variable:modifiers}` syntax. These are most useful for making names e-mail friendly. The following modifiers are available:
271
293
 
@@ -22,6 +22,7 @@ else
22
22
  end
23
23
 
24
24
  require 'textris/base'
25
+ require 'textris/phone_formatter'
25
26
  require 'textris/message'
26
27
 
27
28
  begin
@@ -19,14 +19,17 @@ module Textris
19
19
  end
20
20
 
21
21
  def with_defaults(options)
22
- (@defaults || {}).merge(options)
22
+ defaults.merge(options)
23
+ end
24
+
25
+ def defaults
26
+ @defaults ||= superclass.respond_to?(:defaults) ? superclass.defaults.dup : {}
23
27
  end
24
28
 
25
29
  protected
26
30
 
27
31
  def default(options)
28
- @defaults ||= {}
29
- @defaults.merge!(options)
32
+ defaults.merge!(options)
30
33
  end
31
34
 
32
35
  private
@@ -58,11 +61,11 @@ module Textris
58
61
 
59
62
  options = self.class.with_defaults(options)
60
63
  options.merge!(
61
- :texter => self.class,
62
- :action => @action,
63
- :args => @args,
64
- :content => options[:body].is_a?(String) ? options[:body] : nil,
65
- :renderer => self)
64
+ :texter => self.class,
65
+ :action => @action,
66
+ :args => @args,
67
+ :content => options[:body].is_a?(String) ? options[:body] : nil,
68
+ :renderer => self)
66
69
 
67
70
  ::Textris::Message.new(options)
68
71
  end
@@ -6,7 +6,7 @@ module Textris
6
6
  end
7
7
 
8
8
  def delay_for(interval)
9
- unless interval.is_a?(Fixnum)
9
+ unless interval.is_a?(Integer)
10
10
  raise(ArgumentError, "Proper interval must be provided")
11
11
  end
12
12
 
@@ -23,5 +23,3 @@ module Textris
23
23
  end
24
24
  end
25
25
  end
26
-
27
-
@@ -11,6 +11,11 @@ module Textris
11
11
  log :debug, "From: #{message.from || 'unknown'}"
12
12
  log :debug, "To: #{message.to.map { |i| Phony.format(to) }.join(', ')}"
13
13
  log :debug, "Content: #{message.content}"
14
+ (message.media_urls || []).each_with_index do |media_url, index|
15
+ logged_message = index == 0 ? "Media URLs: " : " "
16
+ logged_message << media_url
17
+ log :debug, logged_message
18
+ end
14
19
  end
15
20
 
16
21
  private
@@ -61,6 +61,8 @@ module Textris
61
61
  get_rails_variable(key)
62
62
  when 'texter', 'action', 'from_name', 'from_phone', 'content'
63
63
  message.send(key)
64
+ when 'media_urls'
65
+ message.media_urls.join(', ')
64
66
  else
65
67
  variables[key.to_sym]
66
68
  end.to_s.strip
@@ -14,7 +14,8 @@ module Textris
14
14
  :from_phone => message.from_phone,
15
15
  :texter => message.texter,
16
16
  :action => message.action,
17
- :to => to))
17
+ :to => to,
18
+ :media_urls => message.media_urls))
18
19
  end
19
20
  end
20
21
  end
@@ -2,19 +2,19 @@ module Textris
2
2
  module Delivery
3
3
  class Twilio < Textris::Delivery::Base
4
4
  def deliver(to)
5
- client.messages.create(
6
- :from => phone_with_plus(message.from_phone),
7
- :to => phone_with_plus(to),
8
- :body => message.content)
5
+ options = {
6
+ :from => PhoneFormatter.format(message.from_phone),
7
+ :to => PhoneFormatter.format(to),
8
+ :body => message.content
9
+ }
10
+ if message.media_urls.is_a?(Array)
11
+ options[:media_url] = message.media_urls
12
+ end
13
+ client.messages.create(options)
9
14
  end
10
15
 
11
16
  private
12
17
 
13
- # Twillo requires phone numbers starting with a '+' sign
14
- def phone_with_plus(phone)
15
- phone.to_s.start_with?('+') ? phone : "+#{phone}"
16
- end
17
-
18
18
  def client
19
19
  @client ||= ::Twilio::REST::Client.new
20
20
  end
@@ -1,15 +1,17 @@
1
1
  module Textris
2
2
  class Message
3
- attr_reader :content, :from_name, :from_phone, :to, :texter, :action, :args
3
+ attr_reader :content, :from_name, :from_phone, :to, :texter, :action, :args,
4
+ :media_urls
4
5
 
5
6
  def initialize(options = {})
6
7
  initialize_content(options)
7
8
  initialize_author(options)
8
9
  initialize_recipients(options)
9
10
 
10
- @texter = options[:texter]
11
- @action = options[:action]
12
- @args = options[:args]
11
+ @texter = options[:texter]
12
+ @action = options[:action]
13
+ @args = options[:args]
14
+ @media_urls = options[:media_urls]
13
15
  end
14
16
 
15
17
  def deliver
@@ -32,7 +34,15 @@ module Textris
32
34
  def from
33
35
  if @from_phone.present?
34
36
  if @from_name.present?
35
- "#{@from_name} <#{Phony.format(@from_phone)}>"
37
+ if PhoneFormatter.is_alphameric?(@from_phone)
38
+ @from_phone
39
+ else
40
+ if PhoneFormatter.is_a_short_code?(@from_phone)
41
+ "#{@from_name} <#{@from_phone}>"
42
+ else
43
+ "#{@from_name} <#{Phony.format(@from_phone)}>"
44
+ end
45
+ end
36
46
  else
37
47
  Phony.format(@from_phone)
38
48
  end
@@ -79,15 +89,23 @@ module Textris
79
89
  end
80
90
 
81
91
  def parse_from_dual(from)
82
- if (matches = from.to_s.match(/(.*)\<(.*)\>\s*$/).to_a).size == 3 &&
83
- Phony.plausible?(matches[2])
84
- [matches[1].strip, Phony.normalize(matches[2])]
92
+ matches = from.match(/(.*)\<(.*)\>\s*$/)
93
+ return unless matches
94
+ name, sender_id = matches.captures
95
+ return unless name && sender_id
96
+
97
+ if Phony.plausible?(sender_id) || PhoneFormatter.is_a_short_code?(sender_id)
98
+ [name.strip, Phony.normalize(sender_id)]
99
+ elsif PhoneFormatter.is_alphameric?(sender_id)
100
+ [name.strip, sender_id]
85
101
  end
86
102
  end
87
103
 
88
104
  def parse_from_singular(from)
89
105
  if Phony.plausible?(from)
90
106
  [nil, Phony.normalize(from)]
107
+ elsif PhoneFormatter.is_a_short_code?(from)
108
+ [nil, from.to_s]
91
109
  elsif from.present?
92
110
  [from.strip, nil]
93
111
  end
@@ -103,8 +121,7 @@ module Textris
103
121
 
104
122
  def parse_content(content)
105
123
  content = content.to_s
106
- content = content.gsub(/\s{1,}/, ' ')
107
- content = content.strip
124
+ content = content.rstrip
108
125
 
109
126
  content
110
127
  end
@@ -0,0 +1,28 @@
1
+ module Textris
2
+ class PhoneFormatter
3
+ class << self
4
+ def format(phone = '')
5
+ return phone if is_a_short_code?(phone) || is_alphameric?(phone) || phone.nil?
6
+ "#{'+' unless phone.start_with?('+')}#{phone}"
7
+ end
8
+
9
+ # Short codes have more dependencies and limitations;
10
+ # but this is a good general start
11
+ def is_a_short_code?(phone)
12
+ !!phone.to_s.match(/\A\d{4,6}\z/)
13
+ end
14
+
15
+ def is_a_phone_number?(phone)
16
+ Phony.plausible?(phone)
17
+ end
18
+
19
+ def is_alphameric?(phone)
20
+ # \A # Start of the string
21
+ # (?=.*[a-zA-Z]) # Lookahead to ensure there is at least one letter in the entire string
22
+ # [a-zA-z\d]{1,11} # Between 1 and 11 characters in the string
23
+ # \z # End of the string
24
+ !!phone.to_s.match(/\A(?=.*[a-zA-Z])[a-zA-z\d]{1,11}\z/)
25
+ end
26
+ end
27
+ end
28
+ end
@@ -1,3 +1,3 @@
1
1
  module Textris
2
- VERSION = '0.4.4'
2
+ VERSION = '0.5.0'
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: textris
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.4
4
+ version: 0.5.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Karol Słuszniak
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2016-04-13 00:00:00.000000000 Z
11
+ date: 2017-12-06 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -136,6 +136,20 @@ dependencies:
136
136
  - - "~>"
137
137
  - !ruby/object:Gem::Version
138
138
  version: '2.0'
139
+ - !ruby/object:Gem::Dependency
140
+ name: appraisal
141
+ requirement: !ruby/object:Gem::Requirement
142
+ requirements:
143
+ - - "~>"
144
+ - !ruby/object:Gem::Version
145
+ version: '2.1'
146
+ type: :development
147
+ prerelease: false
148
+ version_requirements: !ruby/object:Gem::Requirement
149
+ requirements:
150
+ - - "~>"
151
+ - !ruby/object:Gem::Version
152
+ version: '2.1'
139
153
  - !ruby/object:Gem::Dependency
140
154
  name: actionmailer
141
155
  requirement: !ruby/object:Gem::Requirement
@@ -234,6 +248,7 @@ files:
234
248
  - lib/textris/delivery/test.rb
235
249
  - lib/textris/delivery/twilio.rb
236
250
  - lib/textris/message.rb
251
+ - lib/textris/phone_formatter.rb
237
252
  - lib/textris/version.rb
238
253
  homepage: http://github.com/visualitypl/textris
239
254
  licenses:
@@ -255,7 +270,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
255
270
  version: '0'
256
271
  requirements: []
257
272
  rubyforge_project:
258
- rubygems_version: 2.4.5
273
+ rubygems_version: 2.6.11
259
274
  signing_key:
260
275
  specification_version: 4
261
276
  summary: Simple SMS messaging gem for Rails based on concepts and conventions similar