smartkiosk-client 0.0.1
Sign up to get free protection for your applications and to get access to all the features.
- data/Gemfile +5 -0
- data/Gemfile.lock +176 -0
- data/Rakefile +4 -0
- data/app/controllers/banners.rb +14 -0
- data/app/controllers/collections.rb +10 -0
- data/app/controllers/config.rb +23 -0
- data/app/controllers/payments.rb +30 -0
- data/app/controllers/receipts.rb +13 -0
- data/app/controllers/terminal.rb +104 -0
- data/app/models/admin.rb +3 -0
- data/app/models/banner.rb +5 -0
- data/app/models/collection.rb +53 -0
- data/app/models/customer.rb +3 -0
- data/app/models/group.rb +37 -0
- data/app/models/order.rb +25 -0
- data/app/models/payment.rb +80 -0
- data/app/models/phone_range.rb +3 -0
- data/app/models/promotion.rb +11 -0
- data/app/models/provider.rb +42 -0
- data/app/models/receipt.rb +21 -0
- data/app/models/receipt_template.rb +5 -0
- data/app/models/terminal.rb +152 -0
- data/app/uploaders/icon_uploader.rb +9 -0
- data/app/views/banners.haml +50 -0
- data/app/workers/orders/acknowledge_worker.rb +22 -0
- data/app/workers/orders/complete_worker.rb +20 -0
- data/app/workers/orders/disable_worker.rb +16 -0
- data/app/workers/orders/enable_worker.rb +16 -0
- data/app/workers/orders/reboot_worker.rb +18 -0
- data/app/workers/orders/reload_worker.rb +18 -0
- data/app/workers/orders/upgrade_worker.rb +108 -0
- data/app/workers/payments/check_worker.rb +35 -0
- data/app/workers/payments/collect_worker.rb +23 -0
- data/app/workers/payments/pay_worker.rb +21 -0
- data/app/workers/ping_worker.rb +180 -0
- data/app/workers/startup_worker.rb +11 -0
- data/app/workers/sync/icons_worker.rb +20 -0
- data/app/workers/sync/receipt_templates_worker.rb +27 -0
- data/config/boot.rb +104 -0
- data/config/services/application.yml +4 -0
- data/config/services/database.yml +17 -0
- data/config/services/database.yml.sample +33 -0
- data/config/services/smartware.yml +28 -0
- data/config/services/smartware.yml.sample +13 -0
- data/config/sidekiq.yml +12 -0
- data/db/development.sqlite3 +0 -0
- data/db/migrate/20121230080152_create_customers.rb +8 -0
- data/db/migrate/20121230080159_create_admins.rb +11 -0
- data/db/migrate/20130106150707_create_orders.rb +14 -0
- data/db/migrate/20130106155321_create_providers.rb +19 -0
- data/db/migrate/20130106160834_create_groups.rb +11 -0
- data/db/migrate/20130106181512_create_receipt_templates.rb +9 -0
- data/db/migrate/20130106181548_create_payments.rb +26 -0
- data/db/migrate/20130106181729_create_collections.rb +10 -0
- data/db/migrate/20130106181803_create_receipts.rb +15 -0
- data/db/migrate/20130106181844_create_phone_ranges.rb +14 -0
- data/db/migrate/20130108110546_create_promotions.rb +9 -0
- data/db/migrate/20130110025256_create_banners.rb +12 -0
- data/init.rb +1 -0
- data/lib/pinger.rb +22 -0
- data/lib/sidekiq.rb +20 -0
- data/lib/smartkiosk/client/version.rb +7 -0
- data/lib/smartkiosk/client.rb +1 -0
- data/lib/smartkiosk/config/chunk.rb +7 -0
- data/lib/smartkiosk/config/yaml.rb +26 -0
- data/lib/tasks/db.rb +15 -0
- data/lib/tasks/pack.rb +27 -0
- data/lib/tasks/scheduler.rb +27 -0
- data/lib/tasks/services.rb +20 -0
- data/server.rb +11 -0
- data/smartkiosk-client.gemspec +55 -0
- data/tmp/pids/.gitkeep +0 -0
- data/tmp/pids/sidekiq.pid +1 -0
- data/vendor/assets/javascripts/jquery.js +9555 -0
- metadata +444 -0
@@ -0,0 +1,152 @@
|
|
1
|
+
require 'smartware'
|
2
|
+
require 'socket'
|
3
|
+
require 'redis'
|
4
|
+
require 'redis/objects'
|
5
|
+
|
6
|
+
Application.load 'lib/smartkiosk/config/yaml'
|
7
|
+
|
8
|
+
class Terminal
|
9
|
+
include Redis::Objects
|
10
|
+
|
11
|
+
value :state, :global => true
|
12
|
+
value :started_at, :global => true, :marshal => true
|
13
|
+
value :modified_at, :global => true, :marshal => true
|
14
|
+
value :payment_in_progress, :global => true
|
15
|
+
|
16
|
+
value :support_phone, :global => true
|
17
|
+
value :providers_updates, :global => true, :marshal => true
|
18
|
+
|
19
|
+
def self.smartguard
|
20
|
+
DRbObject.new_with_uri(Terminal.config.smartguard_host)
|
21
|
+
end
|
22
|
+
|
23
|
+
#
|
24
|
+
# STATES
|
25
|
+
#
|
26
|
+
def self.enable
|
27
|
+
self.state = 'active'
|
28
|
+
end
|
29
|
+
|
30
|
+
def self.disable
|
31
|
+
self.state = 'disabled'
|
32
|
+
end
|
33
|
+
|
34
|
+
def self.payment_in_progress?
|
35
|
+
self.payment_in_progress.value == "true"
|
36
|
+
end
|
37
|
+
|
38
|
+
def self.actual_state
|
39
|
+
self.state.value || 'active'
|
40
|
+
end
|
41
|
+
|
42
|
+
def self.actual_modified_at
|
43
|
+
self.modified_at.value || DateTime.now
|
44
|
+
end
|
45
|
+
|
46
|
+
def self.providers_updated_at
|
47
|
+
self.providers_updates[self.config.host] rescue nil
|
48
|
+
end
|
49
|
+
|
50
|
+
def self.providers_updated_at=(value)
|
51
|
+
self.providers_updates = {self.config.host => value}
|
52
|
+
end
|
53
|
+
|
54
|
+
#
|
55
|
+
# ACTIONS
|
56
|
+
#
|
57
|
+
def self.ping
|
58
|
+
PingWorker.perform_async
|
59
|
+
end
|
60
|
+
|
61
|
+
def self.reload
|
62
|
+
smartguard.restart_async
|
63
|
+
end
|
64
|
+
|
65
|
+
def self.reboot
|
66
|
+
self.state = 'rebooting'
|
67
|
+
StartupWorker.perform_async self.name, :enable
|
68
|
+
|
69
|
+
smartguard.reboot_async
|
70
|
+
end
|
71
|
+
|
72
|
+
#
|
73
|
+
# CONDITON
|
74
|
+
#
|
75
|
+
def self.config
|
76
|
+
@config ||= Smartkiosk::Config::YAML.new(Application.root.join 'config/services/application.yml')
|
77
|
+
end
|
78
|
+
|
79
|
+
def self.keyword
|
80
|
+
config.keyword
|
81
|
+
end
|
82
|
+
|
83
|
+
def self.enabled?
|
84
|
+
self.actual_state == 'active'
|
85
|
+
end
|
86
|
+
|
87
|
+
def self.version
|
88
|
+
'0.1'
|
89
|
+
end
|
90
|
+
|
91
|
+
def self.ip
|
92
|
+
orig, Socket.do_not_reverse_lookup = Socket.do_not_reverse_lookup, true
|
93
|
+
|
94
|
+
UDPSocket.open do |s|
|
95
|
+
s.connect '64.233.187.99', 1
|
96
|
+
s.addr.last
|
97
|
+
end
|
98
|
+
rescue
|
99
|
+
'0.0.0.0'
|
100
|
+
ensure
|
101
|
+
Socket.do_not_reverse_lookup = orig
|
102
|
+
end
|
103
|
+
|
104
|
+
def self.as_json
|
105
|
+
{
|
106
|
+
:started_at => Terminal.started_at.value,
|
107
|
+
:modified_at => Terminal.actual_modified_at,
|
108
|
+
:keyword => Terminal.keyword,
|
109
|
+
:support_phone => Terminal.support_phone.value,
|
110
|
+
:groups => Group.all.map{|x| x.as_json},
|
111
|
+
:providers => Provider.active.map{|x| x.as_json},
|
112
|
+
:promotions => Promotion.order(:priority).limit(6).map{|x| x.provider_id}
|
113
|
+
}
|
114
|
+
end
|
115
|
+
|
116
|
+
def self.condition
|
117
|
+
{
|
118
|
+
:ip => ip,
|
119
|
+
:state => Terminal.actual_state,
|
120
|
+
:banknotes => Payment.merge_banknotes(Payment.uncollected),
|
121
|
+
:cash => Payment.merge_cash(Payment.uncollected),
|
122
|
+
:providers => {
|
123
|
+
:updated_at => Terminal.providers_updated_at,
|
124
|
+
:ids => Provider.select(:foreign_id).map{|x| x.foreign_id} || []
|
125
|
+
},
|
126
|
+
:queues => {
|
127
|
+
:payments => Sidekiq::Queue.new('payments').size,
|
128
|
+
:pings => Sidekiq::Queue.new('pings').size,
|
129
|
+
:orders => Sidekiq::Queue.new('orders').size,
|
130
|
+
:sync => Sidekiq::Queue.new('sync').size
|
131
|
+
},
|
132
|
+
:cash_acceptor => {
|
133
|
+
:error => Smartware.cash_acceptor.error,
|
134
|
+
:model => Smartware.cash_acceptor.model,
|
135
|
+
:version => Smartware.cash_acceptor.version
|
136
|
+
},
|
137
|
+
:printer => {
|
138
|
+
:error => Smartware.printer.error,
|
139
|
+
:model => Smartware.printer.model,
|
140
|
+
:version => Smartware.printer.version
|
141
|
+
},
|
142
|
+
:modem => {
|
143
|
+
:error => Smartware.modem.error,
|
144
|
+
:signal_level => Smartware.modem.signal_level,
|
145
|
+
:balance => Smartware.modem.balance,
|
146
|
+
:model => Smartware.modem.model,
|
147
|
+
:version => Smartware.modem.version
|
148
|
+
},
|
149
|
+
:version => Terminal.version
|
150
|
+
}
|
151
|
+
end
|
152
|
+
end
|
@@ -0,0 +1,50 @@
|
|
1
|
+
!!!
|
2
|
+
%html{:lang => "ru"}
|
3
|
+
%head
|
4
|
+
%meta{:charset => "utf-8"}
|
5
|
+
%meta{:content => "width=device-width, initial-scale=1.0", :name => "viewport"}
|
6
|
+
%title banners
|
7
|
+
%script{:type => 'text/javascript', :src => '/assets/jquery.js'}
|
8
|
+
|
9
|
+
:javascript
|
10
|
+
var playBanner;
|
11
|
+
|
12
|
+
playBanner = function(prev) {
|
13
|
+
if (prev == null) {
|
14
|
+
prev = 0;
|
15
|
+
}
|
16
|
+
return $.get("/banners/playlist?prev=" + prev, function(banner) {
|
17
|
+
var playNext,
|
18
|
+
_this = this;
|
19
|
+
if (banner.filename.substr(banner.filename.length-4) === '.swf') {
|
20
|
+
$('video').hide();
|
21
|
+
$('video').attr('src', '');
|
22
|
+
$('object').show();
|
23
|
+
$('object').attr('data', banner.filename);
|
24
|
+
$('object > embed').attr('src', banner.filename);
|
25
|
+
return playNext = setTimeout(function() {
|
26
|
+
return playBanner(banner.playorder);
|
27
|
+
}, parseInt(parseFloat(banner.duration) * 1000));
|
28
|
+
} else {
|
29
|
+
$('object').hide();
|
30
|
+
$('object').attr('data', '');
|
31
|
+
$('object > embed').attr('src', '');
|
32
|
+
$('video').show();
|
33
|
+
$('video').attr('src', banner.filename);
|
34
|
+
$('video')[0].play();
|
35
|
+
return playNext = setTimeout(function() {
|
36
|
+
$('video')[0].pause();
|
37
|
+
return playBanner(banner.playorder);
|
38
|
+
}, parseInt(parseFloat(banner.duration) * 1000));
|
39
|
+
}
|
40
|
+
});
|
41
|
+
};
|
42
|
+
|
43
|
+
playBanner();
|
44
|
+
|
45
|
+
|
46
|
+
%body{:style => 'margin: 0; padding: 0;'}
|
47
|
+
%video{:width => "1280", :height => "1024", :type => 'video/webm', :style => "max-height: 1019px; max-width: 1280px;" }
|
48
|
+
%object{:height => '1019', :width => '1280', :type => "application/x-shockwave-flash" }
|
49
|
+
%param{:name => "autoplay", :value => "true"}
|
50
|
+
%embed{:height => '1019', :width => '1280' }
|
@@ -0,0 +1,22 @@
|
|
1
|
+
require 'rest-client'
|
2
|
+
|
3
|
+
Application.load 'lib/sidekiq'
|
4
|
+
|
5
|
+
module Orders
|
6
|
+
class AcknowledgeWorker
|
7
|
+
include Sidekiq::Worker
|
8
|
+
|
9
|
+
sidekiq_options :queue => :orders
|
10
|
+
|
11
|
+
def perform(order_id, error=nil, percent=nil)
|
12
|
+
order = Order.find(order_id)
|
13
|
+
|
14
|
+
response = RestClient.post "#{Terminal.config.host}/terminal_orders/#{order.foreign_id}/acknowledge",
|
15
|
+
:terminal => Terminal.keyword,
|
16
|
+
:error => error,
|
17
|
+
:percent => percent
|
18
|
+
|
19
|
+
order.acknowledged!
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
require 'rest-client'
|
2
|
+
|
3
|
+
Application.load 'lib/sidekiq'
|
4
|
+
|
5
|
+
module Orders
|
6
|
+
class CompleteWorker
|
7
|
+
include Sidekiq::Worker
|
8
|
+
|
9
|
+
sidekiq_options :queue => :orders
|
10
|
+
|
11
|
+
def perform(order_id)
|
12
|
+
order = Order.find(order_id)
|
13
|
+
|
14
|
+
response = RestClient.post "#{Terminal.config.host}/terminal_orders/#{order.foreign_id}/complete",
|
15
|
+
:terminal => Terminal.keyword
|
16
|
+
|
17
|
+
Terminal.ping
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
Application.load 'lib/sidekiq'
|
2
|
+
|
3
|
+
module Orders
|
4
|
+
class DisableWorker
|
5
|
+
include Sidekiq::Worker
|
6
|
+
|
7
|
+
sidekiq_options :queue => :orders
|
8
|
+
|
9
|
+
def perform(order_id)
|
10
|
+
order = Order.find(order_id)
|
11
|
+
|
12
|
+
Terminal.disable
|
13
|
+
order.complete
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
Application.load 'lib/sidekiq'
|
2
|
+
|
3
|
+
module Orders
|
4
|
+
class EnableWorker
|
5
|
+
include Sidekiq::Worker
|
6
|
+
|
7
|
+
sidekiq_options :queue => :orders
|
8
|
+
|
9
|
+
def perform(order_id)
|
10
|
+
order = Order.find(order_id)
|
11
|
+
|
12
|
+
Terminal.enable
|
13
|
+
order.complete
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
Application.load 'lib/sidekiq'
|
2
|
+
|
3
|
+
module Orders
|
4
|
+
class RebootWorker
|
5
|
+
include Sidekiq::Worker
|
6
|
+
|
7
|
+
sidekiq_options :queue => :orders
|
8
|
+
|
9
|
+
def perform(order_id)
|
10
|
+
StartupWorker.perform_async self.class.name, :finish, [order_id]
|
11
|
+
Terminal.reboot
|
12
|
+
end
|
13
|
+
|
14
|
+
def self.finish(order_id)
|
15
|
+
Order.find(order_id).complete
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
Application.load 'lib/sidekiq'
|
2
|
+
|
3
|
+
module Orders
|
4
|
+
class ReloadWorker
|
5
|
+
include Sidekiq::Worker
|
6
|
+
|
7
|
+
sidekiq_options :queue => :orders
|
8
|
+
|
9
|
+
def perform(order_id)
|
10
|
+
StartupWorker.perform_async self.class.name, :finish, [order_id]
|
11
|
+
Terminal.reload
|
12
|
+
end
|
13
|
+
|
14
|
+
def self.finish(order_id)
|
15
|
+
Order.find(order_id).complete
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,108 @@
|
|
1
|
+
require 'pathname'
|
2
|
+
require 'rubygems'
|
3
|
+
require 'fileutils'
|
4
|
+
|
5
|
+
Application.load 'lib/sidekiq'
|
6
|
+
|
7
|
+
module Orders
|
8
|
+
class UpgradeWorker
|
9
|
+
include Sidekiq::Worker
|
10
|
+
|
11
|
+
sidekiq_options :queue => :orders
|
12
|
+
|
13
|
+
def perform(order_id)
|
14
|
+
order = Order.find(order_id)
|
15
|
+
|
16
|
+
@order_id = order_id
|
17
|
+
@build_version = Gem::Version.new order.args[1]
|
18
|
+
@build_id = order.args[0]
|
19
|
+
@base_url = URI.parse(order.args[3]).scheme.nil? ? "#{Terminal.config.host}#{order.args[3]}"
|
20
|
+
: order.args[3]
|
21
|
+
|
22
|
+
@releases_pathname = Terminal.smartguard.releases_path
|
23
|
+
@build_pathname = @releases_pathname.join @build_version.to_s
|
24
|
+
|
25
|
+
self.sync!
|
26
|
+
Terminal.smartguard.switch_release @build_version.to_s.to_sym do
|
27
|
+
order.complete
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
def files!
|
32
|
+
FileUtils.mkdir_p @releases_pathname
|
33
|
+
|
34
|
+
nearest_less_release = Dir.glob(@releases_pathname.join('*.*')).select do |v|
|
35
|
+
Gem::Version.new(File.basename(v)) < @build_version
|
36
|
+
end.max
|
37
|
+
|
38
|
+
if !File.directory?(@build_pathname)
|
39
|
+
if nearest_less_release.blank?
|
40
|
+
FileUtils.mkdir_p @build_pathname
|
41
|
+
else
|
42
|
+
FileUtils.cp_r nearest_less_release, @build_pathname
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
remotes = JSON.parse(RestClient.get "#{Terminal.config.host}/terminal_builds/#{@build_id}/hashes")
|
47
|
+
locals = Dir[File.join(@build_pathname, '**/**')].select{|x| File.file?(x)}.map{|x|
|
48
|
+
Pathname.new(x).relative_path_from(@build_pathname).to_s
|
49
|
+
}
|
50
|
+
|
51
|
+
download = {}
|
52
|
+
remove = []
|
53
|
+
|
54
|
+
remotes.each do |remote, data|
|
55
|
+
local = @build_pathname.join(remote)
|
56
|
+
|
57
|
+
if !File.file?(local) || Digest::MD5.file(local).hexdigest != data[0]
|
58
|
+
download[remote] = data[1]
|
59
|
+
end
|
60
|
+
end
|
61
|
+
|
62
|
+
locals.each do |local, hash|
|
63
|
+
remove << local if remotes[local].blank?
|
64
|
+
end
|
65
|
+
|
66
|
+
{:download => download, :remove => remove}
|
67
|
+
end
|
68
|
+
|
69
|
+
def sync!
|
70
|
+
diff = files!
|
71
|
+
|
72
|
+
total_transfer_size = diff[:download].values.inject(0){|sum,x|(sum+=x) unless x.nil?; sum }.to_f
|
73
|
+
|
74
|
+
diff[:download].each do |key, value|
|
75
|
+
uri = URI.parse(URI.encode("#{@base_url}/#{key}"))
|
76
|
+
path = @build_pathname.join key
|
77
|
+
FileUtils.mkdir_p File.dirname(path)
|
78
|
+
|
79
|
+
File.open(path, "wb") do |f|
|
80
|
+
Net::HTTP.start(uri.host, uri.port) do |http|
|
81
|
+
http.request_get(uri.path) do |resp|
|
82
|
+
resp.read_body do |segment|
|
83
|
+
f.write(segment)
|
84
|
+
end
|
85
|
+
end
|
86
|
+
end
|
87
|
+
end
|
88
|
+
|
89
|
+
diff[:download][key] = 0
|
90
|
+
|
91
|
+
delta_transfer_size = diff[:download].values.inject(0){|sum,x| (sum+=x) unless x.nil?; sum}.to_f
|
92
|
+
|
93
|
+
current_percentage = (100.0 - (delta_transfer_size / total_transfer_size * 100.0)).round(2)
|
94
|
+
if current_percentage > (@percentage ||= 0) + 5 || current_percentage == 100
|
95
|
+
@percentage = current_percentage
|
96
|
+
AcknowledgeWorker.perform_async(@order_id, nil, @percentage)
|
97
|
+
end
|
98
|
+
|
99
|
+
end
|
100
|
+
|
101
|
+
diff[:remove].each do |file|
|
102
|
+
fullpath = @build_pathname.join file
|
103
|
+
File.delete(fullpath) if File.exist?(fullpath)
|
104
|
+
end
|
105
|
+
end
|
106
|
+
|
107
|
+
end
|
108
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
require 'rest-client'
|
2
|
+
|
3
|
+
Application.load 'lib/sidekiq'
|
4
|
+
|
5
|
+
module Payments
|
6
|
+
class CheckWorker
|
7
|
+
include Sidekiq::Worker
|
8
|
+
|
9
|
+
sidekiq_options :queue => :payments
|
10
|
+
|
11
|
+
def perform(payment_id)
|
12
|
+
payment = Payment.find(payment_id)
|
13
|
+
response = RestClient.post "#{Terminal.config.host}/payments",
|
14
|
+
:provider => payment.provider.keyword,
|
15
|
+
:terminal => Terminal.config.keyword,
|
16
|
+
:payment => {
|
17
|
+
:account => payment.account,
|
18
|
+
:fields => payment.fields,
|
19
|
+
:session_id => payment.id
|
20
|
+
}
|
21
|
+
|
22
|
+
answer = JSON.parse(response.to_s, :symbolize_names => true)
|
23
|
+
|
24
|
+
unless answer[:id].nil?
|
25
|
+
payment.update_attributes :foreign_id => answer[:id],
|
26
|
+
:limit => answer[:limits].sort_by(&:weight).last,
|
27
|
+
:commissions => (answer[:commissions].empty? ? nil : answer[:commissions]),
|
28
|
+
:receipt_template => answer[:receipt_template],
|
29
|
+
:checked => true
|
30
|
+
end
|
31
|
+
rescue => e
|
32
|
+
Payment.find(payment_id).update_attributes :error => true
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
Application.load 'lib/sidekiq'
|
2
|
+
|
3
|
+
module Payments
|
4
|
+
class CollectWorker
|
5
|
+
include Sidekiq::Worker
|
6
|
+
|
7
|
+
sidekiq_options :queue => :payments
|
8
|
+
|
9
|
+
def perform(collection_id)
|
10
|
+
collection = Collection.find(collection_id)
|
11
|
+
|
12
|
+
response = RestClient.post "#{Terminal.config.host}/collections",
|
13
|
+
:terminal => Terminal.config.keyword,
|
14
|
+
:collection => {
|
15
|
+
:banknotes => collection.banknotes,
|
16
|
+
:collected_at => collection.created_at,
|
17
|
+
:session_ids => collection.payment_ids
|
18
|
+
}
|
19
|
+
|
20
|
+
collection.update_attribute(:reported_at, DateTime.now)
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
require 'rest-client'
|
2
|
+
|
3
|
+
Application.load 'lib/sidekiq'
|
4
|
+
|
5
|
+
module Payments
|
6
|
+
class PayWorker
|
7
|
+
include Sidekiq::Worker
|
8
|
+
|
9
|
+
sidekiq_options :queue => :payments
|
10
|
+
|
11
|
+
def perform(payment_id)
|
12
|
+
payment = Payment.find(payment_id)
|
13
|
+
response = RestClient.post "#{Terminal.config.host}/payments/#{payment.foreign_id}/pay",
|
14
|
+
:provider => payment.provider.keyword,
|
15
|
+
:terminal => Terminal.config.keyword,
|
16
|
+
:payment => { :paid_amount => payment.paid_amount }
|
17
|
+
Sidekiq::Logging.logger.debug "Pay response: #{response.to_s}"
|
18
|
+
payment.update_attributes(:processed => true) if response
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,180 @@
|
|
1
|
+
require 'rest-client'
|
2
|
+
|
3
|
+
Application.load 'lib/sidekiq'
|
4
|
+
|
5
|
+
class PingWorker
|
6
|
+
include Sidekiq::Worker
|
7
|
+
|
8
|
+
sidekiq_options :retry => false, :queue => :pings
|
9
|
+
|
10
|
+
SEMAPHORE = ConnectionPool.new(:size => 1, :timeout => 5) { true }
|
11
|
+
|
12
|
+
def perform
|
13
|
+
begin
|
14
|
+
SEMAPHORE.with do |glory|
|
15
|
+
condition = Terminal.condition
|
16
|
+
|
17
|
+
Sidekiq::Logging.logger.info "Requesting with updated_at: #{Terminal.providers_updated_at}"
|
18
|
+
|
19
|
+
begin
|
20
|
+
response = RestClient::Request.execute(
|
21
|
+
:method => :post,
|
22
|
+
:url => "#{Terminal.config.host}/terminal_pings",
|
23
|
+
:timeout => 40,
|
24
|
+
:open_timeout => 60,
|
25
|
+
:payload => {
|
26
|
+
:terminal => Terminal.keyword,
|
27
|
+
:terminal_ping => condition
|
28
|
+
}
|
29
|
+
)
|
30
|
+
rescue Exception => e
|
31
|
+
Sidekiq::Logging.logger.warn e.to_s
|
32
|
+
return
|
33
|
+
end
|
34
|
+
|
35
|
+
begin
|
36
|
+
response = JSON.parse(response.to_s, :symbolize_names => true)
|
37
|
+
rescue Exception => e
|
38
|
+
Sidekiq::Logging.logger.warn "Unable to parse JSON: #{e.to_s}"
|
39
|
+
return
|
40
|
+
end
|
41
|
+
|
42
|
+
unless Terminal.support_phone.value == response[:support_phone]
|
43
|
+
Terminal.support_phone = response[:support_phone]
|
44
|
+
Terminal.modified_at = DateTime.now
|
45
|
+
end
|
46
|
+
|
47
|
+
Sidekiq::Logging.logger.info "Response: #{response.inspect}"
|
48
|
+
|
49
|
+
#
|
50
|
+
# ORDERS
|
51
|
+
#
|
52
|
+
response[:orders].each do |order|
|
53
|
+
next unless Order.find_by_foreign_id(order[:id]).blank?
|
54
|
+
|
55
|
+
order[:foreign_id] = order.delete(:id)
|
56
|
+
order = Order.create!(order)
|
57
|
+
|
58
|
+
order.acknowledge
|
59
|
+
order.perform
|
60
|
+
end
|
61
|
+
|
62
|
+
#
|
63
|
+
# PROVIDERS
|
64
|
+
#
|
65
|
+
unless response[:providers].blank?
|
66
|
+
syncs = []
|
67
|
+
|
68
|
+
Provider.transaction do
|
69
|
+
#
|
70
|
+
# GROUPS
|
71
|
+
#
|
72
|
+
unless response[:providers][:groups].nil?
|
73
|
+
remote = response[:providers][:groups]
|
74
|
+
remote_ids = response[:providers][:groups].map{|x| x[:id]}
|
75
|
+
local = Group.all
|
76
|
+
|
77
|
+
local.select{|x| !remote_ids.include?(x.id)}.each do |x|
|
78
|
+
Sidekiq::Logging.logger.info "Group removal: ##{x.id}, #{x.title}"
|
79
|
+
x.destroy
|
80
|
+
end
|
81
|
+
|
82
|
+
remote.each do |r|
|
83
|
+
entry = local.find{|x| x.id == r[:id]}
|
84
|
+
entry ||= Group.new :foreign_id => r[:id]
|
85
|
+
|
86
|
+
entry.title = r[:title]
|
87
|
+
entry.priority = r[:priority]
|
88
|
+
entry.group_id = r[:parent_id]
|
89
|
+
|
90
|
+
Sidekiq::Logging.logger.info "Group replace: #{entry.title}"
|
91
|
+
|
92
|
+
entry.save!
|
93
|
+
|
94
|
+
unless r[:icon].blank?
|
95
|
+
syncs << ['Group', entry.id, r[:icon]]
|
96
|
+
end
|
97
|
+
end
|
98
|
+
end
|
99
|
+
|
100
|
+
#
|
101
|
+
# PROVIDERS REMOVAL
|
102
|
+
#
|
103
|
+
unless response[:providers][:remove].blank?
|
104
|
+
Sidekiq::Logging.logger.info "Providers removal: #{response[:providers][:remove]}"
|
105
|
+
Provider.where(:foreign_id => response[:providers][:remove]).destroy_all
|
106
|
+
end
|
107
|
+
|
108
|
+
#
|
109
|
+
# PROVIDERS UPDATES
|
110
|
+
#
|
111
|
+
unless response[:providers][:updated_at].blank?
|
112
|
+
response[:providers][:update].each do |provider|
|
113
|
+
local = Provider.find_or_initialize_by_foreign_id(provider[:id])
|
114
|
+
|
115
|
+
attributes = {
|
116
|
+
:title => provider[:title],
|
117
|
+
:keyword => provider[:keyword],
|
118
|
+
:priority => provider[:priority],
|
119
|
+
:fields => provider[:fields],
|
120
|
+
:group_id => provider[:group_id],
|
121
|
+
:requires_print => provider[:requires_print]
|
122
|
+
}
|
123
|
+
|
124
|
+
if provider[:icon].blank?
|
125
|
+
attributes[:icon] = nil
|
126
|
+
end
|
127
|
+
|
128
|
+
local.assign_attributes attributes
|
129
|
+
|
130
|
+
Sidekiq::Logging.logger.info "Provider replace: #{local.keyword}"
|
131
|
+
|
132
|
+
local.save!
|
133
|
+
|
134
|
+
unless provider[:icon].blank?
|
135
|
+
syncs << ['Provider', local.id, provider[:icon]]
|
136
|
+
end
|
137
|
+
end
|
138
|
+
end
|
139
|
+
|
140
|
+
#
|
141
|
+
# PROMOTIONS
|
142
|
+
#
|
143
|
+
unless response[:providers][:promotions].nil?
|
144
|
+
providers = Provider.to_hash(:foreign_id, response[:providers][:promotions], :invert => true)
|
145
|
+
remote = response[:providers][:promotions].map{|x| providers[x]}.compact
|
146
|
+
local = Promotion.all
|
147
|
+
|
148
|
+
local.select{|x| !remote.include?(x.provider_id)}.each do |x|
|
149
|
+
Sidekiq::Logging.logger.info "Promotion removal: #{x.provider_id}"
|
150
|
+
x.destroy
|
151
|
+
end
|
152
|
+
|
153
|
+
remote.each_with_index do |r, i|
|
154
|
+
entry = local.find{|x| x.provider_id == r}
|
155
|
+
entry ||= Promotion.new :provider_id => r
|
156
|
+
|
157
|
+
Sidekiq::Logging.logger.info "Promotion replace: #{r}"
|
158
|
+
|
159
|
+
entry.priority = i
|
160
|
+
entry.save!
|
161
|
+
end
|
162
|
+
end
|
163
|
+
end
|
164
|
+
|
165
|
+
unless response[:providers][:updated_at].blank?
|
166
|
+
Terminal.providers_updated_at = response[:providers][:updated_at]
|
167
|
+
end
|
168
|
+
|
169
|
+
Sidekiq::Logging.logger.info "Icons to sync: #{syncs}"
|
170
|
+
|
171
|
+
syncs.each do |args|
|
172
|
+
Sync::IconsWorker.perform_async *args
|
173
|
+
end
|
174
|
+
end
|
175
|
+
end
|
176
|
+
rescue Timeout::Error => e
|
177
|
+
Sidekiq::Logging.logger.warn "Semaphore timeout. #{e.to_s}"
|
178
|
+
end
|
179
|
+
end
|
180
|
+
end
|