aboutsummaryrefslogtreecommitdiffstats
path: root/actionview
diff options
context:
space:
mode:
authorPietro Moro <33845712+pietro-moro@users.noreply.github.com>2019-07-26 20:54:57 +0200
committerRafael França <rafael@franca.dev>2019-07-26 14:54:57 -0400
commit0eff6956a55882817f67c8d471d32ed3e4b109ee (patch)
treed690b7e65e14a9e5bb22ac2cb5969c0f01c4722d /actionview
parent7f16fedad32f01664ad82829f244319bc752fcd7 (diff)
downloadrails-0eff6956a55882817f67c8d471d32ed3e4b109ee.tar.gz
rails-0eff6956a55882817f67c8d471d32ed3e4b109ee.tar.bz2
rails-0eff6956a55882817f67c8d471d32ed3e4b109ee.zip
Added a phone_to helper method, on the style of mail_to and sms_to. (#36775)
* Added a phone_to helper method, on the style of mail_to and sms_to. It creates an anchor tag with the href set to tel: *here your number* which, when clicked on a mobile phone, or on a desktop with a supported application, lets the phone app kick in, and it prepopulates it with the phone number specified. [Pietro Moro + Rafael Mendonça França]
Diffstat (limited to 'actionview')
-rw-r--r--actionview/CHANGELOG.md4
-rw-r--r--actionview/lib/action_view/helpers/url_helper.rb47
-rw-r--r--actionview/test/template/url_helper_test.rb64
3 files changed, 115 insertions, 0 deletions
diff --git a/actionview/CHANGELOG.md b/actionview/CHANGELOG.md
index 504b1d3e98..ca3ce1476a 100644
--- a/actionview/CHANGELOG.md
+++ b/actionview/CHANGELOG.md
@@ -1,3 +1,7 @@
+* Added `phone_to` helper method to create a link from mobile numbers
+
+ *Pietro Moro*
+
* annotated_source_code returns an empty array so TemplateErrors without a
template in the backtrace are surfaced properly by DebugExceptions.
diff --git a/actionview/lib/action_view/helpers/url_helper.rb b/actionview/lib/action_view/helpers/url_helper.rb
index 85fd549177..9b4116834e 100644
--- a/actionview/lib/action_view/helpers/url_helper.rb
+++ b/actionview/lib/action_view/helpers/url_helper.rb
@@ -619,6 +619,53 @@ module ActionView
content_tag("a", name || phone_number, html_options, &block)
end
+ # Creates a TEL anchor link tag to the specified +phone_number+, which is
+ # also used as the name of the link unless +name+ is specified. Additional
+ # HTML attributes for the link can be passed in +html_options+.
+ #
+ # When clicked, the default app to make calls is opened, and it
+ # is prepopulated with the passed phone number and optional
+ # +country_code+ value.
+ #
+ # +phone_to+ has a optional +country_code+ option which automatically adds the country
+ # code as well as the + sign in the phone numer that gets prepopulated,
+ # for example if +country_code: "01"+ +\+01+ will be prepended to the
+ # phone numer, by passing special keys to +html_options+.
+ #
+ # ==== Options
+ # * <tt>:country_code</tt> - Prepends the country code to the number
+ #
+ # ==== Examples
+ # phone_to "1234567890"
+ # # => <a href="tel:1234567890">1234567890</a>
+ #
+ # phone_to "1234567890", "Phone me"
+ # # => <a href="tel:134567890">Phone me</a>
+ #
+ # phone_to "1234567890", "Phone me", country_code: "01"
+ # # => <a href="tel:+015155555785">Phone me</a>
+ #
+ # You can use a block as well if your link target is hard to fit into the name parameter. \ERB example:
+ #
+ # <%= phone_to "1234567890" do %>
+ # <strong>Phone me:</strong>
+ # <% end %>
+ # # => <a href="tel:1234567890">
+ # <strong>Phone me:</strong>
+ # </a>
+ def phone_to(phone_number, name = nil, html_options = {}, &block)
+ html_options, name = name, nil if block_given?
+ html_options = (html_options || {}).stringify_keys
+
+ country_code = html_options.delete("country_code").presence
+ country_code = country_code.nil? ? "" : "+#{ERB::Util.url_encode(country_code)}"
+
+ encoded_phone_number = ERB::Util.url_encode(phone_number)
+ html_options["href"] = "tel:#{country_code}#{encoded_phone_number}"
+
+ content_tag("a", name || phone_number, html_options, &block)
+ end
+
private
def convert_options_to_data_attributes(options, html_options)
if html_options
diff --git a/actionview/test/template/url_helper_test.rb b/actionview/test/template/url_helper_test.rb
index bce6e7f370..d1570553dd 100644
--- a/actionview/test/template/url_helper_test.rb
+++ b/actionview/test/template/url_helper_test.rb
@@ -770,6 +770,70 @@ class UrlHelperTest < ActiveSupport::TestCase
assert_equal({ class: "special" }, options)
end
+ def test_phone_to
+ assert_dom_equal %{<a href="tel:1234567890">1234567890</a>},
+ phone_to("1234567890")
+ assert_dom_equal %{<a href="tel:1234567890">Bob</a>},
+ phone_to("1234567890", "Bob")
+ assert_dom_equal(
+ %{<a class="phoner" href="tel:1234567890">Bob</a>},
+ phone_to("1234567890", "Bob", "class" => "phoner")
+ )
+ assert_equal phone_to("1234567890", "Bob", "class" => "admin"),
+ phone_to("1234567890", "Bob", class: "admin")
+ end
+
+ def test_phone_to_with_options
+ assert_dom_equal(
+ %{<a class="example-class" href="tel:+011234567890">Phone</a>},
+ phone_to("1234567890", "Phone", class: "example-class", country_code: "01")
+ )
+
+ assert_dom_equal(
+ %{<a href="tel:+011234567890">Phone</a>},
+ phone_to("1234567890", "Phone", country_code: "01")
+ )
+ end
+
+ def test_phone_with_img
+ assert_dom_equal %{<a href="tel:1234567890"><img src="/feedback.png" /></a>},
+ phone_to("1234567890", raw('<img src="/feedback.png" />'))
+ end
+
+ def test_phone_with_html_safe_string
+ assert_dom_equal(
+ %{<a href="tel:1%2B234567890">1+234567890</a>},
+ phone_to(raw("1+234567890"))
+ )
+ end
+
+ def test_phone_with_nil
+ assert_dom_equal(
+ %{<a href="tel:"></a>},
+ phone_to(nil)
+ )
+ end
+
+ def test_phone_returns_html_safe_string
+ assert_predicate phone_to("1234567890"), :html_safe?
+ end
+
+ def test_phone_with_block
+ assert_dom_equal %{<a href="tel:1234567890"><span>Phone</span></a>},
+ phone_to("1234567890") { content_tag(:span, "Phone") }
+ end
+
+ def test_phone_with_block_and_options
+ assert_dom_equal %{<a class="special" href="tel:+011234567890"><span>Phone</span></a>},
+ phone_to("1234567890", country_code: "01", class: "special") { content_tag(:span, "Phone") }
+ end
+
+ def test_phone_does_not_modify_html_options_hash
+ options = { class: "special" }
+ phone_to "1234567890", "ME!", options
+ assert_equal({ class: "special" }, options)
+ end
+
def protect_against_forgery?
request_forgery
end