maquina 0.1.0 → 0.2.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.
- checksums.yaml +4 -4
- data/.overmind.env +1 -0
- data/Gemfile +20 -0
- data/Gemfile.lock +346 -0
- data/Procfile.dev +3 -0
- data/app/assets/images/maquina/.keep +0 -0
- data/app/assets/javascripts/maquina/controllers/file_controller.js +1 -1
- data/app/assets/stylesheets/maquina/application.tailwind.css +96 -97
- data/app/controllers/concerns/.keep +0 -0
- data/app/controllers/concerns/maquina/authenticate.rb +5 -1
- data/app/controllers/concerns/maquina/resourceful.rb +9 -9
- data/app/models/concerns/.keep +0 -0
- data/app/models/concerns/maquina/blockeable.rb +13 -3
- data/app/models/maquina/current.rb +2 -1
- data/app/models/maquina/membership.rb +10 -0
- data/app/models/maquina/organization.rb +7 -0
- data/app/models/maquina/plan.rb +2 -0
- data/app/models/maquina/user.rb +8 -0
- data/app/policies/maquina/application_policy.rb +3 -6
- data/app/policies/maquina/navigation_policy.rb +2 -2
- data/app/policies/maquina/user_policy.rb +7 -3
- data/app/views/layouts/maquina/application.html.erb +1 -2
- data/app/views/layouts/maquina/sessions.html.erb +1 -2
- data/app/views/maquina/application/components/file_component.rb +38 -5
- data/app/views/maquina/application/form.rb +3 -2
- data/config/importmap.rb +12 -0
- data/db/migrate/20230829183530_create_maquina_organizations.rb +11 -0
- data/db/migrate/20230829192656_create_maquina_memberships.rb +15 -0
- data/lib/generators/maquina/tailwind_config/USAGE +14 -0
- data/lib/generators/maquina/tailwind_config/tailwind_config_generator.rb +17 -3
- data/lib/generators/maquina/tailwind_config/templates/app/assets/stylesheets/maquina.css +96 -0
- data/lib/generators/maquina/tailwind_config/templates/lib/generators/tailwind_config/tailwind_config_generator.rb.tt +11 -0
- data/lib/generators/maquina/tailwind_config/templates/{app/assets/config/maquina → lib/generators/tailwind_config/templates/config}/tailwind.config.js.tt +4 -0
- data/lib/generators/maquina/tailwind_config/templates/lib/tasks/tailwind.rake.tt +11 -0
- data/lib/maquina/engine.rb +0 -4
- data/lib/maquina/version.rb +1 -1
- data/lib/maquina.rb +7 -4
- metadata +22 -9
- data/config/definitions.rb +0 -1
- data/config/initializers/importmap.rb +0 -17
- data/lib/tasks/tailwind.rake +0 -25
@@ -4,7 +4,16 @@ module Maquina
|
|
4
4
|
module Blockeable
|
5
5
|
extend ActiveSupport::Concern
|
6
6
|
|
7
|
-
included do
|
7
|
+
included do |base|
|
8
|
+
if base.eql?(Maquina::User)
|
9
|
+
define_method(:memberships_blocked?) do
|
10
|
+
return false if management?
|
11
|
+
|
12
|
+
return @memberships_blocked if !@memberships_blocked.nil?
|
13
|
+
@memberships_blocked = !memberships.includes(:organization).where(blocked_at: nil).where(maquina_organizations: {active: true}).exists?
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
8
17
|
if has_attribute?(:blocked_at) && has_attribute?(:temporary_blocked_at)
|
9
18
|
define_method(:blocked?) do
|
10
19
|
temporary_blocked_until = nil
|
@@ -12,13 +21,14 @@ module Maquina
|
|
12
21
|
temporary_blocked_until = temporary_blocked_at.since(Maquina.configuration.temporary_block)
|
13
22
|
end
|
14
23
|
|
15
|
-
blocked_at.present? || (temporary_blocked_until.present? && temporary_blocked_until > Time.zone.now)
|
24
|
+
blocked_at.present? || (temporary_blocked_until.present? && temporary_blocked_until > Time.zone.now) ||
|
25
|
+
(respond_to?(:memberships_blocked?) && memberships_blocked?)
|
16
26
|
end
|
17
27
|
|
18
28
|
scope :unblocked, -> { where(blocked_at: nil).where("(coalesce(temporary_blocked_at + interval '? minutes', now())) <= now()", Maquina.configuration.temporary_block&.in_minutes&.to_i || 0) }
|
19
29
|
elsif has_attribute(:blocked_at)
|
20
30
|
define_method(:blocked?) do
|
21
|
-
blocked_at.present?
|
31
|
+
blocked_at.present? || (respond_to?(:memberships_blocked?) && memberships_blocked?)
|
22
32
|
end
|
23
33
|
|
24
34
|
scope :unblocked, -> { where(blocked_at: nil) }
|
@@ -2,7 +2,7 @@
|
|
2
2
|
|
3
3
|
module Maquina
|
4
4
|
class Current < ActiveSupport::CurrentAttributes
|
5
|
-
attribute :active_session, :user
|
5
|
+
attribute :active_session, :user, :membership
|
6
6
|
|
7
7
|
def signed_in?
|
8
8
|
return false if active_session.blank?
|
@@ -12,6 +12,7 @@ module Maquina
|
|
12
12
|
def active_session=(value)
|
13
13
|
super
|
14
14
|
self.user = value&.user
|
15
|
+
self.membership = user.default_membership
|
15
16
|
end
|
16
17
|
|
17
18
|
def management?
|
@@ -0,0 +1,10 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Maquina
|
4
|
+
class Membership < ApplicationRecord
|
5
|
+
belongs_to :organization, class_name: "Maquina::Organization", foreign_key: :maquina_organization_id
|
6
|
+
belongs_to :user, class_name: "Maquina::User", foreign_key: :maquina_user_id
|
7
|
+
|
8
|
+
enum role: Maquina.configuration.membership_roles
|
9
|
+
end
|
10
|
+
end
|
data/app/models/maquina/plan.rb
CHANGED
@@ -27,6 +27,8 @@ module Maquina
|
|
27
27
|
class Plan < ApplicationRecord
|
28
28
|
include Searchable
|
29
29
|
|
30
|
+
has_many :organizations, class_name: "Maquina::Organization", foreign_key: :maquina_plan_id, dependent: :nullify
|
31
|
+
|
30
32
|
monetize :price_cents
|
31
33
|
|
32
34
|
validates :price, numericality: {greater_than_or_equal_to: 0}, if: ->(plan) { plan.free? }
|
data/app/models/maquina/user.rb
CHANGED
@@ -11,6 +11,8 @@ module Maquina
|
|
11
11
|
PASSWORD_COMPLEXITY_REGEX = /\A(?=.*[a-z])(?=.*[A-Z])(?=.*\d)(?=.*[@$!%*?&#-=+])[A-Za-z\d@$!%*?&#-=+]{8,}\z/
|
12
12
|
has_secure_password
|
13
13
|
|
14
|
+
has_many :memberships, class_name: "Maquina::Membership", foreign_key: :maquina_user_id, inverse_of: :user
|
15
|
+
|
14
16
|
validates :email, presence: true, uniqueness: true, format: {with: URI::MailTo::EMAIL_REGEXP}
|
15
17
|
validates :password, format: {with: PASSWORD_COMPLEXITY_REGEX}, unless: ->(user) { user.password.blank? }
|
16
18
|
|
@@ -24,6 +26,12 @@ module Maquina
|
|
24
26
|
password_expires_at < Time.zone.now
|
25
27
|
end
|
26
28
|
|
29
|
+
def default_membership
|
30
|
+
return nil if management?
|
31
|
+
|
32
|
+
memberships.detect { |membership| membership.blocked_at.blank? && membership.organization.present? && membership.organization.active? }
|
33
|
+
end
|
34
|
+
|
27
35
|
private
|
28
36
|
|
29
37
|
def downcase_email
|
@@ -40,11 +40,8 @@ module Maquina
|
|
40
40
|
user.management?
|
41
41
|
end
|
42
42
|
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
# def owner?
|
47
|
-
# record.user_id == user.id
|
48
|
-
# end
|
43
|
+
def admin?
|
44
|
+
(Maquina::Current.membership.present? && Maquina::Current.membership.admin?)
|
45
|
+
end
|
49
46
|
end
|
50
47
|
end
|
@@ -3,11 +3,11 @@
|
|
3
3
|
module Maquina
|
4
4
|
class UserPolicy < ApplicationPolicy
|
5
5
|
def index?
|
6
|
-
management?
|
6
|
+
management? || admin?
|
7
7
|
end
|
8
8
|
|
9
9
|
def new?
|
10
|
-
management?
|
10
|
+
management? || admin?
|
11
11
|
end
|
12
12
|
|
13
13
|
def create?
|
@@ -21,7 +21,11 @@ module Maquina
|
|
21
21
|
private
|
22
22
|
|
23
23
|
relation_scope do |scope|
|
24
|
-
|
24
|
+
if management?
|
25
|
+
scope.where(management: management?)
|
26
|
+
else
|
27
|
+
scope.joins(memberships: :organization).where(maquina_organizations: {id: Maquina::Current.membership.organization.id})
|
28
|
+
end
|
25
29
|
end
|
26
30
|
end
|
27
31
|
end
|
@@ -6,8 +6,7 @@
|
|
6
6
|
<%= csrf_meta_tags %>
|
7
7
|
<%= csp_meta_tag %>
|
8
8
|
|
9
|
-
<%= stylesheet_link_tag "
|
10
|
-
<%= stylesheet_link_tag "maquina/application", "data-turbo-track": "reload", media: "all" %>
|
9
|
+
<%= stylesheet_link_tag "tailwind", "inter-font", "data-turbo-track": "reload" %>
|
11
10
|
|
12
11
|
<%= maquina_importmap_tags %>
|
13
12
|
</head>
|
@@ -6,8 +6,7 @@
|
|
6
6
|
<%= csrf_meta_tags %>
|
7
7
|
<%= csp_meta_tag %>
|
8
8
|
|
9
|
-
<%= stylesheet_link_tag "
|
10
|
-
<%= stylesheet_link_tag "maquina/application", "data-turbo-track": "reload" %>
|
9
|
+
<%= stylesheet_link_tag "tailwind", "inter-font", "data-turbo-track": "reload" %>
|
11
10
|
|
12
11
|
<%= maquina_importmap_tags %>
|
13
12
|
</head>
|
@@ -5,17 +5,21 @@ module Maquina
|
|
5
5
|
module Components
|
6
6
|
class FileComponent < ComponentBase
|
7
7
|
include Phlex::Rails::Helpers::NumberToHumanSize
|
8
|
+
include Phlex::Rails::Helpers::TokenList
|
9
|
+
|
10
|
+
delegate :main_app, to: :helpers
|
8
11
|
|
9
12
|
def template
|
10
|
-
div(**extend_control_options(
|
13
|
+
div(**extend_control_options(control_html)) do
|
11
14
|
@form.label attribute_name, class: "label #{label_css_class}"
|
12
15
|
div(class: "mt-1") do
|
13
16
|
div(data_file_target: "container") do
|
14
17
|
@form.file_field attribute_name, **extend_input_options(input_html(no_helpers: true))
|
15
|
-
img(class: "
|
16
|
-
svg(viewbox: "0 0 24 24", fill: "currentColor", aria_hidden: "true", data_action: "click->file#select", data_file_target: "placeholder") do |s|
|
18
|
+
img(class: token_list("", hidden: !attached_file?), data_file_target: "preview", src: attached_url)
|
19
|
+
svg(viewbox: "0 0 24 24", fill: "currentColor", class: token_list("", hidden: attached_file?), aria_hidden: "true", data_action: "click->file#select", data_file_target: "placeholder") do |s|
|
17
20
|
s.path(fill_rule: "evenodd", d: "M1.5 6a2.25 2.25 0 012.25-2.25h16.5A2.25 2.25 0 0122.5 6v12a2.25 2.25 0 01-2.25 2.25H3.75A2.25 2.25 0 011.5 18V6zM3 16.06V18c0 .414.336.75.75.75h16.5A.75.75 0 0021 18v-1.94l-2.69-2.689a1.5 1.5 0 00-2.12 0l-.88.879.97.97a.75.75 0 11-1.06 1.06l-5.16-5.159a1.5 1.5 0 00-2.12 0L3 16.061zm10.125-7.81a1.125 1.125 0 112.25 0 1.125 1.125 0 01-2.25 0z", clip_rule: "evenodd")
|
18
21
|
end
|
22
|
+
p(class: "text-skin-muted pb-4 pt-2 italic text-sm") { attached_info } if attached_file?
|
19
23
|
help_template
|
20
24
|
error_template
|
21
25
|
end
|
@@ -41,18 +45,47 @@ module Maquina
|
|
41
45
|
}.deep_merge(input_html)
|
42
46
|
end
|
43
47
|
|
44
|
-
def extend_control_options(
|
48
|
+
def extend_control_options(control_html)
|
45
49
|
max_size = control_html.dig(:data, :file_max_size_value) || 4_194_304
|
46
50
|
human_max_size = number_to_human_size(max_size)
|
51
|
+
file_url = attached_url
|
47
52
|
|
48
53
|
{
|
49
54
|
data: {
|
50
55
|
controller: "file",
|
51
56
|
file_max_size_value: max_size,
|
52
|
-
file_validation_message_value: t("activerecord.errors.attributes.#{@form.object.model_name.i18n_key}.#{attribute_name}.oversize", size: human_max_size, default: t("activerecord.errors.attributes.file.oversize", size: human_max_size))
|
57
|
+
file_validation_message_value: t("activerecord.errors.attributes.#{@form.object.model_name.i18n_key}.#{attribute_name}.oversize", size: human_max_size, default: t("activerecord.errors.attributes.file.oversize", size: human_max_size)),
|
58
|
+
file_url_value: file_url
|
53
59
|
}
|
54
60
|
}.deep_merge(control_html)
|
55
61
|
end
|
62
|
+
|
63
|
+
# Todo: Work on not representable files
|
64
|
+
def attached_url
|
65
|
+
return "" if !attached_file?
|
66
|
+
|
67
|
+
if attached_file.blob.representable?
|
68
|
+
puts "Representable"
|
69
|
+
main_app.url_for(attached_file.blob.variant(resize_to_limit: [1200, 768]))
|
70
|
+
else
|
71
|
+
puts "No representable"
|
72
|
+
main_app.url_for(attached_file.blob)
|
73
|
+
end
|
74
|
+
end
|
75
|
+
|
76
|
+
def attached_info
|
77
|
+
return "" if !attached_file?
|
78
|
+
|
79
|
+
"#{attached_file.blob.filename} (#{number_to_human_size(attached_file.blob.byte_size)})"
|
80
|
+
end
|
81
|
+
|
82
|
+
def attached_file
|
83
|
+
@attached_file ||= @resource.send(attribute_name)
|
84
|
+
end
|
85
|
+
|
86
|
+
def attached_file?
|
87
|
+
attached_file&.attached?
|
88
|
+
end
|
56
89
|
end
|
57
90
|
end
|
58
91
|
end
|
@@ -49,8 +49,9 @@ module Maquina
|
|
49
49
|
|
50
50
|
def form_header_template
|
51
51
|
div do
|
52
|
-
|
53
|
-
|
52
|
+
prefix = @resource.persisted? ? :edit : :new
|
53
|
+
h3(class: "text-lg font-medium leading-6 text-skin-base") { t("#{prefix}.#{resource_class.model_name.i18n_key}.title", model: model_human_name.downcase, default: t("#{prefix}.title", default: model_human_name.downcase)) }
|
54
|
+
p(class: "mt-1 text-sm text-skin-dimmed") { t("#{prefix}.#{resource_class.model_name.i18n_key}.description", model: model_human_name.downcase, default: t("#{prefix}.description", model: model_human_name.downcase)) }
|
54
55
|
end
|
55
56
|
end
|
56
57
|
|
data/config/importmap.rb
ADDED
@@ -0,0 +1,12 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# Stimulus & Turbo
|
4
|
+
pin "@hotwired/turbo-rails", to: "turbo.min.js", preload: true
|
5
|
+
pin "@hotwired/stimulus", to: "stimulus.min.js", preload: true
|
6
|
+
pin "@hotwired/stimulus-loading", to: "stimulus-loading.js", preload: true
|
7
|
+
pin "stimulus-use", to: "https://ga.jspm.io/npm:stimulus-use@0.52.0/dist/index.js"
|
8
|
+
|
9
|
+
# Maquina entrypoint
|
10
|
+
pin "application", to: "maquina/application.js", preload: true
|
11
|
+
|
12
|
+
pin_all_from Maquina::Engine.root.join("app/assets/javascripts/maquina/controllers"), under: "controllers", to: "maquina/controllers"
|
@@ -0,0 +1,11 @@
|
|
1
|
+
class CreateMaquinaOrganizations < ActiveRecord::Migration[7.0]
|
2
|
+
def change
|
3
|
+
create_table :maquina_organizations do |t|
|
4
|
+
t.string :name
|
5
|
+
t.boolean :active, default: true
|
6
|
+
t.references :maquina_plan, null: true, foreign_key: true
|
7
|
+
|
8
|
+
t.timestamps
|
9
|
+
end
|
10
|
+
end
|
11
|
+
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
class CreateMaquinaMemberships < ActiveRecord::Migration[7.0]
|
2
|
+
def change
|
3
|
+
create_enum :maquina_role, %w[admin member]
|
4
|
+
|
5
|
+
create_table :maquina_memberships do |t|
|
6
|
+
t.references :maquina_organization, null: false, foreign_key: true
|
7
|
+
t.references :maquina_user, null: false, foreign_key: true
|
8
|
+
t.boolean :owner, default: false
|
9
|
+
t.enum :role, enum_type: :maquina_role, default: "member", null: false
|
10
|
+
t.timestamp :blocked_at
|
11
|
+
|
12
|
+
t.timestamps
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
Description:
|
2
|
+
It will create a custom TailwindCSS configuration file for Rails applications. The custom configuration file is
|
3
|
+
auto-generated that allows to include Engines files.
|
4
|
+
|
5
|
+
Add the file config/tailwind.config.js to the .gitignore file, and if you need to modify it, modify the template
|
6
|
+
file included in the generator.
|
7
|
+
|
8
|
+
Example:
|
9
|
+
bin/rails generate maquina:tailwind_config
|
10
|
+
|
11
|
+
This will create:
|
12
|
+
lib/tailwind.rake
|
13
|
+
lib/generators/tailwind_config/tailwind_config_generator.rb
|
14
|
+
lib/generators/tailwind_config/templates/tailwind.config.js.tt
|
@@ -2,10 +2,24 @@
|
|
2
2
|
|
3
3
|
module Maquina
|
4
4
|
class TailwindConfigGenerator < Rails::Generators::Base
|
5
|
-
source_root File.expand_path("
|
5
|
+
source_root File.expand_path("templates", __dir__)
|
6
6
|
|
7
|
-
def
|
8
|
-
|
7
|
+
def create_generator
|
8
|
+
tailwind_config_file = "lib/generators/tailwind_config/templates/config/tailwind.config.js.tt"
|
9
|
+
|
10
|
+
template "lib/tasks/tailwind.rake"
|
11
|
+
template "lib/generators/tailwind_config/tailwind_config_generator.rb"
|
12
|
+
|
13
|
+
# Seems that template can't handle .tt.tt extensions correctly
|
14
|
+
copy_file tailwind_config_file, tailwind_config_file
|
15
|
+
end
|
16
|
+
|
17
|
+
def configure_css
|
18
|
+
copy_file "app/assets/stylesheets/maquina.css"
|
19
|
+
|
20
|
+
inject_into_file "app/assets/stylesheets/application.tailwind.css", after: /base"?;/ do
|
21
|
+
%(\n@import "./maquina.css";)
|
22
|
+
end
|
9
23
|
end
|
10
24
|
end
|
11
25
|
end
|
@@ -0,0 +1,96 @@
|
|
1
|
+
:root {
|
2
|
+
--color-base: 31 27 54;
|
3
|
+
--color-accented: 37 99 235;
|
4
|
+
--color-inverted: 255 255 255;
|
5
|
+
--color-accented-hover: 59 130 246;
|
6
|
+
--color-muted: 55 65 81;
|
7
|
+
--color-dimmed: 75 85 99;
|
8
|
+
--color-error: 220 38 38;
|
9
|
+
|
10
|
+
--color-border-base: 209 213 219;
|
11
|
+
--color-border-accented: 37 99 235;
|
12
|
+
}
|
13
|
+
|
14
|
+
.label {
|
15
|
+
@apply text-sm font-medium text-skin-muted;
|
16
|
+
}
|
17
|
+
|
18
|
+
.input {
|
19
|
+
@apply appearance-none rounded-md border border-skin-base px-3 py-2 placeholder-gray-400 shadow-sm focus:border-skin-accented focus:outline-none focus:ring-skin-accented sm:text-sm;
|
20
|
+
}
|
21
|
+
|
22
|
+
.link {
|
23
|
+
@apply font-medium text-skin-accented hover:text-skin-accented-hover;
|
24
|
+
}
|
25
|
+
|
26
|
+
.check {
|
27
|
+
@apply border-skin-base h-4 w-4 text-skin-accented focus:ring-skin-accented rounded;
|
28
|
+
}
|
29
|
+
|
30
|
+
.button {
|
31
|
+
@apply inline-flex justify-center py-2 px-4 border border-skin-base rounded-md shadow-sm text-sm font-medium text-skin-muted bg-white hover:bg-gray-50 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-skin-accented;
|
32
|
+
}
|
33
|
+
|
34
|
+
.control-error .label {
|
35
|
+
@apply text-skin-error;
|
36
|
+
}
|
37
|
+
|
38
|
+
.control-error .input {
|
39
|
+
@apply border-skin-error focus:border-skin-error focus:ring-skin-error;
|
40
|
+
}
|
41
|
+
|
42
|
+
.help {
|
43
|
+
@apply mt-2 text-sm text-skin-dimmed;
|
44
|
+
}
|
45
|
+
|
46
|
+
.help-error {
|
47
|
+
@apply text-skin-error;
|
48
|
+
}
|
49
|
+
|
50
|
+
.button[disabled] {
|
51
|
+
@apply bg-gray-50 text-skin-dimmed cursor-default;
|
52
|
+
}
|
53
|
+
|
54
|
+
.button-accented {
|
55
|
+
@apply rounded-md border border-transparent bg-skin-accented py-2 px-4 text-sm font-medium text-skin-inverted shadow-sm hover:bg-skin-accented-hover focus:outline-none focus:ring-2 focus:ring-skin-accented focus:ring-offset-2;
|
56
|
+
}
|
57
|
+
|
58
|
+
input[type="search"] {
|
59
|
+
@apply block w-full rounded-md border border-skin-base pl-10 leading-5 placeholder-gray-400 focus:placeholder-gray-300 focus:outline-none focus:ring-1 focus:ring-skin-accented focus:border-skin-accented sm:text-sm;
|
60
|
+
}
|
61
|
+
|
62
|
+
.desktop-menu {
|
63
|
+
@apply hidden lg:ml-6 lg:flex lg:space-x-8;
|
64
|
+
}
|
65
|
+
|
66
|
+
.desktop-menu-item {
|
67
|
+
@apply font-sans uppercase border-transparent text-skin-dimmed underline-offset-4 decoration-2 hover:underline hover:decoration-skin-accented hover:text-skin-muted inline-flex items-center px-1 pt-1 text-sm font-medium;
|
68
|
+
}
|
69
|
+
|
70
|
+
.desktop-menu-item__active {
|
71
|
+
@apply decoration-skin-accented underline text-skin-base;
|
72
|
+
}
|
73
|
+
|
74
|
+
.mobile-menu {
|
75
|
+
@apply pt-2 pb-3 space-y-1;
|
76
|
+
}
|
77
|
+
|
78
|
+
.mobile-menu-item {
|
79
|
+
@apply font-sans border-transparent text-skin-dimmed hover:bg-gray-200 hover:border-gray-300 hover:text-skin-muted block pl-3 pr-4 py-2 border-l-4 text-base font-medium;
|
80
|
+
}
|
81
|
+
|
82
|
+
.mobile-menu-item__active {
|
83
|
+
@apply bg-skin-accented-hover border-skin-accented text-skin-accented hover:text-skin-accented hover:bg-skin-accented-hover hover:border-skin-accented;
|
84
|
+
}
|
85
|
+
|
86
|
+
.desktop-profile-menu-item {
|
87
|
+
@apply block w-full text-left font-sans px-4 py-2 text-sm text-skin-dimmed hover:bg-gray-200 hover:text-skin-muted;
|
88
|
+
}
|
89
|
+
|
90
|
+
.mobile-profile-menu-item {
|
91
|
+
@apply block font-sans px-4 py-2 text-base font-medium text-skin-dimmed hover:text-skin-muted hover:bg-gray-200;
|
92
|
+
}
|
93
|
+
|
94
|
+
.mobile-button {
|
95
|
+
@apply inline-flex items-center justify-center p-2 rounded-md text-skin-dimmed hover:text-skin-muted hover:bg-gray-100 focus:outline-none focus:ring-2 focus:ring-inset focus:ring-skin-accented;
|
96
|
+
}
|
@@ -0,0 +1,11 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
class TailwindConfigGenerator < Rails::Generators::Base
|
4
|
+
source_root File.expand_path("templates", __dir__)
|
5
|
+
|
6
|
+
def create_tailwind_config_file
|
7
|
+
@engines_paths = Maquina.configuration.tailwind_content
|
8
|
+
|
9
|
+
template "config/tailwind.config.js"
|
10
|
+
end
|
11
|
+
end
|
@@ -2,6 +2,10 @@ const defaultTheme = require('tailwindcss/defaultTheme')
|
|
2
2
|
|
3
3
|
module.exports = {
|
4
4
|
content: [
|
5
|
+
'public/*.html',
|
6
|
+
'app/helpers/**/*.rb',
|
7
|
+
'app/javascript/**/*.js',
|
8
|
+
'app/views/**/*.{erb,haml,html,slim}',
|
5
9
|
<%= Maquina.configuration.tailwind_content.map{|path| "'#{path}'"}.join(",\n") %>
|
6
10
|
],
|
7
11
|
theme: {
|
@@ -0,0 +1,11 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
namespace :tailwindcss do
|
4
|
+
desc "Generates your tailwind config file"
|
5
|
+
task :config do
|
6
|
+
Rails::Generators.invoke("tailwind_config", ["--force"])
|
7
|
+
end
|
8
|
+
end
|
9
|
+
|
10
|
+
Rake::Task["tailwindcss:build"].enhance(["tailwindcss:config"])
|
11
|
+
Rake::Task["tailwindcss:watch"].enhance(["tailwindcss:config"])
|
data/lib/maquina/engine.rb
CHANGED
@@ -9,9 +9,5 @@ module Maquina
|
|
9
9
|
class Engine < ::Rails::Engine
|
10
10
|
config.autoload_paths += %W[#{Engine.root}/app/views]
|
11
11
|
isolate_namespace Maquina
|
12
|
-
|
13
|
-
initializer "maquina.importmap", before: "importmap" do |app|
|
14
|
-
app.config.importmap.paths << Engine.root.join("config/initializers/importmap.rb")
|
15
|
-
end
|
16
12
|
end
|
17
13
|
end
|
data/lib/maquina/version.rb
CHANGED
data/lib/maquina.rb
CHANGED
@@ -15,22 +15,25 @@ module Maquina
|
|
15
15
|
|
16
16
|
class Configuration
|
17
17
|
attr_accessor :password_retain_count, :temporary_block, :session_expiration, :signin_attempts, :tailwind_content,
|
18
|
-
:importmap, :root_app_path
|
18
|
+
:importmap, :root_app_path, :membership_roles
|
19
19
|
|
20
20
|
def initialize
|
21
21
|
@password_retain_count = 3
|
22
22
|
@temporary_block = 5.minutes
|
23
23
|
@session_expiration = 2.days
|
24
24
|
@signin_attempts = 5
|
25
|
-
@importmap = Importmap::Map.new
|
26
25
|
@root_app_path = nil
|
27
26
|
|
27
|
+
@membership_roles = {admin: "admin", member: "member"}
|
28
|
+
|
29
|
+
@importmap = Importmap::Map.new
|
30
|
+
@importmap.draw(Engine.root.join("config/importmap.rb"))
|
31
|
+
|
28
32
|
@tailwind_content = [
|
29
33
|
"#{Maquina::Engine.root}/app/views/**/*.{rb,erb}",
|
30
34
|
"#{Maquina::Engine.root}/app/helpers/**/*.rb",
|
31
35
|
"#{Maquina::Engine.root}/app/controllers/**/*.rb",
|
32
|
-
"#{Maquina::Engine.root}/app/javascript/**/*.js"
|
33
|
-
"#{Maquina::Engine.root}/app/assets/**/application.tailwind.css"
|
36
|
+
"#{Maquina::Engine.root}/app/javascript/**/*.js"
|
34
37
|
]
|
35
38
|
end
|
36
39
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: maquina
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Mario Alberto Chávez
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-08-
|
11
|
+
date: 2023-08-30 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rails
|
@@ -86,14 +86,14 @@ dependencies:
|
|
86
86
|
requirements:
|
87
87
|
- - "~>"
|
88
88
|
- !ruby/object:Gem::Version
|
89
|
-
version: 1.
|
89
|
+
version: 1.2.0
|
90
90
|
type: :runtime
|
91
91
|
prerelease: false
|
92
92
|
version_requirements: !ruby/object:Gem::Requirement
|
93
93
|
requirements:
|
94
94
|
- - "~>"
|
95
95
|
- !ruby/object:Gem::Version
|
96
|
-
version: 1.
|
96
|
+
version: 1.2.0
|
97
97
|
- !ruby/object:Gem::Dependency
|
98
98
|
name: tailwindcss-rails
|
99
99
|
requirement: !ruby/object:Gem::Requirement
|
@@ -295,9 +295,14 @@ executables: []
|
|
295
295
|
extensions: []
|
296
296
|
extra_rdoc_files: []
|
297
297
|
files:
|
298
|
+
- ".overmind.env"
|
299
|
+
- Gemfile
|
300
|
+
- Gemfile.lock
|
298
301
|
- MIT-LICENSE
|
302
|
+
- Procfile.dev
|
299
303
|
- README.md
|
300
304
|
- Rakefile
|
305
|
+
- app/assets/images/maquina/.keep
|
301
306
|
- app/assets/images/maquina/maquina.svg
|
302
307
|
- app/assets/javascripts/maquina/application.js
|
303
308
|
- app/assets/javascripts/maquina/controllers/alert_controller.js
|
@@ -311,6 +316,7 @@ files:
|
|
311
316
|
- app/assets/javascripts/maquina/controllers/submit_form_controller.js
|
312
317
|
- app/assets/stylesheets/maquina/application.css
|
313
318
|
- app/assets/stylesheets/maquina/application.tailwind.css
|
319
|
+
- app/controllers/concerns/.keep
|
314
320
|
- app/controllers/concerns/maquina/authenticate.rb
|
315
321
|
- app/controllers/concerns/maquina/create.rb
|
316
322
|
- app/controllers/concerns/maquina/destroy.rb
|
@@ -334,6 +340,7 @@ files:
|
|
334
340
|
- app/jobs/maquina/application_job.rb
|
335
341
|
- app/mailers/maquina/application_mailer.rb
|
336
342
|
- app/mailers/maquina/user_notifications_mailer.rb
|
343
|
+
- app/models/concerns/.keep
|
337
344
|
- app/models/concerns/maquina/authenticate_by.rb
|
338
345
|
- app/models/concerns/maquina/blockeable.rb
|
339
346
|
- app/models/concerns/maquina/multifactor.rb
|
@@ -343,6 +350,8 @@ files:
|
|
343
350
|
- app/models/maquina/application_record.rb
|
344
351
|
- app/models/maquina/current.rb
|
345
352
|
- app/models/maquina/invitation.rb
|
353
|
+
- app/models/maquina/membership.rb
|
354
|
+
- app/models/maquina/organization.rb
|
346
355
|
- app/models/maquina/plan.rb
|
347
356
|
- app/models/maquina/used_password.rb
|
348
357
|
- app/models/maquina/user.rb
|
@@ -399,8 +408,7 @@ files:
|
|
399
408
|
- app/views/maquina/unauthorized/401.html.erb
|
400
409
|
- app/views/maquina/user_notifications_mailer/invitation_email.html.erb
|
401
410
|
- app/views/maquina/user_notifications_mailer/invitation_email.text.erb
|
402
|
-
- config/
|
403
|
-
- config/initializers/importmap.rb
|
411
|
+
- config/importmap.rb
|
404
412
|
- config/initializers/money.rb
|
405
413
|
- config/initializers/pagy.rb
|
406
414
|
- config/locales/flash.en.yml
|
@@ -415,18 +423,23 @@ files:
|
|
415
423
|
- db/migrate/20221113020108_create_maquina_used_passwords.rb
|
416
424
|
- db/migrate/20221115223414_create_maquina_active_sessions.rb
|
417
425
|
- db/migrate/20230201203922_create_maquina_invitations.rb
|
426
|
+
- db/migrate/20230829183530_create_maquina_organizations.rb
|
427
|
+
- db/migrate/20230829192656_create_maquina_memberships.rb
|
418
428
|
- db/schema.rb
|
419
429
|
- lib/generators/maquina/install_generator.rb
|
420
430
|
- lib/generators/maquina/install_templates/install_templates_generator.rb
|
431
|
+
- lib/generators/maquina/tailwind_config/USAGE
|
421
432
|
- lib/generators/maquina/tailwind_config/tailwind_config_generator.rb
|
422
|
-
- lib/generators/maquina/tailwind_config/templates/app/assets/
|
433
|
+
- lib/generators/maquina/tailwind_config/templates/app/assets/stylesheets/maquina.css
|
434
|
+
- lib/generators/maquina/tailwind_config/templates/lib/generators/tailwind_config/tailwind_config_generator.rb.tt
|
435
|
+
- lib/generators/maquina/tailwind_config/templates/lib/generators/tailwind_config/templates/config/tailwind.config.js.tt
|
436
|
+
- lib/generators/maquina/tailwind_config/templates/lib/tasks/tailwind.rake.tt
|
423
437
|
- lib/generators/maquina/templates/config/initializers/maquina.rb
|
424
438
|
- lib/maquina.rb
|
425
439
|
- lib/maquina/engine.rb
|
426
440
|
- lib/maquina/version.rb
|
427
441
|
- lib/tasks/install.rake
|
428
442
|
- lib/tasks/maquina_tasks.rake
|
429
|
-
- lib/tasks/tailwind.rake
|
430
443
|
homepage: https://mariochavez.io
|
431
444
|
licenses:
|
432
445
|
- MIT
|
@@ -449,7 +462,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
449
462
|
- !ruby/object:Gem::Version
|
450
463
|
version: '0'
|
451
464
|
requirements: []
|
452
|
-
rubygems_version: 3.4.
|
465
|
+
rubygems_version: 3.4.19
|
453
466
|
signing_key:
|
454
467
|
specification_version: 4
|
455
468
|
summary: Rails engine for building Rails applications.
|