decidim-direct_verifications 0.22 → 1.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (50) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +33 -3
  3. data/app/commands/decidim/direct_verifications/verification/create_import.rb +59 -0
  4. data/app/controllers/decidim/direct_verifications/verification/admin/authorizations_controller.rb +42 -0
  5. data/app/controllers/decidim/direct_verifications/verification/admin/direct_verifications_controller.rb +22 -20
  6. data/app/controllers/decidim/direct_verifications/verification/admin/imports_controller.rb +55 -0
  7. data/app/forms/decidim/direct_verifications/registration_form.rb +8 -0
  8. data/app/forms/decidim/direct_verifications/verification/create_import_form.rb +43 -0
  9. data/app/jobs/decidim/direct_verifications/authorize_users_job.rb +36 -0
  10. data/app/jobs/decidim/direct_verifications/base_import_job.rb +54 -0
  11. data/app/jobs/decidim/direct_verifications/register_users_job.rb +20 -0
  12. data/app/jobs/decidim/direct_verifications/revoke_users_job.rb +18 -0
  13. data/app/mailers/decidim/direct_verifications/import_mailer.rb +27 -0
  14. data/app/mailers/decidim/direct_verifications/stats.rb +23 -0
  15. data/app/packs/entrypoints/decidim_direct_verifications.js +4 -0
  16. data/app/packs/entrypoints/decidim_direct_verifications.scss +1 -0
  17. data/app/packs/src/decidim/direct_verifications/admin/checkboxes.js +7 -0
  18. data/app/packs/stylesheets/decidim/direct_verifications/admin/authorizations.scss +17 -0
  19. data/app/views/decidim/direct_verifications/import_mailer/finished_processing.html.erb +7 -0
  20. data/app/views/decidim/direct_verifications/import_mailer/finished_processing.text.erb +7 -0
  21. data/app/views/decidim/direct_verifications/verification/admin/authorizations/index.html.erb +43 -0
  22. data/app/views/decidim/direct_verifications/verification/admin/direct_verifications/index.html.erb +5 -4
  23. data/app/views/decidim/direct_verifications/verification/admin/imports/new.html.erb +50 -0
  24. data/config/assets.rb +24 -0
  25. data/config/initializers/mail_previews.rb +5 -0
  26. data/config/locales/ca.yml +47 -33
  27. data/config/locales/cs.yml +84 -0
  28. data/config/locales/en.yml +44 -13
  29. data/config/locales/es.yml +45 -31
  30. data/config/locales/fr.yml +84 -0
  31. data/lib/decidim/direct_verifications/authorize_user.rb +64 -0
  32. data/lib/decidim/direct_verifications/instrumenter.rb +58 -0
  33. data/lib/decidim/direct_verifications/parsers/base_parser.rb +37 -0
  34. data/lib/decidim/direct_verifications/parsers/metadata_parser.rb +48 -0
  35. data/lib/decidim/direct_verifications/parsers/name_parser.rb +40 -0
  36. data/lib/decidim/direct_verifications/parsers.rb +11 -0
  37. data/lib/decidim/direct_verifications/register_user.rb +54 -0
  38. data/lib/decidim/direct_verifications/revoke_user.rb +45 -0
  39. data/lib/decidim/direct_verifications/tests/factories.rb +11 -0
  40. data/lib/decidim/direct_verifications/tests/verification_controller_examples.rb +13 -8
  41. data/lib/decidim/direct_verifications/user_processor.rb +17 -101
  42. data/lib/decidim/direct_verifications/user_stats.rb +5 -5
  43. data/lib/decidim/direct_verifications/verification/admin_engine.rb +4 -2
  44. data/lib/decidim/direct_verifications/version.rb +3 -3
  45. data/lib/decidim/direct_verifications.rb +24 -1
  46. data/package.json +192 -0
  47. metadata +41 -11
  48. data/app/assets/config/direct_verifications_admin_manifest.js +0 -1
  49. data/app/assets/javascripts/decidim/direct_verifications/verification/admin/direct_verifications_admin.js.es6 +0 -7
  50. data/lib/decidim/direct_verifications/config.rb +0 -23
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 8a3a36032cc453d0d386579125ace610fbc73e85a975196b56ae84c3f10a2296
4
- data.tar.gz: d20c11a81153e2c9fe79b0663d5b9cd7f077133714d8cf25a872ee1f70ca6741
3
+ metadata.gz: e42a469a3e54d28a703c6565abdb73aa70d33c540882e8737c0e92592d18d238
4
+ data.tar.gz: 1c2ff4b72713ad26ba30b350efbcc31840fa42aac1f171faa32f0b1b64596d22
5
5
  SHA512:
6
- metadata.gz: b3201103a89ca52e19fbd493018e45727d81d3b7d626eca0a5735253bc4ee21b5fc3260038cca70c405aed30f4556c807ae35b3b1ec00bc6157acc3f0c16cc33
7
- data.tar.gz: 170a4e48d8ecadd8abc262626669ed9b8820d85804a0a48350c1ea2a2dc7f2de4a87f6833f71ff23fe1b880ba817b81f8f4823059824bfcce9703d9b45720631
6
+ metadata.gz: 1514cdfd920925b28b1d89e4c615a4ce0a97ceca4a85fcffab0706e6b740e0ae11541c04ce77a992da7aa21ef6b289795abf8cd3ccb950f7c1613531b3f57460
7
+ data.tar.gz: 618916a01ea8ac5fb19188e1b10d15c56a40ed6648da422d5d48c16a93feb8a2ff1f5507ac88f62a08c0651a704fb5c2a5efa502d887b2df07b6eb1bca8f66a4
data/README.md CHANGED
@@ -1,8 +1,10 @@
1
1
  # Decidim::DirectVerifications
2
2
 
3
- ![[CI] Test](https://github.com/Platoniq/decidim-verifications-direct_verifications/workflows/%5BCI%5D%20Test/badge.svg)
3
+ [![Test](https://github.com/Platoniq/decidim-verifications-direct_verifications/actions/workflows/test.yml/badge.svg)](https://github.com/Platoniq/decidim-verifications-direct_verifications/actions/workflows/test.yml)
4
4
  [![Maintainability](https://api.codeclimate.com/v1/badges/2195deb4de6c6354a6bc/maintainability)](https://codeclimate.com/github/Platoniq/decidim-verifications-direct_verifications/maintainability)
5
- [![codecov](https://codecov.io/gh/Platoniq/decidim-verifications-direct_verifications/branch/master/graph/badge.svg?token=FR1zkV71S2)](https://codecov.io/gh/Platoniq/decidim-verifications-direct_verifications)
5
+ [![codecov](https://codecov.io/gh/Platoniq/decidim-verifications-direct_verifications/branch/main/graph/badge.svg?token=FR1zkV71S2)](https://codecov.io/gh/Platoniq/decidim-verifications-direct_verifications)
6
+
7
+
6
8
 
7
9
  A [Decidim](https://github.com/decidim/decidim) that provides a verification method called `Direct verification`. Works only on the admin side, final users do not intervene in the verification process.
8
10
 
@@ -36,6 +38,23 @@ With the detected list of emails admin have different options available:
36
38
  3. Revoke the authorization for the list of users using any verification method available.
37
39
  4. Check the status of the users in order to know if they are verified or registered.
38
40
 
41
+ ### Metadata mode
42
+
43
+ This mode provides extra capabilities over the default processing:
44
+
45
+ * Reads CSV format with header (copy and paste it from your spreadsheet)
46
+ * Stores all columns except the email as authorization metadata
47
+
48
+ This enables querying the authorization metadata however fits you best.
49
+
50
+ To enable it create a new initializer, for instance `config/initializers/decidim_direct_verifications.rb` with the following contents
51
+
52
+ ```ruby
53
+ Decidim::DirectVerifications.configure do |config|
54
+ config.input_parser = :metadata_parser
55
+ end
56
+ ```
57
+
39
58
  ## Installation
40
59
 
41
60
  Add this line to your application's Gemfile:
@@ -50,6 +69,14 @@ And then execute:
50
69
  bundle
51
70
  ```
52
71
 
72
+ Depending on your Decidim version, you might want to specify the version to ensure compatibility:
73
+
74
+ | Direct Verifications version | Compatible Decidim versions |
75
+ |---|---|
76
+ | 1.1 | >= 0.25.x |
77
+ | 1.0 | >= 0.23.x |
78
+ | 0.22.x | 0.22.x |
79
+
53
80
  ## Using additional verification methods
54
81
 
55
82
  You can manage other verification methods (or workflow) a part from `Direct verification`. You need to configure it in a new file in the `config/initializers` folder.
@@ -70,7 +97,10 @@ end
70
97
 
71
98
  # We need to tell the plugin to handle this method in addition to the default "Direct verification". Any registered workflow is valid.
72
99
  Decidim::DirectVerifications.configure do |config|
73
- config.manage_workflows = %w(direct_verifications_managers)
100
+ config.manage_workflows = %w(direct_verifications direct_verifications_managers)
101
+
102
+ # change the to the metadata_parser if you want it
103
+ # config.input_parser = :metadata_parser
74
104
  end
75
105
 
76
106
  ```
@@ -0,0 +1,59 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module DirectVerifications
5
+ module Verification
6
+ class CreateImport < Rectify::Command
7
+ def initialize(form)
8
+ @form = form
9
+ @file = form.file
10
+ @organization = form.organization
11
+ @user = form.user
12
+ @action = form.action
13
+ end
14
+
15
+ def call
16
+ return broadcast(:invalid) unless form.valid?
17
+
18
+ case action
19
+ when :register
20
+ register_users_async(remove_file: true)
21
+ when :authorize
22
+ authorize_users_async(remove_file: true)
23
+ when :register_and_authorize
24
+ register_users_async
25
+ authorize_users_async(remove_file: true)
26
+ when :revoke
27
+ revoke_users_async(remove_file: true)
28
+ end
29
+
30
+ broadcast(:ok)
31
+ end
32
+
33
+ private
34
+
35
+ attr_reader :form, :file, :organization, :user, :action
36
+
37
+ def register_users_async(options = {})
38
+ RegisterUsersJob.perform_later(blob.id, organization, user, form.authorization_handler, options)
39
+ end
40
+
41
+ def revoke_users_async(options = {})
42
+ RevokeUsersJob.perform_later(blob.id, organization, user, form.authorization_handler, options)
43
+ end
44
+
45
+ def authorize_users_async(options = {})
46
+ AuthorizeUsersJob.perform_later(blob.id, organization, user, form.authorization_handler, options)
47
+ end
48
+
49
+ def blob
50
+ @blob ||= ActiveStorage::Blob.create_and_upload!(io: file, filename: secure_name)
51
+ end
52
+
53
+ def secure_name
54
+ @secure_name ||= "#{SecureRandom.uuid}#{File.extname(file.tempfile)}"
55
+ end
56
+ end
57
+ end
58
+ end
59
+ end
@@ -0,0 +1,42 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module DirectVerifications
5
+ module Verification
6
+ module Admin
7
+ class AuthorizationsController < Decidim::Admin::ApplicationController
8
+ layout "decidim/admin/users"
9
+
10
+ def index
11
+ enforce_permission_to :index, :authorization
12
+ @authorizations = collection.includes(:user)
13
+ .page(params[:page])
14
+ .per(15)
15
+ end
16
+
17
+ def destroy
18
+ if authorization.destroy
19
+ flash[:notice] = "successfully"
20
+ redirect_to authorizations_path
21
+ end
22
+ end
23
+
24
+ private
25
+
26
+ def collection
27
+ # Decidim::Verifications::Authorizations Query
28
+ Decidim::Verifications::Authorizations.new(
29
+ organization: current_organization,
30
+ name: "direct_verifications",
31
+ granted: true
32
+ ).query
33
+ end
34
+
35
+ def authorization
36
+ @authorization ||= collection.find_by(id: params[:id])
37
+ end
38
+ end
39
+ end
40
+ end
41
+ end
42
+ end
@@ -17,30 +17,40 @@ module Decidim
17
17
  def create
18
18
  enforce_permission_to :create, :authorization
19
19
 
20
- @userslist = params[:userlist]
21
- @processor = UserProcessor.new(current_organization, current_user, session)
22
- @processor.emails = extract_emails_to_hash @userslist
20
+ @userslist = params[:userslist]
21
+
22
+ @processor = UserProcessor.new(current_organization, current_user, session, instrumenter)
23
+ @processor.emails = parser_class.new(@userslist).to_h
23
24
  @processor.authorization_handler = current_authorization_handler
25
+
24
26
  @stats = UserStats.new(current_organization)
25
27
  @stats.authorization_handler = @processor.authorization_handler
28
+
26
29
  register_users
27
30
  authorize_users
28
31
  revoke_users
29
32
 
30
33
  render(action: :index) && return if show_users_info
31
34
 
35
+ redirect_to direct_verifications_path
36
+ rescue InputParserError => e
37
+ flash[:error] = e.message
32
38
  redirect_to direct_verifications_path
33
39
  end
34
40
 
35
41
  private
36
42
 
43
+ def instrumenter
44
+ @instrumenter ||= Instrumenter.new(current_user)
45
+ end
46
+
37
47
  def register_users
38
48
  return unless params[:register]
39
49
 
40
50
  @processor.register_users
41
51
  flash[:warning] = t(".registered", count: @processor.emails.count,
42
- registered: @processor.processed[:registered].count,
43
- errors: @processor.errors[:registered].count)
52
+ registered: instrumenter.processed_count(:registered),
53
+ errors: instrumenter.errors_count(:registered))
44
54
  end
45
55
 
46
56
  def authorize_users
@@ -49,8 +59,8 @@ module Decidim
49
59
  @processor.authorize_users
50
60
  flash[:notice] = t(".authorized", handler: t("#{@processor.authorization_handler}.name", scope: "decidim.authorization_handlers"),
51
61
  count: @processor.emails.count,
52
- authorized: @processor.processed[:authorized].count,
53
- errors: @processor.errors[:authorized].count)
62
+ authorized: instrumenter.processed_count(:authorized),
63
+ errors: instrumenter.errors_count(:authorized))
54
64
  end
55
65
 
56
66
  def revoke_users
@@ -59,12 +69,12 @@ module Decidim
59
69
  @processor.revoke_users
60
70
  flash[:notice] = t(".revoked", handler: t("#{@processor.authorization_handler}.name", scope: "decidim.authorization_handlers"),
61
71
  count: @processor.emails.count,
62
- revoked: @processor.processed[:revoked].count,
63
- errors: @processor.errors[:revoked].count)
72
+ revoked: instrumenter.processed_count(:revoked),
73
+ errors: instrumenter.errors_count(:revoked))
64
74
  end
65
75
 
66
76
  def show_users_info
67
- return if params[:authorize]
77
+ return if params[:authorize].in? %w(in out)
68
78
 
69
79
  @stats.emails = @processor.emails.keys
70
80
  flash.now[:info] = t(".info", handler: t("#{@processor.authorization_handler}.name", scope: "decidim.authorization_handlers"),
@@ -75,16 +85,8 @@ module Decidim
75
85
  true
76
86
  end
77
87
 
78
- def extract_emails_to_hash(txt)
79
- reg = /([A-Z0-9+._-]+@[A-Z0-9._-]+\.[A-Z0-9_-]+)\b/i
80
- emails = {}
81
- txt.split(/[\r\n;,]/).each do |line|
82
- reg.match line do |m|
83
- n = line.split(m[0]).first
84
- emails[m[0]] = (n.presence || "").gsub(/[^[:print:]]|[\"\$\<\>\|\\]/, "").strip
85
- end
86
- end
87
- emails
88
+ def parser_class
89
+ Decidim::DirectVerifications.find_parser_class(Decidim::DirectVerifications.input_parser)
88
90
  end
89
91
 
90
92
  def authorization_handler(authorization_handler)
@@ -0,0 +1,55 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module DirectVerifications
5
+ module Verification
6
+ module Admin
7
+ class ImportsController < Decidim::Admin::ApplicationController
8
+ layout "decidim/admin/users"
9
+ helper_method :workflows, :current_authorization_handler
10
+
11
+ def new
12
+ enforce_permission_to :create, :authorization
13
+ @form = form(CreateImportForm).instance
14
+ end
15
+
16
+ def create
17
+ enforce_permission_to :create, :authorization
18
+
19
+ defaults = { organization: current_organization, user: current_user }
20
+ form = form(CreateImportForm).from_params(params.merge(defaults))
21
+
22
+ CreateImport.call(form) do
23
+ on(:ok) do
24
+ flash[:notice] = t(".success")
25
+ end
26
+
27
+ on(:invalid) do
28
+ flash[:alert] = t(".error")
29
+ end
30
+ end
31
+
32
+ redirect_to new_import_path
33
+ end
34
+
35
+ def workflows
36
+ workflows = configured_workflows & current_organization.available_authorizations.map.to_a
37
+ workflows.map do |workflow|
38
+ [t("#{workflow}.name", scope: "decidim.authorization_handlers"), workflow]
39
+ end
40
+ end
41
+
42
+ def configured_workflows
43
+ return Decidim::DirectVerifications.config.manage_workflows if Decidim::DirectVerifications.config
44
+
45
+ ["direct_verifications"]
46
+ end
47
+
48
+ def current_authorization_handler
49
+ params[:authorization_handler]
50
+ end
51
+ end
52
+ end
53
+ end
54
+ end
55
+ end
@@ -0,0 +1,8 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module DirectVerifications
5
+ class RegistrationForm < OpenStruct
6
+ end
7
+ end
8
+ end
@@ -0,0 +1,43 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module DirectVerifications
5
+ module Verification
6
+ class CreateImportForm < Form
7
+ ACTIONS = {
8
+ "in" => :authorize,
9
+ "out" => :revoke,
10
+ "check" => :check
11
+ }.freeze
12
+
13
+ attribute :file
14
+ attribute :organization, Decidim::Organization
15
+ attribute :user, Decidim::User
16
+ attribute :authorize, String
17
+ attribute :register, Boolean
18
+ attribute :authorization_handler, String
19
+
20
+ validates :file, :organization, :user, :authorize, :authorization_handler, presence: true
21
+ validates :authorize, inclusion: { in: ACTIONS.keys }
22
+
23
+ validate :available_authorization_handler
24
+
25
+ def available_authorization_handler
26
+ return if authorization_handler.in?(organization.available_authorizations)
27
+
28
+ errors.add(:authorization_handler, :inclusion)
29
+ end
30
+
31
+ def action
32
+ if register && authorize == "in"
33
+ :register_and_authorize
34
+ elsif register
35
+ :register
36
+ else
37
+ ACTIONS[authorize]
38
+ end
39
+ end
40
+ end
41
+ end
42
+ end
43
+ end
@@ -0,0 +1,36 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "decidim/direct_verifications/instrumenter"
4
+
5
+ module Decidim
6
+ module DirectVerifications
7
+ class AuthorizeUsersJob < BaseImportJob
8
+ class NullSession; end
9
+
10
+ def process_users
11
+ Rails.logger.info "AuthorizeUsersJob: Authorizing #{emails.count} emails"
12
+ emails.each do |email, data|
13
+ Rails.logger.debug "AuthorizeUsersJob: Authorizing #{email}"
14
+ AuthorizeUser.new(
15
+ email,
16
+ data,
17
+ session,
18
+ organization,
19
+ instrumenter,
20
+ authorization_handler
21
+ ).call
22
+ end
23
+ end
24
+
25
+ def type
26
+ :authorized
27
+ end
28
+
29
+ private
30
+
31
+ def session
32
+ NullSession.new
33
+ end
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,54 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "decidim/direct_verifications/instrumenter"
4
+
5
+ module Decidim
6
+ module DirectVerifications
7
+ # This class implements the logic to import the user entries and sending an email notification
8
+ # with the result. The specifics to process the entries are meant to be implemented by
9
+ # subclasses which must implement the `#process_users` and `#type` methods.
10
+ class BaseImportJob < ApplicationJob
11
+ queue_as :default
12
+
13
+ def perform(blob_id, organization, current_user, authorization_handler, options = {})
14
+ @blob = ActiveStorage::Blob.find(blob_id)
15
+ @organization = organization
16
+ @current_user = current_user
17
+ @authorization_handler = authorization_handler
18
+
19
+ begin
20
+ @emails = Parsers::MetadataParser.new(userslist).to_h
21
+ @instrumenter = Instrumenter.new(current_user)
22
+
23
+ Rails.logger.info "BaseImportJob: Processing file #{@blob.filename}"
24
+ process_users
25
+ send_email_notification
26
+ rescue StandardError => e
27
+ Rails.logger.error "BaseImportJob Error: #{e.message} #{e.backtrace.filter { |f| f =~ /direct_verifications/ }}"
28
+ end
29
+ remove_file! if options.fetch(:remove_file, false)
30
+ end
31
+
32
+ private
33
+
34
+ attr_reader :blob, :emails, :organization, :current_user, :instrumenter, :authorization_handler
35
+
36
+ def userslist
37
+ @userslist ||= blob.download.force_encoding("UTF-8")
38
+ end
39
+
40
+ def send_email_notification
41
+ ImportMailer.finished_processing(
42
+ current_user,
43
+ instrumenter,
44
+ type,
45
+ authorization_handler
46
+ ).deliver_now
47
+ end
48
+
49
+ def remove_file!
50
+ blob.purge
51
+ end
52
+ end
53
+ end
54
+ end
@@ -0,0 +1,20 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "decidim/direct_verifications/instrumenter"
4
+
5
+ module Decidim
6
+ module DirectVerifications
7
+ class RegisterUsersJob < BaseImportJob
8
+ def process_users
9
+ Rails.logger.info "RegisterUsersJob: Registering #{emails.count} emails"
10
+ emails.each do |email, data|
11
+ RegisterUser.new(email, data, organization, current_user, instrumenter).call
12
+ end
13
+ end
14
+
15
+ def type
16
+ :registered
17
+ end
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,18 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module DirectVerifications
5
+ class RevokeUsersJob < BaseImportJob
6
+ def process_users
7
+ Rails.logger.info "RevokeUsersJob: Revoking #{emails.count} emails"
8
+ emails.each do |email, _name|
9
+ RevokeUser.new(email, organization, instrumenter, authorization_handler).call
10
+ end
11
+ end
12
+
13
+ def type
14
+ :revoked
15
+ end
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,27 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module DirectVerifications
5
+ class ImportMailer < Decidim::Admin::ApplicationMailer
6
+ include LocalisedMailer
7
+
8
+ layout "decidim/mailer"
9
+
10
+ I18N_SCOPE = "decidim.direct_verifications.verification.admin.imports.mailer"
11
+
12
+ def finished_processing(user, instrumenter, type, handler)
13
+ @stats = Stats.from(instrumenter, type)
14
+ @organization = user.organization
15
+ @i18n_key = "#{I18N_SCOPE}.#{type}"
16
+ @handler = handler
17
+
18
+ with_user(user) do
19
+ mail(
20
+ to: user.email,
21
+ subject: I18n.t("#{I18N_SCOPE}.subject")
22
+ )
23
+ end
24
+ end
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,23 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module DirectVerifications
5
+ class Stats
6
+ attr_reader :count, :successful, :errors
7
+
8
+ def self.from(instrumenter, type)
9
+ new(
10
+ count: instrumenter.emails_count(type),
11
+ successful: instrumenter.processed_count(type),
12
+ errors: instrumenter.errors_count(type)
13
+ )
14
+ end
15
+
16
+ def initialize(count:, successful:, errors:)
17
+ @count = count
18
+ @successful = successful
19
+ @errors = errors
20
+ end
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,4 @@
1
+ import "src/decidim/direct_verifications/admin/checkboxes.js"
2
+
3
+ // CSS
4
+ import "entrypoints/decidim_direct_verifications.scss";
@@ -0,0 +1 @@
1
+ @import "stylesheets/decidim/direct_verifications/admin/authorizations";
@@ -0,0 +1,7 @@
1
+ // = require_self
2
+
3
+ $(() => {
4
+ $('[type="checkbox"]#register').change(function () {
5
+ $(this).closest("label").find(".callout").toggleClass("hide", !$(this).prop("checked"))
6
+ })
7
+ })
@@ -0,0 +1,17 @@
1
+ @import "stylesheets/decidim/admin/utils/settings";
2
+
3
+ $code-color: $black;
4
+ $code-font-family: $font-family-monospace;
5
+ $code-font-weight: $global-weight-normal;
6
+ $code-background: $light-gray;
7
+ $code-border: 1px solid $medium-gray;
8
+ $code-padding: rem-calc(2 5 1);
9
+
10
+ .code {
11
+ background: $code-background;
12
+ color: $code-color;
13
+ font-family: $code-font-family;
14
+ font-weight: $code-font-weight;
15
+ border: $code-border;
16
+ padding: $code-padding;
17
+ }
@@ -0,0 +1,7 @@
1
+ <p><%= t(
2
+ @i18n_key,
3
+ count: @stats.count,
4
+ successful: @stats.successful,
5
+ errors: @stats.errors,
6
+ handler: @handler
7
+ ) %></p>
@@ -0,0 +1,7 @@
1
+ <%= t(
2
+ @i18n_key,
3
+ count: @stats.count,
4
+ successful: @stats.successful,
5
+ errors: @stats.errors,
6
+ handler: @handler
7
+ ) %>
@@ -0,0 +1,43 @@
1
+ <%= stylesheet_pack_tag "decidim_direct_verifications" %>
2
+
3
+ <div class="card">
4
+ <div class="card-divider">
5
+ <h2 class="card-title">
6
+ <%= t(".title") %>
7
+ <%= link_to t("admin.index.stats", scope: "decidim.direct_verifications.verification"), stats_path, class: "button tiny button--title" %>
8
+ <%= link_to t(".new_import"), direct_verifications_path, class: "button tiny button--title" %>
9
+ </h2>
10
+ </div>
11
+ <div class="card-section">
12
+ <div class="table-scroll">
13
+ <table class="table-list">
14
+ <thead>
15
+ <tr>
16
+ <th><%= t(".name") %></th>
17
+ <th><%= t(".metadata") %></th>
18
+ <th><%= t(".user_name") %></th>
19
+ <th><%= t(".created_at") %></th>
20
+ <th>&nbsp;</th>
21
+ </tr>
22
+ </thead>
23
+ <tbody>
24
+ <% @authorizations.each do |authorization| %>
25
+ <tr data-authorization-id="<%= authorization.id %>">
26
+ <td><%= authorization.name %></td>
27
+ <td class="metadata">
28
+ <span class="code"><%= authorization.metadata %></span>
29
+ </td>
30
+ <td><%= authorization.user.name %></td>
31
+ <td><%= authorization.created_at %></td>
32
+
33
+ <td class="table-list__actions">
34
+ <%= icon_link_to "circle-x", authorization_path(authorization), t("actions.destroy", scope: "decidim.admin"), class: "action-icon--remove", method: :delete, data: { confirm: t("actions.confirm_destroy", scope: "decidim.admin") } %>
35
+ </td>
36
+ </tr>
37
+ <% end %>
38
+ </tbody>
39
+ </table>
40
+ <%= paginate @authorizations, theme: "decidim" %>
41
+ </div>
42
+ </div>
43
+ </div>