pg_rails 7.6.34 → 7.6.35

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 8275648df93248ebda5f17d4b05ebbfb78bc465e1a79287229523135ddaf3954
4
- data.tar.gz: cf6723fbdc3fb9c432e3be09eb1b8fcd1607a26fe3e9253283605c10660d0f30
3
+ metadata.gz: b2749a5b4bfd158279a0e768b5a8e379302b2c71d0ace5e6162a2ad1eef01adc
4
+ data.tar.gz: 649a2ab01df77e08404832d84b17ae66fd64e383343a165e2c83d6856dd93467
5
5
  SHA512:
6
- metadata.gz: 63b38d4ee27e7688bfb1138fc02bf578b62b692d4efbc80b0fdc129d0868f98fb6f9c4bde061110e0f1136fea26f8c890051bd0c876983dee5c3ada07309e43e
7
- data.tar.gz: 405c40bce987d0963295515b8c5803dc4f146a71f518b7862bc6f2b00cac3657e7a9fcd78b24101683788ab82a039ba8f509115cdaad4fb8023ae1340519164e
6
+ metadata.gz: 8b5a1340887f5c9be83055c40e2316741176aea1810fc28dfe77f3475cefebb557e07f6de6f2e081517fafc6d53a6f14106e9145101d8316b2b91421f114fdf3
7
+ data.tar.gz: 4b3974156468841816dddefa932d7f132448f3e3218e9a41f2911f646361e74bd4c7ed4a2bf6cd98e57cf6dc11f7383f2f98eec9d5107ed4dfe3213f306b1270
@@ -53,7 +53,7 @@ module PgAssociable
53
53
  reflect = associacion_for(atributo)
54
54
  fkid = object.send(reflect.foreign_key)
55
55
  if fkid
56
- # FIXME: write some tests
56
+ # Include the actual value
57
57
  collection = collection.or(klass.where(id: fkid))
58
58
  end
59
59
 
@@ -75,6 +75,7 @@ module PgAssociable
75
75
  options.deep_merge!({ wrapper_html: { data: { controller: 'asociable',
76
76
  'asociable-modal-outlet': '.modal' } } })
77
77
  options[:as] = 'pg_associable'
78
+ options[:collection] = []
78
79
 
79
80
  association atributo, options
80
81
  end
@@ -26,16 +26,6 @@ module Users
26
26
  end
27
27
  end
28
28
 
29
- before_action do
30
- if action_name.in? %w[index]
31
- @container_class = 'container border p-0 my-3'
32
- @container_style = 'max-width: 50em; xborder-left: 1px solid grey'
33
- elsif action_name.in? %w[edit update]
34
- @container_class = 'container border pb-3 my-3'
35
- @container_style = 'max-width: 50em; xborder-left: 1px solid grey'
36
- end
37
- end
38
-
39
29
  def user_root
40
30
  scope = policy_scope(Account)
41
31
  if scope.count == 1
@@ -18,8 +18,6 @@ module Users
18
18
  add_breadcrumb UserAccount.new.decorate.submit_default_value
19
19
 
20
20
  @no_main_frame = true
21
- @container_class = 'container border pb-3 my-3'
22
- @container_style = 'max-width: 50em; xborder-left: 1px solid grey'
23
21
  end
24
22
 
25
23
  def new
@@ -228,6 +228,11 @@ module PgEngine
228
228
 
229
229
  # TODO: default sort
230
230
 
231
+ # include all values that are present in the DB
232
+ # TODO: test
233
+ existing_value = clase_asociacion.where(id: @clase_modelo.pluck(sin_sufijo(campo)).uniq)
234
+
235
+ scope = scope.or(existing_value)
231
236
  map = scope.map { |o| [o.to_s, o.id] }
232
237
 
233
238
  content_tag :div, class: 'col-auto' do
@@ -32,6 +32,12 @@ class PgFormBuilder < SimpleForm::FormBuilder
32
32
  super
33
33
  end
34
34
 
35
+ # :nocov:
36
+ def fetch_association_collection(_reflection, _options)
37
+ raise PgEngine::Error, 'collection option must be passed'
38
+ end
39
+ # :nocov:
40
+
35
41
  def field(attribute_name, options = {}, &)
36
42
  model = convert_to_model(object)
37
43
 
@@ -29,14 +29,25 @@
29
29
  #
30
30
 
31
31
  class User < ApplicationRecord
32
+ # Places where the default_scope applies:
33
+ # _ v en los pg_associable inputs
34
+ # _ v en los select de filtros de listados
35
+ # O en los preload e includes de listados
36
+ # O en los get de belongs_to
32
37
  default_scope lambda {
33
38
  if Current.namespace == :tenant
34
39
  if ActsAsTenant.unscoped?
35
40
  all
36
41
  else
37
- ids = Current.account.user_accounts.ua_active.pluck(:user_id)
38
- # ids = ids.push(Current.user.id) ?
39
- where(id: ids)
42
+ ids = Current.account.user_accounts.pluck(:user_id)
43
+
44
+ # Es importante no hacer:
45
+ # where(id: ids)
46
+ # Ya que eso supone el riesgo de ser sobreescrita, por ejemplo
47
+ # en el getter de un belongs_to
48
+ # rubocop:disable Rails/WhereEquals
49
+ where('users.id IN (?)', ids)
50
+ # rubocop:enable Rails/WhereEquals
40
51
  end
41
52
  else
42
53
  all
@@ -39,19 +39,37 @@ class UserAccount < ApplicationRecord
39
39
 
40
40
  after_destroy :cleanup_invitation
41
41
  def cleanup_invitation
42
- usr = User.unscoped.find(user_id)
43
- return unless usr.invited_to_sign_up? && !usr.confirmed?
44
- return if usr.destroy
45
- # :nocov:
42
+ return unless app_invitation_pending?
43
+
44
+ # unscoped: necesario porque ya la UserAccount fue borrada
45
+ # entonces el User quedaría por fuera de la default_scope
46
+ return if User.unscoped.find(user_id).destroy
46
47
 
48
+ # :nocov:
47
49
  pg_err 'User couldnt be deleted on invitation cleanup'
48
50
  # :nocov:
49
51
  end
52
+
53
+ # The user was invited to the platform and didn't
54
+ # confirm yet
55
+ def app_invitation_pending?
56
+ # usr = User.find(user_id)
57
+
58
+ # invited_to_sign_up? devise_invitable method that
59
+ # indicates if the user was created by invitation
60
+ user.invited_to_sign_up? && !user.confirmed?
61
+ end
62
+
50
63
  # El problema está en el joins(:user), ya que la default scope de user está scopeada dentro
51
64
  # del current_tenant entonces vuelve sobre la tabla user_accounts y bardea
52
65
  #
53
66
  # Tengo que escribir el user joins a mano porque de lo contrario sumaría la default_scope de
54
67
  # User, que a su vez joinea con user_accounts
68
+ #
69
+ # 07-03-2025
70
+ # esto ya no es así, la default scope de User no joinea más con user_accounts
71
+ # FIXME: ver si se podría hacer el joins(:user) normalmente y quitar el unscoped
72
+ #
55
73
  USER_JOINS = 'INNER JOIN users ON users.id = user_accounts.user_id'
56
74
  scope :kept, -> { joins(USER_JOINS, :account).merge(Account.kept).merge(User.unscoped.kept) }
57
75
 
@@ -41,7 +41,8 @@ class UserAccountPolicy < ApplicationPolicy
41
41
  end
42
42
 
43
43
  def destroy?
44
- Current.namespace == :admin || (user_is_account_owner? && !record.profiles.account__owner?)
44
+ Current.namespace == :admin ||
45
+ (user_is_account_owner? && !record.profiles.account__owner? && record.app_invitation_pending?)
45
46
  end
46
47
 
47
48
  def show?
@@ -20,9 +20,10 @@ class UserPolicy < ApplicationPolicy
20
20
  # acceso_total? && !record.readonly?
21
21
  # end
22
22
 
23
- # def puede_crear?
24
- # acceso_total? || user.asesor?
25
- # end
23
+ def puede_crear?
24
+ # acceso_total? || user.asesor?
25
+ true
26
+ end
26
27
 
27
28
  # def puede_borrar?
28
29
  # acceso_total? && !record.readonly?
@@ -8,15 +8,16 @@ h3 = t('pg_engine.base.index.bulk_edit.title', model: @clase_modelo)
8
8
  .col-auto
9
9
  p.text-center.fw-bold
10
10
  = t('pg_engine.base.index.bulk_edit.count', model: @clase_modelo, count: @collection.count)
11
- table.table style="min-width: 20em; max-width: 40em"
12
- - @collection.each do |model|
13
- tr
14
- td style="width: 1em"
15
- .form-check.xform-check-lg
16
- = check_box_tag 'ids[]', model.to_key, true, class: 'form-check-input'
17
- td.column-truncate-90 data-bs-title=model.to_s data-controller="tooltip"
18
- = link_to model, model.decorate.object_url, target: :_blank, rel: :noopener
19
- / = hidden_field_tag 'ids[]', model.to_key
11
+ .table-responsive
12
+ table.table style="min-width: 20em; max-width: 40em"
13
+ - @collection.each do |model|
14
+ tr
15
+ td style="width: 1em"
16
+ .form-check.xform-check-lg
17
+ = check_box_tag 'ids[]', model.to_key, true, class: 'form-check-input'
18
+ td.column-truncate-90 data-bs-title=model.to_s data-controller="tooltip"
19
+ = link_to model, model.decorate.object_url, target: :_blank, rel: :noopener
20
+ / = hidden_field_tag 'ids[]', model.to_key
20
21
  .col.border-start
21
22
  = render BulkEditComponent.new(@clase_modelo, params:, form: f)
22
23
 
@@ -0,0 +1,4 @@
1
+ - content_for(:container_class) { 'container border pb-3 my-3' }
2
+ - content_for(:container_style) { 'max-width: 50em; xborder-left: 1px solid grey' }
3
+
4
+ = render template: 'pg_engine/base/edit'
@@ -0,0 +1,4 @@
1
+ - content_for(:container_class) { 'container border p-0 my-3' }
2
+ - content_for(:container_style) { 'max-width: 50em; xborder-left: 1px solid grey' }
3
+
4
+ = render template: 'pg_engine/base/index'
@@ -75,19 +75,19 @@ module PgEngine
75
75
  end
76
76
  end
77
77
 
78
- initializer 'byebug_bullet' do
78
+ initializer 'bye_bug_bullet' do
79
79
  if Rails.env.local?
80
80
  # :nocov:
81
81
  if ENV['RUBY_DEBUG_OPEN']
82
82
  require 'byebug/core'
83
83
  begin
84
84
  Byebug.start_server 'localhost', ENV.fetch('BYEBUG_SERVER_PORT', 8989).to_i
85
- if ENV.fetch('SLEEP_AFTER_BYEBUG', false)
86
- puts 'waiting 3 secs after starting byebug server for connections'
85
+ if ENV.fetch('SLEEP_AFTER_BYE_BUG', false)
86
+ puts 'waiting 3 secs after starting bye bug server for connections'
87
87
  sleep 3
88
88
  end
89
89
  rescue Errno::EADDRINUSE
90
- Rails.logger.debug 'Byebug server already running'
90
+ Rails.logger.debug 'Bye bug server already running'
91
91
  end
92
92
  end
93
93
  # :nocov:
@@ -15,8 +15,6 @@ def pg_err(*args)
15
15
  # :nocov:
16
16
  end
17
17
 
18
- byebug if ENV.fetch('BYEBUG_ERRORS', false) # rubocop:disable Lint/Debugger
19
-
20
18
  pg_log(:error, *args)
21
19
  end
22
20
 
@@ -77,7 +77,13 @@ FactoryBot.define do
77
77
 
78
78
  trait :guest do
79
79
  after(:create) do |model|
80
- model.user_accounts.create!(profiles: [])
80
+ model.user_accounts.create(profiles: [])
81
+ end
82
+ end
83
+
84
+ trait :disabled do
85
+ after(:create) do |model|
86
+ model.user_accounts.update_all(membership_status: :ms_disabled)
81
87
  end
82
88
  end
83
89
  end
@@ -70,4 +70,73 @@ describe PgFormBuilder do
70
70
  it { expect(subject).to eq 'La fecha' }
71
71
  end
72
72
  end
73
+
74
+ describe '#collection_pc' do
75
+ subject do
76
+ Current.namespace = :tenant
77
+
78
+ instancia.collection_pc(:creado_por, {})
79
+ end
80
+
81
+ context 'when user is foreign' do
82
+ let!(:user) { create :user }
83
+
84
+ context 'when category has not an actual value' do
85
+ let(:categoria) { create :categoria_de_cosa, creado_por: nil }
86
+
87
+ it do
88
+ expect(subject[0]).to eq []
89
+ end
90
+ end
91
+
92
+ context 'when category has an actual value' do
93
+ let(:categoria) { create :categoria_de_cosa, creado_por: user }
94
+
95
+ it 'doent show even when it is the actual value' do
96
+ expect(categoria.reload.creado_por).to eq user
97
+ expect(subject[0]).to eq []
98
+ end
99
+ end
100
+ end
101
+
102
+ context 'when its active' do
103
+ let!(:user) { create :user, :guest }
104
+
105
+ context 'when category has not an actual value' do
106
+ let(:categoria) { create :categoria_de_cosa, creado_por: nil }
107
+
108
+ it do
109
+ expect(subject[0]).to eq [user]
110
+ end
111
+ end
112
+
113
+ context 'when category has an actual value' do
114
+ let(:categoria) { create :categoria_de_cosa, creado_por: user }
115
+
116
+ it do
117
+ expect(subject[0]).to include user
118
+ end
119
+ end
120
+ end
121
+
122
+ context 'when its disabled' do
123
+ let!(:user) { create :user, :guest, :disabled }
124
+
125
+ context 'when category has not an actual value' do
126
+ let(:categoria) { create :categoria_de_cosa, creado_por: nil }
127
+
128
+ it do
129
+ expect(subject[0]).to eq []
130
+ end
131
+ end
132
+
133
+ context 'when category has an actual value' do
134
+ let(:categoria) { create :categoria_de_cosa, creado_por: user }
135
+
136
+ it do
137
+ expect(subject[0]).to include user
138
+ end
139
+ end
140
+ end
141
+ end
73
142
  end
@@ -192,7 +192,8 @@ describe 'invite users to the platform and to an account #' do
192
192
  end
193
193
 
194
194
  it 'removes the UserAccount but not the User' do
195
- expect { subject }.to change { UserAccount.unscoped.count }.by(-1).and(not_change(User.unscoped, :count))
195
+ subject
196
+ expect(response).to have_http_status(:unauthorized)
196
197
  end
197
198
  end
198
199
 
@@ -84,7 +84,8 @@ describe 'user accounts', :tpath_req do
84
84
  end
85
85
 
86
86
  it do
87
- expect { subject }.to change(UserAccount.unscoped, :count).by(-1)
87
+ subject
88
+ expect(response).to have_http_status(:unauthorized)
88
89
  end
89
90
  end
90
91
  end
@@ -2,7 +2,7 @@
2
2
 
3
3
  <h3>
4
4
  <%= resource.invited_by %>
5
- te invitó a su cuenta en ProcuraBien
5
+ te invitó a su cuenta en <%= PgEngine.site_brand.name %>
6
6
  </h3>
7
7
  <% if User.require_password_on_accepting %>
8
8
  <p>
@@ -1,9 +1,12 @@
1
+ <% content_for(:container_class) { 'container border pb-3 my-3' } %>
2
+ <% content_for(:container_style) { 'max-width: 50em; xborder-left: 1px solid grey' } %>
3
+
1
4
  <h2><%= UserAccount.new.decorate.submit_default_value %></h2>
2
5
 
3
6
  <div style="max-width: 40em" data-controller="pg_form">
4
7
  <%= pg_form_for(resource, as: resource_name, url: invitation_path(resource_name), html: { method: :post }) do |f| %>
5
8
  <div class="form-inputs">
6
- <%= f.input :email, hint: 'Si la persona aún no tiene cuenta en ProcuraBien, se le enviará una invitación para que se registre' %>
9
+ <%= f.input :email, hint: "Si la persona aún no tiene cuenta en #{PgEngine.site_brand.name}, se le enviará una invitación para que se registre" %>
7
10
  </div>
8
11
  <%= f.fields_for :user_accounts do |nf| %>
9
12
  <%= render partial: 'tenant/user_accounts/fields', locals: { f: nf } %>
@@ -1,6 +1,6 @@
1
1
  - content_for :content do
2
- - klass = modal_targeted? ? '' : (@container_class || 'container-fluid')
3
- div class="pt-3 #{klass}" style=@container_style
2
+ - klass = modal_targeted? ? '' : (yield(:container_class) || 'container-fluid')
3
+ div class="pt-3 #{klass}" style=yield(:container_style)
4
4
  = content_for?(:containerized_content) ? yield(:containerized_content) : yield
5
5
 
6
6
  = render template: 'layouts/pg_layout/base'
@@ -2,6 +2,6 @@
2
2
 
3
3
  # :nocov:
4
4
  module PgRails
5
- VERSION = '7.6.34'
5
+ VERSION = '7.6.35'
6
6
  end
7
7
  # :nocov:
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: pg_rails
3
3
  version: !ruby/object:Gem::Version
4
- version: 7.6.34
4
+ version: 7.6.35
5
5
  platform: ruby
6
6
  authors:
7
7
  - Martín Rosso
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2025-03-06 00:00:00.000000000 Z
11
+ date: 2025-03-11 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails
@@ -840,6 +840,8 @@ files:
840
840
  - pg_engine/app/views/tenant/user_accounts/_form.html.slim
841
841
  - pg_engine/app/views/tenant/user_accounts/show.html.slim
842
842
  - pg_engine/app/views/users/accounts/_form.html.slim
843
+ - pg_engine/app/views/users/accounts/edit.html.slim
844
+ - pg_engine/app/views/users/accounts/index.html.slim
843
845
  - pg_engine/app/views/users/accounts/show.html.slim
844
846
  - pg_engine/config/initializers/action_controller.rb
845
847
  - pg_engine/config/initializers/action_mailer.rb