emojimmy 0.1.2 → 0.1.3

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: 537d4a671f8d4f03de4905c27435d57b53d9b72b
4
- data.tar.gz: 262e130bc35f71d5d0a33d38094a7b9aa3ed92ee
3
+ metadata.gz: 6685f81445ccf98ccc717eca34550679da23de6c
4
+ data.tar.gz: cd0149baa61ea77ac10f98938fb596528a9f9645
5
5
  SHA512:
6
- metadata.gz: 13be2c19665b325c30b618df13053418294c8cafb0f91afde16252e3ac15bf45e9a3616b28b08cdd4d477371831a7666ac32ed32c6ffa160d7b9036ceea31030
7
- data.tar.gz: 210b4ecd796feb3b7cdd1b4c02450502c9131d358c7161a11e5708d6e02fe87faecb92980e58088b072b8ef4f02ce11a7bc64ca4f5b1e6fe86c42c02a0db4935
6
+ metadata.gz: e6e3939944d4120e6953db4c5c29d38f8cfa77bcf0d3a2a7e751167fce287ab3fe47c22367851a8be470b96899207999431969b133cef90ca96b179d235e36f5
7
+ data.tar.gz: 3dbe38216a0779620e3ed6aec197e16e62d646e8d88353549b3c50daeeaa253549c6b77c54ecbaa30b4711463b3c7f0e5fad1c9dc75c13039df173384ff19ca0
data/README.md CHANGED
@@ -2,6 +2,14 @@
2
2
 
3
3
  Emojimmy makes it possible to store emoji characters in ActiveRecord datastores that don’t support *4-Byte UTF-8 Unicode* (`utf8mb4`) encoding.
4
4
 
5
+ You probably should be using a database that supports `utf8mb4` though (and not this gem), like PostgreSQL or MySQL (5.5+). We built this gem because stock [Heroku](http://heroku.com) machines cannot compile the `mysql2` gem to use the `utf8mb4` encoding (because they ship with an old version of `libmysqlclient`).
6
+
7
+ <a href="https://rubygems.org/gems/emojimmy"><img src="https://badge.fury.io/rb/emojimmy.png" /></a>
8
+ <a href="https://codeclimate.com/github/mirego/emojimmy"><img src="https://codeclimate.com/github/mirego/emojimmy.png" /></a>
9
+ <a href='https://coveralls.io/r/mirego/emojimmy?branch=master'><img src='https://coveralls.io/repos/mirego/emojimmy/badge.png?branch=master' /></a>
10
+ <a href='https://gemnasium.com/mirego/emojimmy'><img src="https://gemnasium.com/mirego/emojimmy.png" /></a>
11
+ <a href="https://travis-ci.org/mirego/emojimmy"><img src="https://travis-ci.org/mirego/emojimmy.png?branch=master" /></a>
12
+
5
13
  ---
6
14
 
7
15
  ## Installation
@@ -21,6 +29,8 @@ First, you must enable Emojimmy in an initializer (when your application boots):
21
29
  Emojimmy.initialize!
22
30
  ```
23
31
 
32
+ #### ActiveRecord
33
+
24
34
  Then, you can edit your models to specify which fields will be storing emoji characters:
25
35
 
26
36
  ```ruby
@@ -46,6 +56,18 @@ Your model will now be able to store emoji characters in its `body` column.
46
56
  @comment.read_attribute(:body) # => "Hello! {U+1F601}"
47
57
  ```
48
58
 
59
+ #### Custom
60
+
61
+ If you only want to use Emojimmy’s conversion methods, you can use two methods, `token_to_emoji` and `emoji_to_token`:
62
+
63
+ ```ruby
64
+ Emojimmy.emoji_to_token("Hello! \xF0\x9F\x98\x81")
65
+ # => "Hello! {U+1F601}"
66
+
67
+ Emojimmy.token_to_emoji("Hello! {U+1F601}")
68
+ # => "Hello! \xF0\x9F\x98\x81"
69
+ ```
70
+
49
71
  ## License
50
72
 
51
73
  `Emojimmy` is © 2013 [Mirego](http://www.mirego.com) and may be freely distributed under the [New BSD license](http://opensource.org/licenses/BSD-3-Clause). See the [`LICENSE.md`](https://github.com/mirego/emojimmy/blob/master/LICENSE.md) file.
@@ -0,0 +1,8 @@
1
+ class ActiveRecord::Base
2
+ def self.stores_emoji_characters(options = {})
3
+ return unless table_exists?
4
+
5
+ options[:in] ||= []
6
+ Emojimmy::Mixin.inject_methods(self, options[:in])
7
+ end
8
+ end
@@ -5,12 +5,16 @@ module Emojimmy
5
5
  model.class_eval <<-RUBY, __FILE__, __LINE__ + 1
6
6
  # Before saving the record, convert the attribute value
7
7
  before_save do
8
- self.#{attribute} = Emojimmy.emoji_to_text(self.#{attribute})
8
+ unless respond_to?("#{attribute}=")
9
+ raise ArgumentError.new('#{model} must respond to #{attribute}= in order for Emojimmy to store emoji characters in it.')
10
+ end
11
+
12
+ self.#{attribute} = Emojimmy.emoji_to_token(self.#{attribute})
9
13
  end
10
14
 
11
15
  # When calling the attribute name, convert its value
12
16
  def #{attribute}
13
- Emojimmy.text_to_emoji(read_attribute(#{attribute.inspect}))
17
+ Emojimmy.token_to_emoji(read_attribute(#{attribute.inspect}))
14
18
  end
15
19
  RUBY
16
20
  end
@@ -1,3 +1,3 @@
1
1
  module Emojimmy
2
- VERSION = '0.1.2'
2
+ VERSION = '0.1.3'
3
3
  end
data/lib/emojimmy.rb CHANGED
@@ -6,58 +6,56 @@ require 'active_record'
6
6
 
7
7
  # Modules
8
8
  require 'emojimmy/mixin'
9
+ require 'emojimmy/extensions'
9
10
 
10
11
  module Emojimmy
11
12
  DATA_FILE = File.expand_path('../../data/emoji.txt', __FILE__)
13
+ TOKEN_REGEXP = /({U\+[^}]+})/
12
14
 
13
- # Load emoji data from config/emoji.txt and build the `text_to_emoji`
14
- # and `emoji_to_text` hash tables
15
+ # Load emoji data from config/emoji.txt and build the `token_to_emoji`
16
+ # and `emoji_to_token` hash tables
15
17
  def self.initialize!
16
18
  content = File.read(DATA_FILE).each_line.to_a
17
19
  build_hash_tables(content)
18
20
  end
19
21
 
20
22
  # Loop through all emoji and replace them with
21
- # their matching text equivalent
22
- def self.emoji_to_text(content)
23
- @emoji_to_text.each_pair do |emoji, text|
24
- content = content.gsub(emoji, text)
23
+ # their matching token
24
+ def self.emoji_to_token(content)
25
+ return content unless content.present?
26
+
27
+ content.dup.tap do |content|
28
+ @emoji_to_token.each_pair do |emoji, token|
29
+ content.gsub!(emoji, token)
30
+ end
25
31
  end
26
-
27
- content
28
32
  end
29
33
 
30
- # Loop through each {U+...} part in the string and
34
+ # Loop through each {U+...} token in the string and
31
35
  # convert it to the matching emoji
32
- def self.text_to_emoji(content)
33
- content.gsub /({U\+[^}]+})/ do |data|
34
- @text_to_emoji[data]
35
- end
36
+ def self.token_to_emoji(content)
37
+ return content unless content.present?
38
+
39
+ content.gsub(TOKEN_REGEXP) { |data| @token_to_emoji[data] }
36
40
  end
37
41
 
38
42
  private
39
43
 
40
- # Build or `emoji_to_text` and `text_to_emoji` hash tables
44
+ # Build or `emoji_to_token` and `token_to_emoji` hash tables
41
45
  def self.build_hash_tables(content)
42
- @emoji_to_text = {}
43
- @text_to_emoji = {}
46
+ @emoji_to_token = {}
47
+ @token_to_emoji = {}
44
48
 
45
49
  content.each do |line|
46
- line = line.chomp.split("\t")
47
- emoji = eval('"' + line[1] + '"')
48
- text = "{#{line[0]}}"
49
-
50
- @emoji_to_text[emoji] = text
51
- @text_to_emoji[text] = emoji
52
- end
53
- end
54
- end
50
+ token, emoji = line.chomp.split("\t")
51
+ token = "{#{token}}"
55
52
 
56
- class ActiveRecord::Base
57
- def self.stores_emoji_characters(options = {})
58
- return unless table_exists?
53
+ # We use `eval` here to convert
54
+ # "\\xF0\\x9F\\x98\\x81" into "\xF0\x9F\x98\x81"
55
+ emoji = eval('"' + emoji + '"')
59
56
 
60
- options[:in] ||= []
61
- Emojimmy::Mixin.inject_methods(self, options[:in])
57
+ @emoji_to_token[emoji] = token
58
+ @token_to_emoji[token] = emoji
59
+ end
62
60
  end
63
61
  end
@@ -9,52 +9,74 @@ describe Emojimmy::Mixin do
9
9
  t.text :body
10
10
  end
11
11
  end
12
-
13
- spawn_emojimmy_model 'Comment', in: [:body]
14
12
  end
15
13
 
16
- describe :InstanceMethod do
17
- subject { Comment.create(body: body) }
18
-
19
- context 'with a single emoji' do
20
- let(:body) { "Hello, 😁😁 world!" }
21
- it { should be_persisted }
22
- its(:body) { should eql body }
14
+ context 'with invalid options for `in`' do
15
+ before do
16
+ spawn_emojimmy_model 'Comment', in: [:foo]
23
17
  end
24
18
 
25
- context 'with multiple emoji' do
26
- let(:body) { "Hello, 😁😁😁 😍 world!" }
27
- it { should be_persisted }
28
- its(:body) { should eql body }
19
+ specify do
20
+ expect {
21
+ Comment.create(body: 'Hello.')
22
+ }.to raise_error(ArgumentError, 'Comment must respond to foo= in order for Emojimmy to store emoji characters in it.')
29
23
  end
24
+ end
30
25
 
31
- context 'without any emoji' do
32
- let(:body) { "Hello, boring world!" }
33
- it { should be_persisted }
34
- its(:body) { should eql body }
26
+ context 'with valid options for `in`' do
27
+ before do
28
+ spawn_emojimmy_model 'Comment', in: [:body]
35
29
  end
36
- end
37
30
 
38
- describe :Callback do
39
- subject { Comment.create(body: body) }
40
- let(:persisted_body) { subject.read_attribute(:body) }
31
+ describe :InstanceMethod do
32
+ subject { Comment.create(body: body) }
41
33
 
42
- context 'with a single emoji' do
43
- let(:body) { "Hello, 😁 world!" }
44
- it { should be_persisted }
45
- it { expect(persisted_body).to eql "Hello, {U+1F601} world!" }
46
- end
34
+ context 'with a single emoji' do
35
+ let(:body) { "Hello, 😁😁 world!" }
36
+ it { should be_persisted }
37
+ its(:body) { should eql body }
38
+ end
39
+
40
+ context 'with multiple emoji' do
41
+ let(:body) { "Hello, 😁😁😁 😍 world!" }
42
+ it { should be_persisted }
43
+ its(:body) { should eql body }
44
+ end
47
45
 
48
- context 'with multiple emoji' do
49
- let(:body) { "Hello, 😁😁 😍 world!" }
50
- it { should be_persisted }
51
- it { expect(persisted_body).to eql "Hello, {U+1F601}{U+1F601} {U+1F60D} world!" }
46
+ context 'without any emoji' do
47
+ let(:body) { "Hello, boring world!" }
48
+ it { should be_persisted }
49
+ its(:body) { should eql body }
50
+ end
51
+
52
+ context 'with a nil value' do
53
+ let(:body) { nil }
54
+ it { should be_persisted }
55
+ its(:body) { should eql body }
56
+ end
52
57
  end
53
58
 
54
- context 'without any emoji' do
55
- let(:body) { "Hello, boring world!" }
56
- it { should be_persisted }
57
- it { expect(persisted_body).to eql "Hello, boring world!" }
59
+ describe :Callback do
60
+ subject { Comment.create(body: body) }
61
+ let(:persisted_body) { subject.read_attribute(:body) }
62
+
63
+ context 'with a single emoji' do
64
+ let(:body) { "Hello, 😁 world!" }
65
+ it { should be_persisted }
66
+ it { expect(persisted_body).to eql "Hello, {U+1F601} world!" }
67
+ end
68
+
69
+ context 'with multiple emoji' do
70
+ let(:body) { "Hello, 😁😁 😍 world!" }
71
+ it { should be_persisted }
72
+ it { expect(persisted_body).to eql "Hello, {U+1F601}{U+1F601} {U+1F60D} world!" }
73
+ end
74
+
75
+ context 'without any emoji' do
76
+ let(:body) { "Hello, boring world!" }
77
+ it { should be_persisted }
78
+ it { expect(persisted_body).to eql "Hello, boring world!" }
79
+ end
58
80
  end
59
81
  end
60
82
  end
@@ -2,21 +2,21 @@
2
2
  require 'spec_helper'
3
3
 
4
4
  describe Emojimmy do
5
- describe :text_to_emoji do
6
- let(:stored_comment) { 'Hello {U+1F601}{U+1F601} you {U+1F608} {U+1F438}!' }
7
- let(:returned_comment) { 'Hello 😁😁 you 😈 🐸!' }
5
+ describe :token_to_emoji do
6
+ let(:stored_text) { 'Hello {U+1F601}{U+1F601} you {U+1F608} {U+1F438}!' }
7
+ let(:returned_text) { 'Hello 😁😁 you 😈 🐸!' }
8
8
 
9
9
  specify do
10
- expect(Emojimmy.text_to_emoji(stored_comment)).to eql returned_comment
10
+ expect(Emojimmy.token_to_emoji(stored_text)).to eql returned_text
11
11
  end
12
12
  end
13
13
 
14
- describe :emoji_to_text do
15
- let(:received_comment) { 'Hello 😁😁 you 😈 🐸!' }
16
- let(:stored_comment) { 'Hello {U+1F601}{U+1F601} you {U+1F608} {U+1F438}!' }
14
+ describe :emoji_to_token do
15
+ let(:received_text) { 'Hello 😁😁 you 😈 🐸!' }
16
+ let(:stored_text) { 'Hello {U+1F601}{U+1F601} you {U+1F608} {U+1F438}!' }
17
17
 
18
18
  specify do
19
- expect(Emojimmy.emoji_to_text(received_comment)).to eql stored_comment
19
+ expect(Emojimmy.emoji_to_token(received_text)).to eql stored_text
20
20
  end
21
21
  end
22
22
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: emojimmy
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.2
4
+ version: 0.1.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Rémi Prévost
@@ -114,6 +114,7 @@ files:
114
114
  - gemfiles/Gemfile.activerecord-3.2.x
115
115
  - gemfiles/Gemfile.activerecord-4.0
116
116
  - lib/emojimmy.rb
117
+ - lib/emojimmy/extensions.rb
117
118
  - lib/emojimmy/mixin.rb
118
119
  - lib/emojimmy/version.rb
119
120
  - spec/emojimmy/mixin_spec.rb