avo 1.2.2 → 1.2.6

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of avo might be problematic. Click here for more details.

Files changed (35) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile.lock +1 -1
  3. data/app/controllers/avo/application_controller.rb +19 -0
  4. data/app/controllers/avo/home_controller.rb +3 -1
  5. data/app/packs/stylesheets/components/code.css +5 -0
  6. data/app/views/avo/home/_actions.html.erb +5 -5
  7. data/app/views/avo/home/_docs.html.erb +1 -1
  8. data/app/views/avo/home/_filters.html.erb +4 -4
  9. data/app/views/avo/home/_resources.html.erb +15 -2
  10. data/app/views/avo/home/index.html.erb +1 -1
  11. data/app/views/avo/partials/_custom_tools_alert.html.erb +6 -0
  12. data/app/views/avo/sidebar/_license_warning.html.erb +3 -7
  13. data/app/views/avo/sidebar/_sidebar.html.erb +2 -1
  14. data/app/views/layouts/avo/application.html.erb +6 -2
  15. data/lib/avo.rb +4 -0
  16. data/lib/avo/app.rb +7 -3
  17. data/lib/avo/configuration.rb +6 -0
  18. data/lib/avo/licensing/h_q.rb +3 -3
  19. data/lib/avo/licensing/license.rb +2 -0
  20. data/lib/avo/licensing/pro_license.rb +2 -1
  21. data/lib/avo/version.rb +1 -1
  22. data/lib/generators/avo/templates/initializer/avo.tt +10 -1
  23. data/lib/generators/avo/tool_generator.rb +2 -2
  24. data/public/avo-packs/css/{application-13cc02fb.css → application-af3e670d.css} +23 -12
  25. data/public/avo-packs/css/application-af3e670d.css.br +0 -0
  26. data/public/avo-packs/css/application-af3e670d.css.gz +0 -0
  27. data/public/avo-packs/css/{application-13cc02fb.css.map → application-af3e670d.css.map} +1 -1
  28. data/public/avo-packs/css/application-af3e670d.css.map.br +0 -0
  29. data/public/avo-packs/css/application-af3e670d.css.map.gz +0 -0
  30. data/public/avo-packs/manifest.json +7 -7
  31. metadata +9 -8
  32. data/public/avo-packs/css/application-13cc02fb.css.br +0 -0
  33. data/public/avo-packs/css/application-13cc02fb.css.gz +0 -0
  34. data/public/avo-packs/css/application-13cc02fb.css.map.br +0 -0
  35. data/public/avo-packs/css/application-13cc02fb.css.map.gz +0 -0
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: a5cd3316f4906c09337ae6079468f6779b272ec800112cefa1db60a169acaddf
4
- data.tar.gz: 6238d803e939ed4471cf6b67fbcf2568bc74fddd6f125eb10575d15f2ee6c244
3
+ metadata.gz: 29978f5965b8f3a7d37592960629537572e297b6c247793893f12ef662135271
4
+ data.tar.gz: 9b178a096a42375b531170a1d522568d96134523e94298787b670502ef09c350
5
5
  SHA512:
6
- metadata.gz: 3e81e69fdb6f0094ccada08f1ca66c522fbf813b9dbc310de63a8c1ed64c9155d62e2dadee337b7ea937280755b157325e07ada2de94a88e219d4f29a8c58d66
7
- data.tar.gz: f82850865b3a6592364534c33b4766f808e9d869025ea57bbe8148625fd0399d46575046d86bcca9115a68f604c302628c39965ba7f36f55c9822f2b3bf41480
6
+ metadata.gz: 2f14e3a6cad2b57e494fe73088903ab6f92aa9521860e5f47b8fe8d07e69b54393e25a80adb4f995a941503e62a403dfec2b7579c8982dcf022931e5fdc1990c
7
+ data.tar.gz: 3f8fcfe855e2c260015d5ed3d74b0a26e8621da2f3c404caeaf948c03f43922cc3de59d291fa6fc6145aa0921ace48fcfea1e8105469b214ec2bd274686bd638
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- avo (1.2.2)
4
+ avo (1.2.6)
5
5
  active_link_to
6
6
  addressable
7
7
  breadcrumbs_on_rails
@@ -4,6 +4,7 @@ module Avo
4
4
  include Pagy::Backend
5
5
  protect_from_forgery with: :exception
6
6
  before_action :init_app
7
+ before_action :check_avo_license
7
8
  before_action :set_authorization
8
9
  before_action :_authenticate!
9
10
  before_action :set_container_classes
@@ -34,6 +35,24 @@ module Avo
34
35
  end
35
36
  end
36
37
 
38
+ def render(*args)
39
+ raise Avo::LicenseVerificationTemperedError, "License verification mechanism tempered with." unless method(:check_avo_license).source_location.first.match?(/.*\/app\/controllers\/avo\/application_controller\.rb/)
40
+
41
+ super(*args)
42
+ end
43
+
44
+ def check_avo_license
45
+ unless request.original_url.match?(/.*\/avo\/resources\/.*/)
46
+ if @license.invalid? || @license.lacks(:custom_tools)
47
+ if Rails.env.development?
48
+ @custom_tools_alert_visible = true
49
+ else
50
+ raise Avo::LicenseInvalidError, "Your license is invalid or doesn't support custom tools."
51
+ end
52
+ end
53
+ end
54
+ end
55
+
37
56
  def _current_user
38
57
  instance_eval(&Avo.configuration.current_user)
39
58
  end
@@ -5,7 +5,9 @@ module Avo
5
5
  def index
6
6
  @page_title = "Get started"
7
7
 
8
- unless Rails.env.development?
8
+ if Avo.configuration.home_path.present?
9
+ redirect_to Avo.configuration.home_path
10
+ elsif !Rails.env.development?
9
11
  redirect_to resources_path Avo::App.get_resources.min_by { |resource| resource.route_key }.model_class
10
12
  end
11
13
  end
@@ -9,3 +9,8 @@
9
9
  height: var(--height) !important;
10
10
  min-height: auto;
11
11
  }
12
+
13
+ /* overlay CodeMirror fullscreen & Preview on small screens */
14
+ .CodeMirror-fullscreen, .editor-preview-active-side {
15
+ z-index: 50;
16
+ }
@@ -1,16 +1,16 @@
1
1
  <div>
2
2
  <h3>Actions</h3>
3
3
 
4
- <div class="mt-2" data-controller="hidden-input">
4
+ <div class="mt-2">
5
5
  Avo actions allow you to perform specific tasks on one or more of your records. For example, you might want to mark a user as inactive and optionally send a message that may be customized by the person that wants to run the action.
6
6
 
7
- <strong class="cursor-pointer block mt-2" data-action="click->hidden-input#showContent">Generate action 👇</strong>
8
-
9
- <div class="mt-2 hidden" data-hidden-input-target="content">
7
+ <div class="mt-2">
10
8
  <code class="text-lg">Toggle published</code>
11
- <div>
9
+ <div class="mt-1">
12
10
  <code class="p-1 rounded bg-light-blue-500 text-white">bin/rails generate avo:action toggle_published</code>
13
11
  </div>
14
12
  </div>
13
+
14
+ <a href="https://docs.avohq.io/1.0/actions.html" target="_blank" title="Avo Actions documentation" class="text-bold cursor-pointer block mt-2">Actions in the docs 👉</a>
15
15
  </div>
16
16
  </div>
@@ -4,6 +4,6 @@
4
4
  <div class="mt-2">
5
5
  We take pride in our documentation. Please check it out to see what you can build with Avo
6
6
 
7
- <a href="https://docs.avohq.io" class="text-bold cursor-pointer block mt-2">Check out the docs 👉</a>
7
+ <a href="https://docs.avohq.io" target="_blank" title="Avo documentation" class="text-bold cursor-pointer block mt-2">Check out the docs 👉</a>
8
8
  </div>
9
9
  </div>
@@ -4,13 +4,13 @@
4
4
  <div class="mt-2" data-controller="hidden-input">
5
5
  Filters allow you to better scope the index queries for records you are looking for.
6
6
 
7
- <strong class="cursor-pointer block mt-2" data-action="click->hidden-input#showContent">Generate filter 👇</strong>
8
-
9
- <div class="mt-2 hidden" data-hidden-input-target="content">
7
+ <div class="mt-2">
10
8
  <code class="text-lg">Published filter</code>
11
- <div>
9
+ <div class="mt-1">
12
10
  <code class="p-1 rounded bg-light-blue-500 text-white">bin/rails generate avo:filter published_filter</code>
13
11
  </div>
14
12
  </div>
13
+
14
+ <a href="https://docs.avohq.io/1.0/filters.html" target="_blank" title="Avo Filters documentation" class="text-bold cursor-pointer block mt-2">Filters in the docs 👉</a>
15
15
  </div>
16
16
  </div>
@@ -1,5 +1,9 @@
1
1
  <%
2
- models = ApplicationRecord.descendants
2
+ models = begin
3
+ ApplicationRecord.descendants
4
+ rescue => exception
5
+ []
6
+ end
3
7
  %>
4
8
  <div>
5
9
  <h3>Resources</h3>
@@ -10,7 +14,7 @@
10
14
  <div class="mt-2" data-controller="hidden-input">
11
15
  It seems you already have <%= models.count %> <%= 'model'.pluralize models.count %> in your app. You can generate resources for each one with the following commands.
12
16
 
13
- <strong class="cursor-pointer block mt-2" data-action="click->hidden-input#showContent">Generate resources 👇</strong>
17
+ <strong class="cursor-pointer block mt-2" data-action="click->hidden-input#showContent">Generate resources 👇 (click to reveal)</strong>
14
18
 
15
19
  <div class="mt-2 hidden" data-hidden-input-target="content">
16
20
  <% models.each do |model| %>
@@ -22,7 +26,16 @@
22
26
  </div>
23
27
  </div>
24
28
  <% else %>
29
+ <div class="mt-2" data-controller="hidden-input">
30
+ You may generate a resource using the following command:
31
+ <br>
25
32
 
33
+ <code class="p-1 rounded bg-light-blue-500 text-white">bin/rails generate avo:resource post</code>
34
+ </div>
26
35
  <% end %>
36
+
37
+ <p>
38
+ <a href="https://docs.avohq.io/1.0/resources.html" target="_blank" title="Avo Resources documentation">Docs</a>
39
+ </p>
27
40
  </div>
28
41
 
@@ -27,7 +27,7 @@
27
27
  <li><span class="mr-2">👍</span> Grid view</li>
28
28
  <li><span class="mr-2">👍</span> Authorization</li>
29
29
  <li><span class="mr-2">👍</span> Localization</li>
30
- <li><span class="mr-2">⏳</span> Custom tools</li>
30
+ <li><span class="mr-2">👍</span> Custom tools</li>
31
31
  <li><span class="mr-2">⏳</span> Custom fields</li>
32
32
  <li><span class="mr-2">⏳</span> Search</li>
33
33
  <li><span class="mr-2">🕐</span> Dashboards</li>
@@ -0,0 +1,6 @@
1
+ <div class="w-full inset-auto bottom-0 z-50 mb-4 opacity-75 hover:opacity-100 transition-opacity duration-150">
2
+ <a href="https://avohq.io/pricing" target="_blank" class="rounded bg-green-700 text-white py-2 px-4 text-sm block items-center flex leading-tight">
3
+ <%= svg "exclamation", class: "h-6 inline mr-2 text-bold flex-shrink-0" %> Warning. Your license is invalid or doesn't support custom tools. This page will not be visible in a production environment.
4
+ </a>
5
+ </div>
6
+
@@ -1,12 +1,8 @@
1
1
  <div class="w-10/12 ml-1/12 inset-auto bottom-0 z-50 my-4 opacity-50 hover:opacity-100 transition-opacity duration-150 group">
2
- <a href="https://avohq.io/pricing" target="_blank" class="rounded bg-teal-700 text-white py-2 px-4 text-sm block group-hover:pt-4">
3
- <% if icon.present? %>
4
- <div class="h-6 inline mr-1 text-bold" :is="iconElement" v-if="icon">
5
- <%= title %>
6
- </div>
7
- <% end %>
2
+ <a href="https://avohq.io/pricing" target="_blank" class="rounded bg-green-700 text-white py-2 px-4 text-sm block group-hover:pt-4">
3
+ <%= svg 'exclamation', class: 'h-6 inline mr-1 text-bold' %> <%= title %>
8
4
  <div class="group-hover:block hidden py-2">
9
- <%= message %> <arrow-circle-right-icon class="h-6 inline float-right"></arrow-circle-right-icon>
5
+ <%= message %> <%= svg 'arrow-circle-right', class: "h-6 inline float-right" %>
10
6
  </div>
11
7
  </a>
12
8
  </div>
@@ -6,7 +6,8 @@
6
6
 
7
7
  <div class="flex-1 flex flex-col justify-between">
8
8
  <div class="tools py-4">
9
- <%= render Avo::NavigationLinkComponent.new label: 'Get started', path: '/avo', active: :exclusive if Rails.env.development? %>
9
+ <%= render Avo::NavigationLinkComponent.new label: 'Get started', path: Avo.configuration.root_path, active: :exclusive if Rails.env.development? && Avo.configuration.home_path.nil? %>
10
+
10
11
  <%= render Avo::NavigationHeadingComponent.new label: t('avo.resources') %>
11
12
 
12
13
  <div class="w-full">
@@ -30,8 +30,12 @@
30
30
  </div>
31
31
 
32
32
  <div class="content p-8 flex-1 flex flex-col justify-between items-stretch <%= @container_classes %>">
33
- <%= yield %>
34
- <%= render partial: "avo/partials/footer" %>
33
+ <%= render partial: "avo/partials/custom_tools_alert" if @custom_tools_alert_visible %>
34
+
35
+ <div class="flex flex-1 flex-col justify-between items-stretch">
36
+ <%= yield %>
37
+ <%= render partial: "avo/partials/footer" %>
38
+ </div>
35
39
  </div>
36
40
  </div>
37
41
  </div>
data/lib/avo.rb CHANGED
@@ -10,6 +10,10 @@ module Avo
10
10
  IN_DEVELOPMENT = ENV["AVO_IN_DEVELOPMENT"] == "1"
11
11
  PACKED = !IN_DEVELOPMENT
12
12
 
13
+ class LicenseVerificationTemperedError < StandardError; end
14
+
15
+ class LicenseInvalidError < StandardError; end
16
+
13
17
  class << self
14
18
  def webpacker
15
19
  @webpacker ||= ::Webpacker::Instance.new(
data/lib/avo/app.rb CHANGED
@@ -26,12 +26,16 @@ module Avo
26
26
  self.request = request
27
27
  self.context = context
28
28
 
29
+ self.license = Licensing::LicenseManager.new(Licensing::HQ.new(request).response).license
30
+
29
31
  # Set the current host for ActiveStorage
30
- ActiveStorage::Current.host = request.base_url
32
+ begin
33
+ ActiveStorage::Current.host = request.base_url
34
+ rescue => exception
35
+ Rails.logger.debug "[Avo] Failed to set ActiveStorage::Current.host, #{exception.inspect}"
36
+ end
31
37
 
32
38
  init_resources
33
-
34
- self.license = Licensing::LicenseManager.new(Licensing::HQ.new(request).response).license
35
39
  end
36
40
 
37
41
  def cache_store
@@ -21,6 +21,7 @@ module Avo
21
21
  attr_accessor :context
22
22
  attr_accessor :display_breadcrumbs
23
23
  attr_accessor :initial_breadcrumbs
24
+ attr_accessor :home_path
24
25
 
25
26
  def initialize
26
27
  @root_path = "/avo"
@@ -54,6 +55,7 @@ module Avo
54
55
  add_breadcrumb I18n.t("avo.home").humanize, avo.root_path
55
56
  }
56
57
  @display_breadcrumbs = true
58
+ @home_path = nil
57
59
  end
58
60
 
59
61
  def locale_tag
@@ -81,6 +83,10 @@ module Avo
81
83
  def set_initial_breadcrumbs(&block)
82
84
  @initial_breadcrumbs = block if block.present?
83
85
  end
86
+
87
+ def namespace
88
+ root_path.delete "/"
89
+ end
84
90
  end
85
91
 
86
92
  def self.configuration
@@ -3,8 +3,8 @@ module Avo
3
3
  class HQ
4
4
  attr_accessor :current_request
5
5
 
6
- ENDPOINT = "https://avohq.io/api/v1/licenses/check" unless const_defined?(:ENDPOINT)
7
- CACHE_KEY = "avo.hq.response" unless const_defined?(:CACHE_KEY)
6
+ ENDPOINT = "https://avohq.io/api/v1/licenses/check".freeze unless const_defined?(:ENDPOINT)
7
+ CACHE_KEY = "avo.hq.response".freeze unless const_defined?(:CACHE_KEY)
8
8
  REQUEST_TIMEOUT = 5 unless const_defined?(:REQUEST_TIMEOUT) # seconds
9
9
 
10
10
  def initialize(current_request)
@@ -54,7 +54,7 @@ module Avo
54
54
  end
55
55
 
56
56
  def perform_request
57
- puts "Performing request to avohq.io API to check license availability.".inspect if Rails.env.development?
57
+ ::Rails.logger.debug "[Avo] Performing request to avohq.io API to check license availability." if Rails.env.development?
58
58
 
59
59
  HTTParty.post ENDPOINT, body: payload.to_json, headers: {'Content-type': "application/json"}, timeout: REQUEST_TIMEOUT
60
60
  end
@@ -4,11 +4,13 @@ module Avo
4
4
  attr_accessor :id
5
5
  attr_accessor :response
6
6
  attr_accessor :valid
7
+ attr_accessor :payload
7
8
 
8
9
  def initialize(response)
9
10
  @response = response
10
11
  @id = response["id"]
11
12
  @valid = response["valid"]
13
+ @payload = response["payload"]
12
14
  end
13
15
 
14
16
  def valid?
@@ -3,7 +3,8 @@ module Avo
3
3
  class ProLicense < License
4
4
  def abilities
5
5
  [
6
- :authorization
6
+ :authorization,
7
+ :custom_tools
7
8
  ]
8
9
  end
9
10
  end
data/lib/avo/version.rb CHANGED
@@ -1,3 +1,3 @@
1
1
  module Avo
2
- VERSION = "1.2.2"
2
+ VERSION = "1.2.6"
3
3
  end
@@ -29,10 +29,10 @@ Avo.configure do |config|
29
29
  # }
30
30
 
31
31
  ## == Localization ==
32
+ # config.locale = 'en-US'
32
33
 
33
34
  ## == Customization ==
34
35
  # config.app_name = 'Avocadelicious'
35
- # config.locale = 'en-US'
36
36
  # config.timezone = 'UTC'
37
37
  # config.currency = 'USD'
38
38
  # config.per_page = 24
@@ -43,4 +43,13 @@ Avo.configure do |config|
43
43
  # config.full_width_container = false
44
44
  # config.full_width_index_view = false
45
45
  # config.cache_resources_on_index_view = true
46
+
47
+ # Where should the user be redirected when he hits the `/<%= options[:path] %>` url
48
+ # config.home_path = nil
49
+
50
+ ## == Breadcrumbs ==
51
+ # config.display_breadcrumbs = true
52
+ # config.set_initial_breadcrumbs do
53
+ # add_breadcrumb "Home", '/<%= options[:path] %>'
54
+ # end
46
55
  end
@@ -34,8 +34,8 @@ module Generators
34
34
  template "tool/view.tt", "app/views/avo/tools/#{file_name}.html.erb"
35
35
 
36
36
  route <<-ROUTE
37
- namespace :#{::Avo.configuration.root_path.gsub('/', '')} do
38
- get "#{file_name}", to: "tools##{file_name}"
37
+ scope :#{::Avo.configuration.namespace} do
38
+ get "#{file_name}", to: "avo/tools##{file_name}"
39
39
  end
40
40
  ROUTE
41
41
  end
@@ -3646,6 +3646,11 @@ span.CodeMirror-selectedtext { background: none; }
3646
3646
  min-height: auto;
3647
3647
  }
3648
3648
 
3649
+ /* overlay CodeMirror fullscreen & Preview on small screens */
3650
+ .CodeMirror-fullscreen, .editor-preview-active-side {
3651
+ z-index: 50;
3652
+ }
3653
+
3649
3654
  .container {
3650
3655
  width: 100%;
3651
3656
  }
@@ -4558,15 +4563,15 @@ span.CodeMirror-selectedtext { background: none; }
4558
4563
  .top-full {
4559
4564
  top: 100%
4560
4565
  }
4566
+ .bottom-0 {
4567
+ bottom: 0px
4568
+ }
4561
4569
  .left-1\/2 {
4562
4570
  left: 50%
4563
4571
  }
4564
4572
  .top-1\/2 {
4565
4573
  top: 50%
4566
4574
  }
4567
- .bottom-0 {
4568
- bottom: 0px
4569
- }
4570
4575
  .top-\[-1px\] {
4571
4576
  top: -1px
4572
4577
  }
@@ -4632,6 +4637,12 @@ span.CodeMirror-selectedtext { background: none; }
4632
4637
  .mb-0 {
4633
4638
  margin-bottom: 0px
4634
4639
  }
4640
+ .mt-1 {
4641
+ margin-top: 0.25rem
4642
+ }
4643
+ .mb-4 {
4644
+ margin-bottom: 1rem
4645
+ }
4635
4646
  .-ml-20 {
4636
4647
  margin-left: -5rem
4637
4648
  }
@@ -4680,9 +4691,6 @@ span.CodeMirror-selectedtext { background: none; }
4680
4691
  .mb-2 {
4681
4692
  margin-bottom: 0.5rem
4682
4693
  }
4683
- .mb-4 {
4684
- margin-bottom: 1rem
4685
- }
4686
4694
  .ml-2 {
4687
4695
  margin-left: 0.5rem
4688
4696
  }
@@ -4716,6 +4724,9 @@ span.CodeMirror-selectedtext { background: none; }
4716
4724
  .h-5 {
4717
4725
  height: 1.25rem
4718
4726
  }
4727
+ .h-6 {
4728
+ height: 1.5rem
4729
+ }
4719
4730
  .h-64 {
4720
4731
  height: 16rem
4721
4732
  }
@@ -4728,9 +4739,6 @@ span.CodeMirror-selectedtext { background: none; }
4728
4739
  .h-full {
4729
4740
  height: 100%
4730
4741
  }
4731
- .h-6 {
4732
- height: 1.5rem
4733
- }
4734
4742
  .h-16 {
4735
4743
  height: 4rem
4736
4744
  }
@@ -5126,9 +5134,9 @@ span.CodeMirror-selectedtext { background: none; }
5126
5134
  --tw-bg-opacity: 1;
5127
5135
  background-color: rgba(243, 244, 246, var(--tw-bg-opacity))
5128
5136
  }
5129
- .bg-teal-700 {
5137
+ .bg-green-700 {
5130
5138
  --tw-bg-opacity: 1;
5131
- background-color: rgba(15, 118, 110, var(--tw-bg-opacity))
5139
+ background-color: rgba(4, 120, 87, var(--tw-bg-opacity))
5132
5140
  }
5133
5141
  .bg-blue-gray-200 {
5134
5142
  --tw-bg-opacity: 1;
@@ -5397,6 +5405,9 @@ span.CodeMirror-selectedtext { background: none; }
5397
5405
  --tw-text-opacity: 1;
5398
5406
  color: rgba(185, 28, 28, var(--tw-text-opacity))
5399
5407
  }
5408
+ .opacity-75 {
5409
+ opacity: 0.75
5410
+ }
5400
5411
  .opacity-50 {
5401
5412
  opacity: 0.5
5402
5413
  }
@@ -5903,4 +5914,4 @@ html, body{
5903
5914
  }
5904
5915
 
5905
5916
 
5906
- /*# sourceMappingURL=application-13cc02fb.css.map*/
5917
+ /*# sourceMappingURL=application-af3e670d.css.map*/