sinatra-hexacta 0.0.2 → 0.1.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.
Files changed (46) hide show
  1. checksums.yaml +4 -4
  2. data/lib/sinatra/extensions/antiquity.rb +34 -0
  3. data/lib/sinatra/extensions/date.rb +49 -0
  4. data/lib/sinatra/extensions/init.rb +4 -0
  5. data/lib/sinatra/extensions/notification.rb +41 -0
  6. data/lib/sinatra/handlers/errors.rb +10 -3
  7. data/lib/sinatra/handlers/init.rb +3 -1
  8. data/lib/sinatra/handlers/notifications.rb +17 -28
  9. data/lib/sinatra/handlers/params.rb +26 -0
  10. data/lib/sinatra/handlers/reports.rb +28 -1
  11. data/lib/sinatra/helpers/alerts.rb +27 -0
  12. data/lib/sinatra/helpers/cas.rb +92 -0
  13. data/lib/sinatra/helpers/charts.rb +20 -4
  14. data/lib/sinatra/helpers/init.rb +4 -0
  15. data/lib/sinatra/helpers/inputs.rb +2 -2
  16. data/lib/sinatra/helpers/libraries.rb +2 -2
  17. data/lib/sinatra/helpers/mailer.rb +74 -0
  18. data/lib/sinatra/helpers/reports.rb +27 -0
  19. data/lib/sinatra/helpers/schedule.rb +68 -0
  20. data/lib/sinatra/helpers/subscriptions.rb +1 -1
  21. data/lib/sinatra/hexacta.rb +13 -5
  22. data/lib/sinatra/public/css/app.min.1.css +130 -12
  23. data/lib/sinatra/public/js/app.js +49 -42
  24. data/lib/sinatra/public/vendors/chartist/chartist-plugin-legend.js +237 -0
  25. data/lib/sinatra/views/alerts/empty.slim +7 -0
  26. data/lib/sinatra/views/alerts/error.slim +7 -0
  27. data/lib/sinatra/views/alerts/info.slim +7 -0
  28. data/lib/sinatra/views/alerts/warning.slim +7 -0
  29. data/lib/sinatra/views/charts/bar.slim +56 -0
  30. data/lib/sinatra/views/charts/gauge.slim +30 -0
  31. data/lib/sinatra/views/charts/{simple_line.slim → line.slim} +7 -8
  32. data/lib/sinatra/views/charts/pie.slim +34 -0
  33. data/lib/sinatra/views/charts/stacked_bar.slim +36 -0
  34. data/lib/sinatra/views/inputs/multiple_select.slim +4 -0
  35. data/lib/sinatra/views/inputs/select.slim +3 -0
  36. data/lib/sinatra/views/libraries/include_js_after.slim +0 -24
  37. data/lib/sinatra/views/libraries/include_js_before.slim +1 -0
  38. data/lib/sinatra/views/notifications.slim +37 -31
  39. data/lib/sinatra/views/notifications/form.slim +4 -4
  40. data/lib/sinatra/views/notifications/new.slim +4 -4
  41. data/lib/sinatra/views/notifications/widget.slim +9 -5
  42. data/lib/sinatra/views/reports/pick_date.slim +14 -0
  43. data/lib/sinatra/views/reports/pick_dates.slim +16 -0
  44. data/lib/sinatra/views/reports/pick_month.slim +14 -0
  45. data/lib/sinatra/views/reports/pick_year.slim +14 -0
  46. metadata +26 -3
@@ -1,15 +1,31 @@
1
1
  # encoding: utf-8
2
2
  module Sinatra
3
- module ChartsHandler
3
+ module ChartsHelper
4
4
  extend Hexacta
5
5
 
6
- def simple_line(option_hash)
7
- slim "#{Hexacta::GEM_FILE_DIR}/charts/simple_line".to_sym, locals: option_hash
6
+ def line_chart(option_hash)
7
+ slim "#{Hexacta::GEM_FILE_DIR}/charts/line".to_sym, locals: option_hash
8
+ end
9
+
10
+ def bar_chart(option_hash)
11
+ slim "#{Hexacta::GEM_FILE_DIR}/charts/bar".to_sym, locals: option_hash
12
+ end
13
+
14
+ def pie_chart(option_hash)
15
+ slim "#{Hexacta::GEM_FILE_DIR}/charts/pie".to_sym, locals: option_hash
16
+ end
17
+
18
+ def gauge_chart(option_hash)
19
+ slim "#{Hexacta::GEM_FILE_DIR}/charts/gauge".to_sym, locals: option_hash
20
+ end
21
+
22
+ def stacked_bar_chart(option_hash)
23
+ slim "#{Hexacta::GEM_FILE_DIR}/charts/stacked_bar".to_sym, locals: option_hash
8
24
  end
9
25
 
10
26
  setup_dir("/app/views/#{Hexacta::GEM_FILE_DIR}/charts")
11
27
  symlink_all("/lib/sinatra/views/charts","/app/views/#{Hexacta::GEM_FILE_DIR}/charts")
12
28
  end
13
29
 
14
- helpers ChartsHandler
30
+ helpers ChartsHelper
15
31
  end
@@ -3,3 +3,7 @@ require_relative 'libraries'
3
3
  require_relative 'inputs'
4
4
  require_relative 'charts'
5
5
  require_relative 'subscriptions'
6
+ require_relative 'cas'
7
+ require_relative 'schedule'
8
+ require_relative 'alerts'
9
+ require_relative 'reports'
@@ -1,6 +1,6 @@
1
1
  # encoding: utf-8
2
2
  module Sinatra
3
- module InputHandler
3
+ module InputHelper
4
4
  extend Hexacta
5
5
 
6
6
  def date_input(option_hash)
@@ -43,5 +43,5 @@ module Sinatra
43
43
  symlink_all("/lib/sinatra/views/inputs","/app/views/#{Hexacta::GEM_FILE_DIR}/inputs")
44
44
  end
45
45
 
46
- helpers InputHandler
46
+ helpers InputHelper
47
47
  end
@@ -1,6 +1,6 @@
1
1
  # encoding: utf-8
2
2
  module Sinatra
3
- module LibrariesHandler
3
+ module LibrariesHelper
4
4
  extend Hexacta
5
5
 
6
6
  def include_css
@@ -21,5 +21,5 @@ module Sinatra
21
21
  symlink_all("/lib/sinatra/views/libraries","/app/views/#{Hexacta::GEM_FILE_DIR}/libraries")
22
22
  end
23
23
 
24
- helpers LibrariesHandler
24
+ helpers LibrariesHelper
25
25
  end
@@ -0,0 +1,74 @@
1
+ # encoding: utf-8
2
+ require 'sucker_punch'
3
+
4
+ module Sinatra
5
+ module MailHelper
6
+
7
+ attr_reader :access_token, :expire, :refresh_token
8
+
9
+ def _do_connect(uri, form={},token=nil)
10
+ url = URI.parse("#{uri}")
11
+ http = Net::HTTP.new(url.host, url.port)
12
+ http.read_timeout = 1000
13
+ http.use_ssl = (url.scheme == 'https')
14
+ http.verify_mode = OpenSSL::SSL::VERIFY_NONE
15
+ header = { 'Content-Type' => 'application/x-www-form-urlencoded' }
16
+ header["Authorization"] = "Bearer #{token}" unless token.nil?
17
+ request = Net::HTTP::Post.new(url, header)
18
+ request.form_data = form
19
+ http.start {|http| http.request(request) }
20
+ end
21
+
22
+ def _authorize_mail
23
+ params = [ [ "grant_type", "password" ], [ "client_id", "MailApp" ], [ "client_secret", "MailAppPRD2018!" ] ]
24
+ response = _do_connect("https://comunicacion.hexacta.com:4443/apptoken",params)
25
+ if( response.is_a?( Net::HTTPSuccess ) )
26
+ token = JSON.parse(response.body)
27
+ @access_token = token["access_token"]
28
+ @refresh_token = token["refresh_token"]
29
+ @expire = DateTime.parse(token[".expires"])
30
+ else
31
+ p "Didn't succeed :("
32
+ end
33
+ end
34
+
35
+ def _build_map_values(mail_values)
36
+ values = []
37
+ for key in mail_values.keys
38
+ index = mail_values.keys.index(key)
39
+ values << ["MailValues[#{index}].Key", key]
40
+ values << ["MailValues[#{index}].Value", mail_values[key]]
41
+ end
42
+ values
43
+ end
44
+
45
+ def _build_to_map(to_map)
46
+ values = []
47
+ for key in to_map.keys
48
+ index = to_map.keys.index(key)
49
+ values << ["ResourcesRequest[#{index}].TypeGroup", to_map[key]]
50
+ values << ["ResourcesRequest[#{index}].Name", key]
51
+ end
52
+ values
53
+ end
54
+
55
+ def _expired?
56
+ expire.nil? || DateTime.now < expire
57
+ end
58
+
59
+ def send_mail(template,subject,mail_values={},to_map)
60
+ if _expired?
61
+ _authorize_mail
62
+ end
63
+ params = [ [ "ApplicationCode", 1 ], [ "Name", template ], [ "Subject", subject ], [ "EmailAddress", "apps@hexacta.com" ] ]
64
+ params = params + _build_map_values(mail_values) + _build_to_map(to_map)
65
+ response = do_connect("https://comunicacion.hexacta.com:4444/api/app/TemplateNotification/SendMail",params,@access_token)
66
+ if( !response.is_a?( Net::HTTPSuccess ) )
67
+ p "Didn't succeed :("
68
+ end
69
+ end
70
+
71
+ end
72
+
73
+ helpers MailHelper
74
+ end
@@ -0,0 +1,27 @@
1
+ # encoding: utf-8
2
+ module Sinatra
3
+ module ReportHelper
4
+ extend Hexacta
5
+
6
+ def pick_date_input(option_hash)
7
+ slim "#{Hexacta::GEM_FILE_DIR}/reports/pick_date".to_sym, locals: option_hash
8
+ end
9
+
10
+ def pick_dates_input(option_hash)
11
+ slim "#{Hexacta::GEM_FILE_DIR}/reports/pick_dates".to_sym, locals: option_hash
12
+ end
13
+
14
+ def pick_month_input(option_hash)
15
+ slim "#{Hexacta::GEM_FILE_DIR}/reports/pick_month".to_sym, locals: option_hash
16
+ end
17
+
18
+ def pick_year_input(option_hash)
19
+ slim "#{Hexacta::GEM_FILE_DIR}/reports/pick_year".to_sym, locals: option_hash
20
+ end
21
+
22
+ setup_dir("/app/views/#{Hexacta::GEM_FILE_DIR}/reports")
23
+ symlink_all("/lib/sinatra/views/reports","/app/views/#{Hexacta::GEM_FILE_DIR}/reports")
24
+ end
25
+
26
+ helpers ReportHelper
27
+ end
@@ -0,0 +1,68 @@
1
+ require 'timeout'
2
+ # encoding: utf-8
3
+ module Sinatra
4
+ module ScheduleHelper
5
+
6
+ @@scheduler = Rufus::Scheduler.new
7
+
8
+ def schedule_every(time)
9
+ @@scheduler.every time do
10
+ begin
11
+ file_path = "/tmp/schedule.lock";
12
+ f = File.open(file_path, "w+")
13
+ # if file was previosly locked then flock throw a exception
14
+ f.flock(File::LOCK_EX)
15
+ ten_minutes = 600
16
+ # if the process overcome ten minutes, the timeout api throw a exception
17
+ Timeout::timeout(ten_minutes) do
18
+
19
+ begin
20
+ yield
21
+ rescue StandardError => error
22
+ title = error.message.split(':')[0].gsub('#<','');
23
+ message = error.backtrace.join(',');
24
+ NotificationSender.send_error(nil,title,message)
25
+ end
26
+
27
+ end
28
+ ensure
29
+ unless f.nil?
30
+ f.flock(File::LOCK_UN)
31
+ f.close
32
+ end
33
+ end
34
+ end
35
+ end
36
+
37
+ def schedule_at(cron_expression)
38
+ @@scheduler.cron cron_expression do
39
+ begin
40
+ file_path = "/tmp/schedule.lock";
41
+ f = File.open(file_path, "w+")
42
+ # if file was previosly locked then flock throw a exception
43
+ f.flock(File::LOCK_EX)
44
+ ten_minutes = 600
45
+ # if the process overcome ten minutes, the timeout api throw a exception
46
+ Timeout::timeout(ten_minutes) do
47
+
48
+ begin
49
+ yield
50
+ rescue error
51
+ title = error.message.split(':')[0].gsub('#<','');
52
+ message = error.backtrace.join(',');
53
+ NotificationSender.send_error(nil,title,message)
54
+ end
55
+
56
+ end
57
+ ensure
58
+ unless f.nil?
59
+ f.flock(File::LOCK_UN)
60
+ f.close
61
+ end
62
+ end
63
+ end
64
+ end
65
+ end
66
+
67
+ register ScheduleHelper
68
+ end
@@ -3,7 +3,6 @@ module Sinatra
3
3
  module SubscriptionHelper
4
4
 
5
5
  def notify_to(user,creator,title,message,label,link=nil)
6
- #return if creator.id == user.id
7
6
  notification = Notification.find_or_create(:user_id => user.id,
8
7
  :creator_id => creator.id,
9
8
  :title => title,
@@ -26,6 +25,7 @@ module Sinatra
26
25
 
27
26
  def notify_error(creator,title,message)
28
27
  Subscription.where(:label => 'error').all.each do |subscription|
28
+ creator = subscription.user if creator.nil?
29
29
  notification = Notification.find(:user_id => subscription.user_id,
30
30
  :creator_id => creator.id,
31
31
  :title => title,
@@ -1,32 +1,40 @@
1
1
  # encoding: utf-8
2
2
  require 'sinatra/base'
3
3
  require 'fileutils'
4
+ require 'sucker_punch'
5
+ require 'rufus-scheduler'
4
6
 
5
7
  module Sinatra
8
+
6
9
  module Hexacta
7
10
  GEM_FILE_DIR = "sinatra-hexacta"
8
11
 
9
12
  def symlink(original_path, link_path)
10
- #p "Symlinking #{original_path} #{link_path}"
11
13
  File.symlink "#{Gem.loaded_specs["sinatra-hexacta"].gem_dir}#{original_path}", "#{link_path}" unless Gem.loaded_specs["sinatra-hexacta"].nil? || File.exist?("#{link_path}")
12
14
  end
13
15
 
14
16
  def symlink_all(original_path, link_path)
15
17
  Dir.foreach("#{Gem.loaded_specs["sinatra-hexacta"].gem_dir}#{original_path}") do |child|
16
18
  symlink("#{original_path}/#{child}","#{link_path}/#{child}") unless child == '.' || child == '..'
17
- end
19
+ end unless Gem.loaded_specs["sinatra-hexacta"].nil?
18
20
  end
19
21
 
20
22
  def setup_dir(path)
21
- FileUtils.mkdir_p path unless Dir.exist? path
23
+ unless Gem.loaded_specs["sinatra-hexacta"].nil?
24
+ FileUtils.remove_dir path if Dir.exist? path
25
+ FileUtils.mkdir_p path
26
+ end
22
27
  end
23
28
 
24
29
  def copy_dir_structure(original_path, destination_path)
25
- FileUtils.remove_dir destination_path if Dir.exist? destination_path
26
- FileUtils.copy_entry("#{Gem.loaded_specs["sinatra-hexacta"].gem_dir}#{original_path}", destination_path)
30
+ unless Gem.loaded_specs["sinatra-hexacta"].nil?
31
+ FileUtils.remove_dir destination_path if Dir.exist? destination_path
32
+ FileUtils.copy_entry("#{Gem.loaded_specs["sinatra-hexacta"].gem_dir}#{original_path}", destination_path)
33
+ end
27
34
  end
28
35
  end
29
36
  end
30
37
 
31
38
  require_relative 'helpers/init'
32
39
  require_relative 'handlers/init'
40
+ require_relative 'extensions/init'
@@ -10550,10 +10550,6 @@ h6 small,
10550
10550
  left: 0;
10551
10551
  top: 0;
10552
10552
  padding: 0 11px;
10553
- transition: all .5s ease-out;
10554
- -moz-transition: all .5s ease-out;
10555
- -o-transition: all .5s ease-out;
10556
- -webkit-transition: all .5s ease-out;
10557
10553
  }
10558
10554
 
10559
10555
  #header:not(.sidebar-toggled).header-up {
@@ -10571,14 +10567,6 @@ h6 small,
10571
10567
  left: 0;
10572
10568
  width: 100%;
10573
10569
  height: 70px;
10574
- background: #fff;
10575
- -webkit-transition: all;
10576
- -o-transition: all;
10577
- transition: all;
10578
- -webkit-transition-duration: 300ms;
10579
- transition-duration: 300ms;
10580
- opacity: 0;
10581
- filter: alpha(opacity=0);
10582
10570
  z-index: 10;
10583
10571
  }
10584
10572
 
@@ -11925,6 +11913,10 @@ a.lv-footer:hover {
11925
11913
  width: 100%;
11926
11914
  }
11927
11915
 
11916
+ .chart-table table {
11917
+ font-size: 11px;
11918
+ }
11919
+
11928
11920
  /*
11929
11921
  * Sparkline Tooltip
11930
11922
  */
@@ -16229,3 +16221,129 @@ body.login-content:before {
16229
16221
  .error .chosen-container-active .chosen-single:after {
16230
16222
  background: #f6675d !Important;
16231
16223
  }
16224
+
16225
+ svg.ct-chart-bar, svg.ct-chart-line{
16226
+ overflow: visible;
16227
+ }
16228
+
16229
+ .ct-label.ct-label.ct-horizontal.ct-end {
16230
+ position: relative;
16231
+ justify-content: flex-end;
16232
+ text-align: right;
16233
+ transform-origin: 100% 0;
16234
+ transform: translate(-100%) rotate(-45deg);
16235
+ white-space:nowrap;
16236
+ }
16237
+
16238
+
16239
+ .ct-legend {
16240
+ position: relative;
16241
+ z-index: 10;
16242
+ list-style: none;
16243
+ text-align: left;
16244
+ cursor: pointer;
16245
+ }
16246
+
16247
+ .bar-chart .ct-legend, .line-chart .ct-legend {
16248
+ text-align: center;
16249
+ }
16250
+
16251
+ .ct-legend li {
16252
+ position: relative;
16253
+ padding-left: 23px;
16254
+ margin-bottom: 3px;
16255
+ }
16256
+
16257
+ .bar-chart .ct-legend li, .line-chart .ct-legend li{
16258
+ display: inline-block;
16259
+ margin: 10px;
16260
+ }
16261
+
16262
+ .ct-legend li:before {
16263
+ width: 12px;
16264
+ height: 12px;
16265
+ position: absolute;
16266
+ left: 0;
16267
+ content: '';
16268
+ border: 3px solid transparent;
16269
+ border-radius: 2px;
16270
+ }
16271
+
16272
+ .ct-legend li.inactive:before {
16273
+ background: transparent;
16274
+ }
16275
+
16276
+ .ct-legend .ct-series-0:before {
16277
+ background-color: #d70206;
16278
+ border-color: #d70206;
16279
+ }
16280
+
16281
+ .ct-legend .ct-series-1:before {
16282
+ background-color: #f05b4f;
16283
+ border-color: #f05b4f;
16284
+ }
16285
+
16286
+ .ct-legend .ct-series-2:before {
16287
+ background-color: #f4c63d;
16288
+ border-color: #f4c63d;
16289
+ }
16290
+
16291
+ .ct-legend .ct-series-3:before {
16292
+ background-color: #d17905;
16293
+ border-color: #d17905;
16294
+ }
16295
+
16296
+ .ct-legend .ct-series-4:before {
16297
+ background-color: #453d3f;
16298
+ border-color: #453d3f;
16299
+ }
16300
+
16301
+ .ct-legend .ct-series-5:before {
16302
+ background-color: #59922b;
16303
+ border-color: #59922b;
16304
+ }
16305
+
16306
+ .ct-legend .ct-series-6:before {
16307
+ background-color: #0544d3;
16308
+ border-color: #0544d3;
16309
+ }
16310
+
16311
+ .ct-legend .ct-series-7:before {
16312
+ background-color: #6b0392;
16313
+ border-color: #6b0392;
16314
+ }
16315
+
16316
+ .ct-legend .ct-series-8:before {
16317
+ background-color: #f05b4f;
16318
+ border-color: #f05b4f;
16319
+ }
16320
+
16321
+ .ct-legend .ct-series-9:before {
16322
+ background-color: #dda458;
16323
+ border-color: #dda458;
16324
+ }
16325
+
16326
+ .ct-legend .ct-series-10:before {
16327
+ background-color: #eacf7d;
16328
+ border-color: #eacf7d;
16329
+ }
16330
+
16331
+ .ct-legend .ct-series-11:before {
16332
+ background-color: #86797d;
16333
+ border-color: #86797d;
16334
+ }
16335
+
16336
+ .ct-legend .ct-series-12:before {
16337
+ background-color: #b2c326;
16338
+ border-color: #b2c326;
16339
+ }
16340
+
16341
+ .ct-legend .ct-series-13:before {
16342
+ background-color: #6188e2;
16343
+ border-color: #6188e2;
16344
+ }
16345
+
16346
+ .ct-legend .ct-series-14:before {
16347
+ background-color: #a748ca;
16348
+ border-color: #a748ca;
16349
+ }