jera_push 1.2.4 → 2.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (74) hide show
  1. checksums.yaml +4 -4
  2. data/Rakefile +12 -18
  3. data/app/controllers/jera_push/admin/messages_controller.rb +27 -12
  4. data/app/controllers/jera_push/jera_push_controller.rb +0 -2
  5. data/app/presenters/jera_push/message_presenter.rb +22 -18
  6. data/app/views/jera_push/admin/messages/show.html.erb +7 -4
  7. data/config/locale/jera_push.pt-BR.yml +7 -0
  8. data/config/routes.rb +1 -0
  9. data/lib/generators/active_record/templates/create_jera_push_devices.rb +2 -1
  10. data/lib/generators/active_record/templates/create_jera_push_messages.rb +6 -3
  11. data/lib/generators/active_record/templates/create_jera_push_messages_devices.rb +3 -3
  12. data/lib/generators/jera_push/templates/jera_push.rb +2 -1
  13. data/lib/jera_push/firebase/client.rb +53 -56
  14. data/lib/jera_push/models/android_config.rb +33 -0
  15. data/lib/jera_push/models/apple_config.rb +61 -0
  16. data/lib/jera_push/models/device.rb +3 -31
  17. data/lib/jera_push/models/message.rb +2 -142
  18. data/lib/jera_push/models/message_device.rb +1 -0
  19. data/lib/jera_push/models/notification.rb +25 -0
  20. data/lib/jera_push/models/push_body.rb +90 -0
  21. data/lib/jera_push/services/base_service.rb +23 -0
  22. data/lib/jera_push/services/send_message.rb +20 -4
  23. data/lib/jera_push/services/send_push_service.rb +42 -0
  24. data/lib/jera_push/services/send_to_device_service.rb +42 -0
  25. data/lib/jera_push/services/send_to_devices_service.rb +45 -0
  26. data/lib/jera_push/services/send_to_everyone_service.rb +40 -0
  27. data/lib/jera_push/services/send_to_topic_service.rb +37 -0
  28. data/lib/jera_push/services/topic_service.rb +18 -0
  29. data/lib/jera_push/version.rb +1 -1
  30. data/lib/jera_push.rb +23 -5
  31. metadata +75 -116
  32. data/test/dummy/README.rdoc +0 -28
  33. data/test/dummy/Rakefile +0 -6
  34. data/test/dummy/app/assets/javascripts/application.js +0 -13
  35. data/test/dummy/app/assets/stylesheets/application.css +0 -15
  36. data/test/dummy/app/controllers/application_controller.rb +0 -5
  37. data/test/dummy/app/helpers/application_helper.rb +0 -2
  38. data/test/dummy/app/models/user.rb +0 -3
  39. data/test/dummy/app/views/layouts/application.html.erb +0 -14
  40. data/test/dummy/bin/bundle +0 -3
  41. data/test/dummy/bin/rails +0 -4
  42. data/test/dummy/bin/rake +0 -4
  43. data/test/dummy/bin/setup +0 -29
  44. data/test/dummy/config/application.rb +0 -25
  45. data/test/dummy/config/boot.rb +0 -5
  46. data/test/dummy/config/database.yml +0 -16
  47. data/test/dummy/config/environment.rb +0 -5
  48. data/test/dummy/config/environments/development.rb +0 -41
  49. data/test/dummy/config/environments/production.rb +0 -79
  50. data/test/dummy/config/environments/test.rb +0 -42
  51. data/test/dummy/config/initializers/assets.rb +0 -12
  52. data/test/dummy/config/initializers/backtrace_silencers.rb +0 -7
  53. data/test/dummy/config/initializers/cookies_serializer.rb +0 -3
  54. data/test/dummy/config/initializers/filter_parameter_logging.rb +0 -4
  55. data/test/dummy/config/initializers/inflections.rb +0 -16
  56. data/test/dummy/config/initializers/mime_types.rb +0 -4
  57. data/test/dummy/config/initializers/session_store.rb +0 -3
  58. data/test/dummy/config/initializers/wrap_parameters.rb +0 -14
  59. data/test/dummy/config/locales/en.yml +0 -23
  60. data/test/dummy/config/locales/pt-BR.yml +0 -23
  61. data/test/dummy/config/routes.rb +0 -57
  62. data/test/dummy/config/secrets.yml +0 -22
  63. data/test/dummy/config.ru +0 -4
  64. data/test/dummy/db/migrate/20161005121035_create_users.rb +0 -10
  65. data/test/dummy/db/schema.rb +0 -61
  66. data/test/dummy/db/seeds.rb +0 -70
  67. data/test/dummy/public/404.html +0 -67
  68. data/test/dummy/public/422.html +0 -67
  69. data/test/dummy/public/500.html +0 -66
  70. data/test/dummy/public/favicon.ico +0 -0
  71. data/test/dummy/test/fixtures/users.yml +0 -7
  72. data/test/dummy/test/models/user_test.rb +0 -7
  73. data/test/jera_push_test.rb +0 -7
  74. data/test/test_helper.rb +0 -20
@@ -2,152 +2,12 @@ require 'enumerize'
2
2
 
3
3
  class JeraPush::Message < ActiveRecord::Base
4
4
  extend Enumerize
5
+
5
6
  self.table_name = "jera_push_messages"
6
7
 
7
8
  has_many :message_devices
8
9
  has_many :devices, through: :message_devices
9
10
 
10
- serialize :broadcast_result
11
-
12
- enumerize :kind, in: [:broadcast, :specific], predicate: true, default: :specific
13
-
14
- def self.send_to(target, content: {})
15
- return nil if target.blank? || content.blank?
16
-
17
- push_message = JeraPush::Message.create content: content
18
- push_message.devices << target
19
-
20
- if push_message && target.is_a?(JeraPush::Device)
21
- push_message.send_to_device device: target
22
- else
23
- push_message.send_to_devices devices: target
24
- end
25
- push_message
26
- end
27
-
28
- def self.send_broadcast(content:)
29
- return nil if content.blank?
30
-
31
- push_message = JeraPush::Message.create content: content, kind: :broadcast
32
- @@client ||= JeraPush::Firebase::Client.instance
33
-
34
- results = []
35
- results << push_message.to_android_topic
36
- results << push_message.to_ios_topic
37
- results << push_message.to_chrome_topic
38
-
39
- JeraPush::Firebase::ApiResult.broadcast_result(message: push_message, results: results)
40
- push_message
41
- end
42
-
43
- def self.send_to_topic(topic: , content: {})
44
- return nil if topic.blank? || content.blank?
45
-
46
- push_message = JeraPush::Message.create content: content, topic: topic
47
- client = JeraPush::Firebase::Client.instance
48
- response = client.send_message_to_topic(message: { data: content }, topic: topic)
49
- response.topic_result(message: push_message)
50
- push_message
51
- end
52
-
53
- def self.format_hash(messages = [])
54
- return false if messages.blank?
55
- messages.collect do |obj|
56
- hash = { obj[:key].to_sym => obj[:value] }
57
- hash.delete_if { |key, value| key.blank? || value.blank? }
58
- end.reduce(:merge)
59
- end
60
-
61
- def content=(content)
62
- raise 'Invalid message format. Hash format expected' unless content.is_a? Hash
63
-
64
- super(content.to_json)
65
- end
66
-
67
- def content
68
- if super()
69
- JSON.parse(super())
70
- else
71
- return {}
72
- end
73
- end
74
-
75
- def send_to_devices(devices: [])
76
- return nil if devices.empty?
77
- platform_devices = devices.group_by { |device| device.platform }
78
- client = JeraPush::Firebase::Client.instance
79
-
80
- platform_devices.keys.each do |platform|
81
- payload = self.send("body_#{platform.to_s}", self.content)
82
- response = client.send_message(message: payload, devices: platform_devices[platform])
83
- if response
84
- response.result_to(message: self)
85
- end
86
- end
87
- end
88
-
89
- def send_to_device(device: nil)
90
- return nil if device.nil?
91
-
92
- payload = {}
93
- if device.platform.ios?
94
- payload = body_ios(self.content)
95
- elsif device.platform.android?
96
- payload = body_android(self.content)
97
- elsif device.platform.chrome?
98
- payload = body_chrome(self.content)
99
- end
100
- client = JeraPush::Firebase::Client.instance
101
- response = client.send_message(message: payload, devices: [device])
102
- if response
103
- response.result_to(message: self)
104
- end
105
- end
106
-
107
- def to_android_topic
108
- @@client.send_message_to_topic(
109
- message: body_android(content),
110
- topic: JeraPush.topic_android
111
- )
112
- end
113
-
114
- def to_ios_topic
115
- @@client.send_message_to_topic(
116
- message: body_ios(content),
117
- topic: JeraPush.topic_ios
118
- )
119
- end
120
-
121
- def to_chrome_topic
122
- @@client.send_message_to_topic(
123
- message: body_chrome(content),
124
- topic: JeraPush.topic_chrome
125
- )
126
- end
127
-
128
- private
129
-
130
- def body_ios(content)
131
- params = [:title, :body, :'content-available', :sound, :badge, :click_action, :body_loc_key, :body_loc_args, :title_loc_key, :title_loc_args]
132
-
133
- content.symbolize_keys!
134
- content[:sound] = 'default' unless content.has_key?(:sound)
135
-
136
- return {
137
- notification: content.select { |key, value| params.include?(key) },
138
- data: content.reject { |key, value| params.include?(key) }
139
- }
140
- end
141
-
142
- def body_android(content)
143
- return {
144
- data: content
145
- }
146
- end
11
+ enumerize :kind, in: [:specific, :everyone, :topic], predicate: true, default: :specific
147
12
 
148
- def body_chrome(content)
149
- return {
150
- data: content
151
- }
152
- end
153
13
  end
@@ -1,6 +1,7 @@
1
1
  require 'enumerize'
2
2
  class JeraPush::MessageDevice < ActiveRecord::Base
3
3
  extend Enumerize
4
+
4
5
  self.table_name = "jera_push_messages_devices"
5
6
 
6
7
  belongs_to :device
@@ -0,0 +1,25 @@
1
+ module JeraPush
2
+ class Notification
3
+ attr_accessor :title
4
+ attr_accessor :body
5
+ attr_accessor :image
6
+
7
+ def initialize(
8
+ title: '',
9
+ body: '',
10
+ image: ''
11
+ )
12
+ self.title = title
13
+ self.body = body
14
+ self.image = image
15
+ end
16
+
17
+ def to_json
18
+ {
19
+ title: title,
20
+ body: body,
21
+ image: image
22
+ }
23
+ end
24
+ end
25
+ end
@@ -0,0 +1,90 @@
1
+ module JeraPush
2
+ class PushBody
3
+ attr_accessor :device
4
+ attr_accessor :devices
5
+ attr_accessor :notification
6
+ attr_accessor :data
7
+ attr_accessor :android
8
+ attr_accessor :ios
9
+ attr_accessor :analytics_label
10
+ attr_accessor :validate_only
11
+
12
+ def initialize(
13
+ data: {},
14
+ device: nil,
15
+ devices: [],
16
+ validate_only: false,
17
+ analytics_label: '',
18
+ ios_config: AppleConfig.new,
19
+ title: '',
20
+ body: '',
21
+ image: '',
22
+ notification: nil,
23
+ android_config: AndroidConfig.new
24
+ )
25
+ self.data = data
26
+ self.device = device
27
+ self.devices = devices
28
+ self.validate_only = validate_only
29
+ self.analytics_label = analytics_label
30
+ self.ios = ios_config
31
+ self.notification = notification.nil? ? Notification.new(title: title, body: body, image: image) : notification
32
+ self.android = android_config
33
+ end
34
+
35
+ def to_json
36
+ base_body
37
+ end
38
+
39
+ private
40
+
41
+ # REF: https://firebase.google.com/docs/reference/fcm/rest/v1/projects.messages?hl=pt-br#resource:-message
42
+ def base_body
43
+ {
44
+ message: build_message_body,
45
+ validate_only: validate_only
46
+ }
47
+ end
48
+
49
+ # REF: https://firebase.google.com/docs/reference/fcm/rest/v1/projects.messages?hl=pt-br#resource:-message
50
+ def build_message_body
51
+ {
52
+ token: device.token,
53
+ notification: notification_body,
54
+ data: data_body,
55
+ apns: apns_body,
56
+ android: android_body,
57
+ fcm_options: fcm_body
58
+ }
59
+ end
60
+
61
+ # REF: https://firebase.google.com/docs/reference/fcm/rest/v1/projects.messages?hl=pt-br#Notification
62
+ def notification_body
63
+ notification.to_json
64
+ end
65
+
66
+ # REF: https://firebase.google.com/docs/reference/fcm/rest/v1/projects.messages?hl=pt-br#resource:-message
67
+ def data_body
68
+ data.merge(notification.to_json)
69
+ end
70
+
71
+ # REF: https://firebase.google.com/docs/reference/fcm/rest/v1/projects.messages?hl=pt-br#ApnsConfig
72
+ def apns_body
73
+ ios.analytics_label = analytics_label
74
+ ios.to_json
75
+ end
76
+
77
+ # REF: https://firebase.google.com/docs/reference/fcm/rest/v1/projects.messages?hl=pt-br#AndroidConfig
78
+ def android_body
79
+ android.analytics_label = analytics_label
80
+ android.to_json
81
+ end
82
+
83
+ # REF: https://firebase.google.com/docs/reference/fcm/rest/v1/projects.messages?hl=pt-br#FcmOptions
84
+ def fcm_body
85
+ {
86
+ analytics_label: analytics_label
87
+ }
88
+ end
89
+ end
90
+ end
@@ -0,0 +1,23 @@
1
+ module JeraPush::Services
2
+ class BaseService
3
+ extend ActiveModel::Naming
4
+
5
+ def initialize(*)
6
+ @errors = ActiveModel::Errors.new(self)
7
+ @firebase = JeraPush::Firebase::Client.new
8
+ end
9
+
10
+ def read_attribute_for_validation(attr)
11
+ send(attr)
12
+ end
13
+
14
+ def self.human_attribute_name(attr, options = {})
15
+ attr
16
+ end
17
+
18
+ def self.lookup_ancestors
19
+ [self]
20
+ end
21
+
22
+ end
23
+ end
@@ -1,5 +1,5 @@
1
1
  module JeraPush
2
- module Service
2
+ module Services
3
3
  class SendMessage
4
4
 
5
5
  def initialize(*args)
@@ -11,13 +11,21 @@ module JeraPush
11
11
  def call
12
12
  return false unless valid?
13
13
 
14
- message_content = JeraPush::Message.format_hash @message
14
+ message_content = format_hash(@message)
15
15
  case @type
16
16
  when :broadcast
17
- JeraPush::Message.send_broadcast(content: message_content)
17
+ # Topicos não estão funcionando.
18
+ # JeraPush::Message.send_broadcast(content: message_content)
18
19
  when :specific
19
20
  target_devices = JeraPush::Device.where(id: @devices.uniq.map(&:to_i))
20
- JeraPush::Message.send_to(target_devices, content: message_content)
21
+ push = JeraPush::PushBody.new(
22
+ title: message_content[:title],
23
+ body: message_content[:body],
24
+ data: message_content,
25
+ devices: target_devices
26
+ )
27
+ result = JeraPush::Services::SendToDevicesService.new(push: push).call
28
+ result
21
29
  end
22
30
  end
23
31
 
@@ -26,6 +34,14 @@ module JeraPush
26
34
  @type.to_sym == :broadcast ? valid : valid && @devices.present?
27
35
  end
28
36
 
37
+ def format_hash(messages = [])
38
+ return false if messages.blank?
39
+ messages.collect do |obj|
40
+ hash = { obj[:key].to_sym => obj[:value] }
41
+ hash.delete_if { |key, value| key.blank? || value.blank? }
42
+ end.reduce(:merge)
43
+ end
44
+
29
45
  end
30
46
  end
31
47
  end
@@ -0,0 +1,42 @@
1
+ module JeraPush::Services
2
+ class SendPushService < JeraPush::Services::BaseService
3
+ def initialize(push:, message:, message_device:)
4
+ super
5
+ @push = push
6
+ @message = message
7
+ @message_device = message_device
8
+ end
9
+
10
+ def call
11
+ return @errors if @errors.present?
12
+
13
+ send_push
14
+
15
+ @message
16
+ end
17
+
18
+ private
19
+
20
+ def send_push
21
+ @response = @firebase.send_to_device(push: @push)
22
+ save_success
23
+ rescue Google::Apis::AuthorizationError => e
24
+ message = JSON.parse(e.body)
25
+ save_error(message)
26
+ rescue Google::Apis::ClientError => e
27
+ response = JSON.parse(e.body, symbolize_names: true)
28
+ error_code = response[:error][:details][0][:errorCode]
29
+ save_error(response)
30
+ end
31
+
32
+ def save_success
33
+ @message_device.update(status: :success)
34
+ @message.update(success_count: @message.success_count + 1)
35
+ end
36
+
37
+ def save_error(error)
38
+ @message_device.update(status: :error, error_message: error.to_json)
39
+ @message.update(failure_count: @message.failure_count + 1)
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,42 @@
1
+ module JeraPush::Services
2
+ class SendToDeviceService < JeraPush::Services::BaseService
3
+ def initialize(push:)
4
+ super
5
+ @push = push
6
+ @device = @push.device
7
+ end
8
+
9
+ def call
10
+ validate_device
11
+
12
+ return @errors if @errors.present?
13
+
14
+ create_message
15
+ add_devices_to_message
16
+ send_push
17
+
18
+ @message
19
+ end
20
+
21
+ private
22
+
23
+ def validate_device
24
+ @errors.add(:base, message: I18n.t('jera_push.services.errors.not_found.device')) if @device.blank?
25
+ end
26
+
27
+ def create_message
28
+ @message = JeraPush::Message.create(title: @push.notification.title, body: @push.notification.body, data: @push.data)
29
+ end
30
+
31
+ def add_devices_to_message
32
+ @message_device = @message.message_devices.create(device: @device)
33
+ end
34
+
35
+ def send_push
36
+ JeraPush::Services::SendPushService.new(push: @push,
37
+ message: @message,
38
+ message_device: @message_device
39
+ ).call
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,45 @@
1
+ module JeraPush::Services
2
+ class SendToDevicesService < JeraPush::Services::BaseService
3
+ def initialize(push:)
4
+ super
5
+ @push = push
6
+ @device = @push.devices
7
+ end
8
+
9
+ def call
10
+ validate_device
11
+
12
+ return @errors if @errors.present?
13
+
14
+ create_message
15
+ send_push_to_devices
16
+
17
+ @message
18
+ end
19
+
20
+ private
21
+
22
+ def validate_device
23
+ @errors.add(:base, message: I18n.t('jera_push.services.errors.not_found.device')) if @devices.empty?
24
+ end
25
+
26
+ def create_message
27
+ @message = JeraPush::Message.create(title: @push.notification.title, body: @push.notification.body, data: @push.data)
28
+ end
29
+
30
+ def send_push_to_devices
31
+ @devices.each do |device|
32
+ message_device = @message.message_devices.create(device: device)
33
+ @push.device = device
34
+ send_push(device, message_device)
35
+ end
36
+ end
37
+
38
+ def send_push
39
+ JeraPush::Services::SendPushService.new(push: @push,
40
+ message: @message,
41
+ message_device: @message_device
42
+ ).call
43
+ end
44
+ end
45
+ end
@@ -0,0 +1,40 @@
1
+ module JeraPush::Services
2
+ class SendToEveryoneService < JeraPush::Services::BaseService
3
+ def initialize(title:, body:)
4
+ super
5
+ @title = title
6
+ @body = body
7
+ end
8
+
9
+ def call
10
+ create_message
11
+ send_android
12
+ send_ios
13
+ update_message
14
+
15
+ @message
16
+ end
17
+
18
+ private
19
+
20
+ def create_message
21
+ @message = JeraPush::Message.create(title: @title, body: @body, kind: :everyone)
22
+ end
23
+
24
+ def send_android
25
+ @response_android = @firebase.send_message_to_topic(message: @message, topic: JeraPush.send('topic_android'))
26
+ end
27
+
28
+ def send_ios
29
+ @response_ios = @firebase.send_message_to_topic(message: @message, topic: JeraPush.send('topic_ios'))
30
+ end
31
+
32
+ def update_message
33
+ @message.update(
34
+ success_count: @response_android["success"] + @response_ios["success"],
35
+ failure_count: @response_android["failure"] + @response_ios["failure"]
36
+ )
37
+ end
38
+
39
+ end
40
+ end
@@ -0,0 +1,37 @@
1
+ module JeraPush::Services
2
+ class SendToTopicService < JeraPush::Services::BaseService
3
+ def initialize(title:, body:, topic:)
4
+ super
5
+ @title = title
6
+ @body = body
7
+ @topic = topic
8
+ end
9
+
10
+ def call
11
+ create_message
12
+ send_topic
13
+ update_message
14
+
15
+ @message
16
+ end
17
+
18
+ private
19
+
20
+ def create_message
21
+ @message = JeraPush::Message.create(title: @title, body: @body, kind: :topic)
22
+ end
23
+
24
+ def send_topic
25
+ @response = @firebase.send_message_to_topic(message: @message, topic: @topic)
26
+ end
27
+
28
+ def update_message
29
+ @message.update(
30
+ multicast_id: @response["multicast_id"],
31
+ success_count: @response["success"],
32
+ failure_count: @response["failure"]
33
+ )
34
+ end
35
+
36
+ end
37
+ end
@@ -0,0 +1,18 @@
1
+ module JeraPush::Services
2
+ class TopicService < JeraPush::Services::BaseService
3
+ DEFAULT_TOPIC = 'general'
4
+
5
+ def initialize(*)
6
+ super
7
+ end
8
+
9
+ def subscribe(device:, topic: DEFAULT_TOPIC)
10
+ @firebase.add_device_to_topic(device: device, topic: topic)
11
+ end
12
+
13
+ def unsubscribe(device:, topic: DEFAULT_TOPIC)
14
+ @firebase.remove_device_from_topic(devices: [device], topic: topic)
15
+ end
16
+
17
+ end
18
+ end
@@ -1,3 +1,3 @@
1
1
  module JeraPush
2
- VERSION = "1.2.4"
2
+ VERSION = "2.1.0"
3
3
  end
data/lib/jera_push.rb CHANGED
@@ -5,31 +5,52 @@ require 'kaminari'
5
5
  require 'jera_push/engine'
6
6
  require 'jera_push/firebase/client'
7
7
  require 'jera_push/firebase/api_result'
8
+ require 'googleauth'
9
+ require 'google/apis/fcm_v1'
10
+
11
+ require 'jera_push/services/base_service'
8
12
  require 'jera_push/services/send_message'
13
+ require 'jera_push/services/send_push_service'
14
+ require 'jera_push/services/send_to_device_service'
15
+ require 'jera_push/services/send_to_devices_service'
16
+ require 'jera_push/services/send_to_everyone_service'
17
+ require 'jera_push/services/send_to_topic_service'
18
+ require 'jera_push/services/topic_service'
9
19
 
10
20
  module JeraPush
11
-
12
21
  autoload :Device, 'jera_push/models/device.rb'
13
22
  autoload :Message, 'jera_push/models/message.rb'
14
23
  autoload :MessageDevice, 'jera_push/models/message_device.rb'
15
24
  autoload :DeviceFilter, 'jera_push/models/device_filter.rb'
25
+ autoload :PushBody, 'jera_push/models/push_body.rb'
26
+ autoload :AppleConfig, 'jera_push/models/apple_config.rb'
27
+ autoload :AndroidConfig, 'jera_push/models/android_config.rb'
28
+ autoload :Notification, 'jera_push/models/notification.rb'
16
29
 
17
30
  mattr_accessor :firebase_api_key
18
31
  @@firebase_api_key = nil
19
32
 
33
+ mattr_accessor :project_name
34
+ @@project_name = nil
35
+
36
+ mattr_accessor :project_id
37
+ @@project_id = nil
38
+
20
39
  mattr_accessor :default_topic
21
40
  @@default_topic = 'jera_push_development'
22
41
 
23
42
  mattr_accessor :resources_name
24
43
  @@resources_name = nil
25
44
 
45
+ mattr_accessor :credentials_path
46
+ @@credentials_path = nil
47
+
26
48
  mattr_accessor :resource_attributes
27
49
  @@resource_attributes = []
28
50
 
29
51
  mattr_accessor :admin_login
30
52
  @@resources_name = { username: 'jera_push', password: 'JeraPushAdmin' }
31
53
 
32
-
33
54
  def self.setup
34
55
  yield self
35
56
  end
@@ -42,7 +63,4 @@ module JeraPush
42
63
  @@ios_topic ||= "#{@@default_topic}_ios"
43
64
  end
44
65
 
45
- def self.topic_chrome
46
- @@chrome_topic ||= "#{@@default_topic}_chrome"
47
- end
48
66
  end