From 70c4740725ed8931241c0c7da640986b6fb152d1 Mon Sep 17 00:00:00 2001 From: snyk-bot Date: Fri, 19 Jul 2024 09:16:30 +0000 Subject: [PATCH 01/45] fix: Gemfile & Gemfile.lock to reduce vulnerabilities The following vulnerabilities are fixed with an upgrade: - https://snyk.io/vuln/SNYK-RUBY-RACK-1061917 --- Gemfile | 2 +- Gemfile.lock | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/Gemfile b/Gemfile index 7f45ad9c..a5f967d8 100644 --- a/Gemfile +++ b/Gemfile @@ -26,7 +26,7 @@ gem 'pundit' gem "jsbundling-rails", ">= 1.3.0" # Hotwire's SPA-like page accelerator [https://turbo.hotwired.dev] -gem "turbo-rails", ">= 2.0.0" +gem "turbo-rails", ">= 2.0.6" # Hotwire's modest JavaScript framework [https://stimulus.hotwired.dev] gem "stimulus-rails", ">= 1.3.1" diff --git a/Gemfile.lock b/Gemfile.lock index 95489626..2879af3e 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -313,7 +313,7 @@ GEM method_source (1.1.0) mini_magick (4.12.0) mini_mime (1.1.5) - minitest (5.23.1) + minitest (5.24.1) msgpack (1.7.2) multi_xml (0.7.1) bigdecimal (~> 3.1) @@ -568,7 +568,7 @@ GEM tilt (2.3.0) timeout (0.4.1) tty-which (0.4.2) - turbo-rails (2.0.5) + turbo-rails (2.0.6) actionpack (>= 6.0.0) activejob (>= 6.0.0) railties (>= 6.0.0) @@ -677,7 +677,7 @@ DEPENDENCIES spring (~> 3.0.0) sprockets-rails (>= 3.5.1) stimulus-rails (>= 1.3.1) - turbo-rails (>= 2.0.0) + turbo-rails (>= 2.0.6) tzinfo-data vcr web-console (>= 4.2.1) From 463b5d3febfb837c192dc860de3852c36275373c Mon Sep 17 00:00:00 2001 From: snyk-bot Date: Sat, 27 Jul 2024 10:23:38 +0000 Subject: [PATCH 02/45] fix: package.json & yarn.lock to reduce vulnerabilities The following vulnerabilities are fixed with an upgrade: - https://snyk.io/vuln/SNYK-JS-BOOTSTRAP-7444580 From 37df92ba98751cde1ba8b4a90559ee228b3711d7 Mon Sep 17 00:00:00 2001 From: snyk-bot Date: Tue, 30 Jul 2024 07:43:11 +0000 Subject: [PATCH 03/45] fix: Gemfile & Gemfile.lock to reduce vulnerabilities The following vulnerabilities are fixed with an upgrade: - https://snyk.io/vuln/SNYK-RUBY-RACK-1061917 --- Gemfile | 2 +- Gemfile.lock | 12 ++++++------ 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/Gemfile b/Gemfile index bef8374e..d81fd689 100644 --- a/Gemfile +++ b/Gemfile @@ -23,7 +23,7 @@ gem "puma", "~> 6.4", ">= 6.4.2" gem 'pundit' # Bundle and transpile JavaScript [https://github.com/rails/jsbundling-rails] -gem "jsbundling-rails", ">= 1.3.0" +gem "jsbundling-rails", ">= 1.3.1" # Hotwire's SPA-like page accelerator [https://turbo.hotwired.dev] gem "turbo-rails", ">= 2.0.0" diff --git a/Gemfile.lock b/Gemfile.lock index cf5293a8..8477b367 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -284,7 +284,7 @@ GEM actionview (>= 5.0.0) activesupport (>= 5.0.0) jmespath (1.6.2) - jsbundling-rails (1.3.0) + jsbundling-rails (1.3.1) railties (>= 6.0.0) json (2.7.2) jsonapi-serializer (2.2.0) @@ -328,9 +328,9 @@ GEM net-protocol newrelic_rpm (9.10.1) nio4r (2.7.3) - nokogiri (1.16.6-arm64-darwin) + nokogiri (1.16.7-arm64-darwin) racc (~> 1.4) - nokogiri (1.16.6-x86_64-linux) + nokogiri (1.16.7-x86_64-linux) racc (~> 1.4) orm_adapter (0.5.0) pagy (6.0.4) @@ -355,7 +355,7 @@ GEM pundit (2.3.2) activesupport (>= 3.0.0) raabro (1.4.0) - racc (1.8.0) + racc (1.8.1) rack (2.2.9) rack-cors (2.0.2) rack (>= 2.0.0) @@ -605,7 +605,7 @@ GEM xpath (3.2.0) nokogiri (~> 1.8) yard (0.9.36) - zeitwerk (2.6.16) + zeitwerk (2.6.17) PLATFORMS arm64-darwin-22 @@ -639,7 +639,7 @@ DEPENDENCIES image_processing (~> 1.2) inherited_resources (= 1.14.0) jbuilder - jsbundling-rails (>= 1.3.0) + jsbundling-rails (>= 1.3.1) jsonapi-serializer listen (~> 3.2) net-smtp From ae5d3f4b471125371533ca40ea75797ee59e0e4f Mon Sep 17 00:00:00 2001 From: snyk-bot Date: Thu, 1 Aug 2024 08:13:12 +0000 Subject: [PATCH 04/45] fix: package.json & yarn.lock to reduce vulnerabilities The following vulnerabilities are fixed with an upgrade: - https://snyk.io/vuln/SNYK-JS-BOOTSTRAP-7444593 From afddae47fbb0f42373b47b1016fd105645fda4c6 Mon Sep 17 00:00:00 2001 From: snyk-bot Date: Thu, 1 Aug 2024 08:27:06 +0000 Subject: [PATCH 05/45] fix: Gemfile & Gemfile.lock to reduce vulnerabilities The following vulnerabilities are fixed with an upgrade: - https://snyk.io/vuln/SNYK-RUBY-RACK-1061917 --- Gemfile | 2 +- Gemfile.lock | 10 +++++----- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/Gemfile b/Gemfile index bef8374e..8af40d0d 100644 --- a/Gemfile +++ b/Gemfile @@ -11,7 +11,7 @@ gem 'inherited_resources', '1.14.0' # Bundle Rails instead: gem 'rails', github: 'rails/rails' gem "rails", "~> 7.0.8", ">= 7.0.8.4" # The original asset pipeline for Rails [https://github.com/rails/sprockets-rails] -gem "sprockets-rails", ">= 3.5.1" +gem "sprockets-rails", ">= 3.5.2" # Use postgresql as the database for Active Record gem "pg", "~> 1.1" diff --git a/Gemfile.lock b/Gemfile.lock index cf5293a8..e5d47d32 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -328,9 +328,9 @@ GEM net-protocol newrelic_rpm (9.10.1) nio4r (2.7.3) - nokogiri (1.16.6-arm64-darwin) + nokogiri (1.16.7-arm64-darwin) racc (~> 1.4) - nokogiri (1.16.6-x86_64-linux) + nokogiri (1.16.7-x86_64-linux) racc (~> 1.4) orm_adapter (0.5.0) pagy (6.0.4) @@ -355,7 +355,7 @@ GEM pundit (2.3.2) activesupport (>= 3.0.0) raabro (1.4.0) - racc (1.8.0) + racc (1.8.1) rack (2.2.9) rack-cors (2.0.2) rack (>= 2.0.0) @@ -556,7 +556,7 @@ GEM sprockets (4.2.1) concurrent-ruby (~> 1.0) rack (>= 2.2.4, < 4) - sprockets-rails (3.5.1) + sprockets-rails (3.5.2) actionpack (>= 6.1) activesupport (>= 6.1) sprockets (>= 3.0.0) @@ -675,7 +675,7 @@ DEPENDENCIES solargraph spreadsheet_architect spring (~> 3.0.0) - sprockets-rails (>= 3.5.1) + sprockets-rails (>= 3.5.2) stimulus-rails (>= 1.3.1) turbo-rails (>= 2.0.0) tzinfo-data From 517883b6e90bdcbb9bec64091f7d19e18788a37b Mon Sep 17 00:00:00 2001 From: Paulo Felipe Souza Date: Fri, 2 Aug 2024 16:45:54 -0300 Subject: [PATCH 06/45] paginate per 10 stocks Also adjust stock index request to interact throughout each stock --- config/initializers/pagy.rb | 2 +- spec/requests/stocks_spec.rb | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/config/initializers/pagy.rb b/config/initializers/pagy.rb index fe6c1cbf..5c417846 100644 --- a/config/initializers/pagy.rb +++ b/config/initializers/pagy.rb @@ -12,7 +12,7 @@ # Instance variables # See https://ddnexus.github.io/pagy/api/pagy#instance-variables # Pagy::DEFAULT[:page] = 1 # default -Pagy::DEFAULT[:items] = 25 # default +Pagy::DEFAULT[:items] = 10 # default # Pagy::DEFAULT[:outset] = 0 # default # Other Variables diff --git a/spec/requests/stocks_spec.rb b/spec/requests/stocks_spec.rb index b122eb23..0364dd21 100644 --- a/spec/requests/stocks_spec.rb +++ b/spec/requests/stocks_spec.rb @@ -8,7 +8,7 @@ describe 'GET /index' do before do - FactoryBot.create_list(:stock, 2, product:) + FactoryBot.create_list(:stock, 10, product:, account_id: user.account.id) sign_in user end From 82a005796713e2fa1ef8aefe363bdc7393c09f63 Mon Sep 17 00:00:00 2001 From: snyk-bot Date: Thu, 15 Aug 2024 08:07:13 +0000 Subject: [PATCH 07/45] fix: package.json & yarn.lock to reduce vulnerabilities The following vulnerabilities are fixed with an upgrade: - https://snyk.io/vuln/SNYK-JS-AXIOS-7361793 --- package.json | 2 +- yarn.lock | 18 +++++++++--------- 2 files changed, 10 insertions(+), 10 deletions(-) diff --git a/package.json b/package.json index 05a76238..05a6021e 100644 --- a/package.json +++ b/package.json @@ -12,7 +12,7 @@ "@rails/actioncable": "^7.0.8", "@rails/activestorage": "^7.1.0", "@rails/ujs": "^6.1.6", - "axios": "^1.6.4", + "axios": "^1.7.4", "bootstrap": "^5.0.0", "chartjs": "^0.3.24", "cleave.js": "^1.4.7", diff --git a/yarn.lock b/yarn.lock index b15b1d19..77e121ef 100644 --- a/yarn.lock +++ b/yarn.lock @@ -515,12 +515,12 @@ asynckit@^0.4.0: resolved "https://registry.yarnpkg.com/asynckit/-/asynckit-0.4.0.tgz#c79ed97f7f34cb8f2ba1bc9790bcc366474b4b79" integrity sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q== -axios@^1.6.4: - version "1.6.4" - resolved "https://registry.yarnpkg.com/axios/-/axios-1.6.4.tgz#184ee1f63d412caffcf30d2c50982253c3ee86e0" - integrity sha512-heJnIs6N4aa1eSthhN9M5ioILu8Wi8vmQW9iHQ9NUvfkJb0lEEDUiIdQNAuBtfUt3FxReaKdpQA5DbmMOqzF/A== +axios@^1.7.4: + version "1.7.4" + resolved "https://registry.yarnpkg.com/axios/-/axios-1.7.4.tgz#4c8ded1b43683c8dd362973c393f3ede24052aa2" + integrity sha512-DukmaFRnY6AzAALSH4J2M3k6PkaC+MfaAGdEERRWcC9q3/TWQwLpHR8ZRLKTdQ3aBDL64EdluRDjJqKw+BPZEw== dependencies: - follow-redirects "^1.15.4" + follow-redirects "^1.15.6" form-data "^4.0.0" proxy-from-env "^1.1.0" @@ -1010,10 +1010,10 @@ follow-redirects@^1.0.0: resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.15.2.tgz#b460864144ba63f2681096f274c4e57026da2c13" integrity sha512-VQLG33o04KaQ8uYi2tVNbdrWp1QWxNNea+nmIB4EVM28v0hmP17z7aG1+wAkNzVq4KeXTq3221ye5qTJP91JwA== -follow-redirects@^1.15.4: - version "1.15.4" - resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.15.4.tgz#cdc7d308bf6493126b17ea2191ea0ccf3e535adf" - integrity sha512-Cr4D/5wlrb0z9dgERpUL3LrmPKVDsETIJhaCMeDfuFYcqa5bldGV6wBsAN6X/vxlXQtFBMrXdXxdL8CbDTGniw== +follow-redirects@^1.15.6: + version "1.15.6" + resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.15.6.tgz#7f815c0cda4249c74ff09e95ef97c23b5fd0399b" + integrity sha512-wWN62YITEaOpSK584EZXJafH1AGpO8RVgElfkuXbTOrPX4fIfOyEpW/CsiNd8JdYrAoOvafRTOEnvsO++qCqFA== form-data@^4.0.0: version "4.0.0" From 6405eeae187306d63fdd01b6f57ed362ab925b83 Mon Sep 17 00:00:00 2001 From: Paulo Felipe Souza Date: Thu, 15 Aug 2024 13:26:33 -0300 Subject: [PATCH 08/45] provide seeds for stocks profiling --- db/seeds.rb | 6 ++++++ spec/factories/products.rb | 3 +-- spec/factories/shein_orders.rb | 4 +--- spec/factories/stocks.rb | 3 ++- 4 files changed, 10 insertions(+), 6 deletions(-) diff --git a/db/seeds.rb b/db/seeds.rb index b3bee1f5..eccc519a 100644 --- a/db/seeds.rb +++ b/db/seeds.rb @@ -32,4 +32,10 @@ cpf: Faker::Number.number(digits: 11), account_id: 1) end 50.times { Supplier.create(name: Faker::Lorem.word, account_id: 1) } + +puts 'Stock' +FactoryBot.create_list(:stock, 500) + +Product.update_all(account_id: user.account.id) + # 50.times { Post.create(title: Faker::Lorem.word,content: Faker::Lorem.sentence(word_count: 3, supplemental: true, random_words_to_add: 4), status: true) } diff --git a/spec/factories/products.rb b/spec/factories/products.rb index d5116778..43842fbd 100644 --- a/spec/factories/products.rb +++ b/spec/factories/products.rb @@ -42,7 +42,6 @@ price { rand(100..400) } active { true } - account_id { create(:account).id } - category_id { create(:category, account_id:).id } + association :account end end diff --git a/spec/factories/shein_orders.rb b/spec/factories/shein_orders.rb index a1fb9d44..a9d477e8 100644 --- a/spec/factories/shein_orders.rb +++ b/spec/factories/shein_orders.rb @@ -11,9 +11,7 @@ # Indexes # # index_shein_orders_on_account_id (account_id) -# data :json -# created_at :datetime not null -# updated_at :datetime not null +# FactoryBot.define do factory :shein_order do diff --git a/spec/factories/stocks.rb b/spec/factories/stocks.rb index d69f347e..91784d80 100644 --- a/spec/factories/stocks.rb +++ b/spec/factories/stocks.rb @@ -13,10 +13,11 @@ # FactoryBot.define do factory :stock do - product_id { 1 } bling_product_id { 1 } total_balance { [10, 30, 40, 0, -1, 100, -4].sample } total_virtual_balance { [10, 30, 40, 0, -1, 100, -4].sample } account_id { 1 } + + association :product end end From a3f0770d5b440ef4fe32ab2c2329478a15ea71ec Mon Sep 17 00:00:00 2001 From: snyk-bot Date: Fri, 16 Aug 2024 11:43:14 +0000 Subject: [PATCH 09/45] fix: Gemfile & Gemfile.lock to reduce vulnerabilities The following vulnerabilities are fixed with an upgrade: - https://snyk.io/vuln/SNYK-RUBY-RACK-1061917 --- Gemfile | 2 +- Gemfile.lock | 16 ++++++++-------- 2 files changed, 9 insertions(+), 9 deletions(-) diff --git a/Gemfile b/Gemfile index bef8374e..63641bb3 100644 --- a/Gemfile +++ b/Gemfile @@ -80,7 +80,7 @@ group :development, :test do gem 'bullet' gem 'byebug', platforms: %i[mri mingw x64_mingw] gem 'pry-byebug' - gem 'rspec-rails', '>= 6.1.3' + gem 'rspec-rails', '>= 6.1.4' gem 'solargraph' end diff --git a/Gemfile.lock b/Gemfile.lock index cf5293a8..1af5c660 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -170,7 +170,7 @@ GEM coderay (1.1.3) coercible (1.0.0) descendants_tracker (~> 0.0.1) - concurrent-ruby (1.3.3) + concurrent-ruby (1.3.4) crack (1.0.0) bigdecimal rexml @@ -313,7 +313,7 @@ GEM method_source (1.1.0) mini_magick (4.12.0) mini_mime (1.1.5) - minitest (5.24.1) + minitest (5.25.0) msgpack (1.7.2) multi_xml (0.7.1) bigdecimal (~> 3.1) @@ -328,9 +328,9 @@ GEM net-protocol newrelic_rpm (9.10.1) nio4r (2.7.3) - nokogiri (1.16.6-arm64-darwin) + nokogiri (1.16.7-arm64-darwin) racc (~> 1.4) - nokogiri (1.16.6-x86_64-linux) + nokogiri (1.16.7-x86_64-linux) racc (~> 1.4) orm_adapter (0.5.0) pagy (6.0.4) @@ -355,7 +355,7 @@ GEM pundit (2.3.2) activesupport (>= 3.0.0) raabro (1.4.0) - racc (1.8.0) + racc (1.8.1) rack (2.2.9) rack-cors (2.0.2) rack (>= 2.0.0) @@ -439,7 +439,7 @@ GEM rspec-mocks (3.13.1) diff-lcs (>= 1.2.0, < 2.0) rspec-support (~> 3.13.0) - rspec-rails (6.1.3) + rspec-rails (6.1.4) actionpack (>= 6.1) activesupport (>= 6.1) railties (>= 6.1) @@ -605,7 +605,7 @@ GEM xpath (3.2.0) nokogiri (~> 1.8) yard (0.9.36) - zeitwerk (2.6.16) + zeitwerk (2.6.17) PLATFORMS arm64-darwin-22 @@ -659,7 +659,7 @@ DEPENDENCIES roo roo-xls rqrcode_png! - rspec-rails (>= 6.1.3) + rspec-rails (>= 6.1.4) rubocop-performance (>= 1.20.0) rubocop-rails (>= 2.25.1) rubocop-rspec (>= 2.24.1) From 53e1927896a2ad445c1e5a55ea8a516491fd0990 Mon Sep 17 00:00:00 2001 From: snyk-bot Date: Sun, 18 Aug 2024 13:47:56 +0000 Subject: [PATCH 10/45] fix: Gemfile & Gemfile.lock to reduce vulnerabilities The following vulnerabilities are fixed with an upgrade: - https://snyk.io/vuln/SNYK-RUBY-RACK-1061917 --- Gemfile | 2 +- Gemfile.lock | 16 ++++++++-------- 2 files changed, 9 insertions(+), 9 deletions(-) diff --git a/Gemfile b/Gemfile index bef8374e..e81d0cec 100644 --- a/Gemfile +++ b/Gemfile @@ -29,7 +29,7 @@ gem "jsbundling-rails", ">= 1.3.0" gem "turbo-rails", ">= 2.0.0" # Hotwire's modest JavaScript framework [https://stimulus.hotwired.dev] -gem "stimulus-rails", ">= 1.3.1" +gem "stimulus-rails", ">= 1.3.4" gem "sentry-ruby" gem "sentry-rails", ">= 5.18.0" diff --git a/Gemfile.lock b/Gemfile.lock index cf5293a8..1fef380b 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -170,7 +170,7 @@ GEM coderay (1.1.3) coercible (1.0.0) descendants_tracker (~> 0.0.1) - concurrent-ruby (1.3.3) + concurrent-ruby (1.3.4) crack (1.0.0) bigdecimal rexml @@ -313,7 +313,7 @@ GEM method_source (1.1.0) mini_magick (4.12.0) mini_mime (1.1.5) - minitest (5.24.1) + minitest (5.25.1) msgpack (1.7.2) multi_xml (0.7.1) bigdecimal (~> 3.1) @@ -328,9 +328,9 @@ GEM net-protocol newrelic_rpm (9.10.1) nio4r (2.7.3) - nokogiri (1.16.6-arm64-darwin) + nokogiri (1.16.7-arm64-darwin) racc (~> 1.4) - nokogiri (1.16.6-x86_64-linux) + nokogiri (1.16.7-x86_64-linux) racc (~> 1.4) orm_adapter (0.5.0) pagy (6.0.4) @@ -355,7 +355,7 @@ GEM pundit (2.3.2) activesupport (>= 3.0.0) raabro (1.4.0) - racc (1.8.0) + racc (1.8.1) rack (2.2.9) rack-cors (2.0.2) rack (>= 2.0.0) @@ -560,7 +560,7 @@ GEM actionpack (>= 6.1) activesupport (>= 6.1) sprockets (>= 3.0.0) - stimulus-rails (1.3.3) + stimulus-rails (1.3.4) railties (>= 6.0.0) strscan (3.1.0) thor (1.3.1) @@ -605,7 +605,7 @@ GEM xpath (3.2.0) nokogiri (~> 1.8) yard (0.9.36) - zeitwerk (2.6.16) + zeitwerk (2.6.17) PLATFORMS arm64-darwin-22 @@ -676,7 +676,7 @@ DEPENDENCIES spreadsheet_architect spring (~> 3.0.0) sprockets-rails (>= 3.5.1) - stimulus-rails (>= 1.3.1) + stimulus-rails (>= 1.3.4) turbo-rails (>= 2.0.0) tzinfo-data vcr From 141954babaf77f41745124302bca4497a5ff3212 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Tue, 20 Aug 2024 15:26:55 -0300 Subject: [PATCH 11/45] comment the calculate_basic_forecast to be able to open the view --- app/controllers/stocks_controller.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/controllers/stocks_controller.rb b/app/controllers/stocks_controller.rb index 3774034f..0afe1e11 100644 --- a/app/controllers/stocks_controller.rb +++ b/app/controllers/stocks_controller.rb @@ -25,8 +25,8 @@ def collection .only_positive_price(true) .filter_by_status(params['status']) .filter_by_total_balance_situation(params['balance_situation']) - .sort_by(&:calculate_basic_forecast) - .reverse! + #.sort_by(&:calculate_basic_forecast) + #.reverse! @pagy, @stocks = pagy_array(stocks) end end From 3a6aee1949386c5eb1fc7cfb3cb20e1828ec0846 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Tue, 20 Aug 2024 15:38:39 -0300 Subject: [PATCH 12/45] update the popperjs --- package-lock.json | 2666 --------------------------------------------- package.json | 1 + yarn.lock | 5 + 3 files changed, 6 insertions(+), 2666 deletions(-) delete mode 100644 package-lock.json diff --git a/package-lock.json b/package-lock.json deleted file mode 100644 index 5dd689ca..00000000 --- a/package-lock.json +++ /dev/null @@ -1,2666 +0,0 @@ -{ - "name": "purple_stock", - "version": "0.1.0", - "lockfileVersion": 1, - "requires": true, - "dependencies": { - "@discoveryjs/json-ext": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/@discoveryjs/json-ext/-/json-ext-0.5.7.tgz", - "integrity": "sha512-dBVuXR082gk3jsFp7Rd/JI4kytwGHecnCoTtXFb7DB6CNHp4rg5k1bhg0nWdLGLnOV71lmDzGQaLMy8iPLY0pw==" - }, - "@fortawesome/fontawesome-free": { - "version": "5.15.4", - "resolved": "https://registry.npmjs.org/@fortawesome/fontawesome-free/-/fontawesome-free-5.15.4.tgz", - "integrity": "sha512-eYm8vijH/hpzr/6/1CJ/V/Eb1xQFW2nnUKArb3z+yUWv7HTwj6M7SP957oMjfZjAHU6qpoNc2wQvIxBLWYa/Jg==" - }, - "@hotwired/stimulus": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/@hotwired/stimulus/-/stimulus-3.2.2.tgz", - "integrity": "sha512-eGeIqNOQpXoPAIP7tC1+1Yc1yl1xnwYqg+3mzqxyrbE5pg5YFBZcA6YoTiByJB6DKAEsiWtl6tjTJS4IYtbB7A==" - }, - "@hotwired/turbo": { - "version": "7.3.0", - "resolved": "https://registry.npmjs.org/@hotwired/turbo/-/turbo-7.3.0.tgz", - "integrity": "sha512-Dcu+NaSvHLT7EjrDrkEmH4qET2ZJZ5IcCWmNXxNQTBwlnE5tBZfN6WxZ842n5cHV52DH/AKNirbPBtcEXDLW4g==" - }, - "@hotwired/turbo-rails": { - "version": "7.3.0", - "resolved": "https://registry.npmjs.org/@hotwired/turbo-rails/-/turbo-rails-7.3.0.tgz", - "integrity": "sha512-fvhO64vp/a2UVQ3jue9WTc2JisMv9XilIC7ViZmXAREVwiQ2S4UC7Go8f9A1j4Xu7DBI6SbFdqILk5ImqVoqyA==", - "requires": { - "@hotwired/turbo": "^7.3.0", - "@rails/actioncable": "^7.0" - } - }, - "@jridgewell/gen-mapping": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.3.tgz", - "integrity": "sha512-HLhSWOLRi875zjjMG/r+Nv0oCW8umGb0BgEhyX3dDX3egwZtB8PqLnjz3yedt8R5StBrzcg4aBpnh8UA9D1BoQ==", - "requires": { - "@jridgewell/set-array": "^1.0.1", - "@jridgewell/sourcemap-codec": "^1.4.10", - "@jridgewell/trace-mapping": "^0.3.9" - } - }, - "@jridgewell/resolve-uri": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.1.tgz", - "integrity": "sha512-dSYZh7HhCDtCKm4QakX0xFpsRDqjjtZf/kjI/v3T3Nwt5r8/qz/M19F9ySyOqU94SXBmeG9ttTul+YnR4LOxFA==" - }, - "@jridgewell/set-array": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.1.2.tgz", - "integrity": "sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==" - }, - "@jridgewell/source-map": { - "version": "0.3.5", - "resolved": "https://registry.npmjs.org/@jridgewell/source-map/-/source-map-0.3.5.tgz", - "integrity": "sha512-UTYAUj/wviwdsMfzoSJspJxbkH5o1snzwX0//0ENX1u/55kkZZkcTZP6u9bwKGkv+dkk9at4m1Cpt0uY80kcpQ==", - "requires": { - "@jridgewell/gen-mapping": "^0.3.0", - "@jridgewell/trace-mapping": "^0.3.9" - } - }, - "@jridgewell/sourcemap-codec": { - "version": "1.4.15", - "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.15.tgz", - "integrity": "sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg==" - }, - "@jridgewell/trace-mapping": { - "version": "0.3.19", - "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.19.tgz", - "integrity": "sha512-kf37QtfW+Hwx/buWGMPcR60iF9ziHa6r/CZJIHbmcm4+0qrXiVdxegAH0F6yddEVQ7zdkjcGCgCzUu+BcbhQxw==", - "requires": { - "@jridgewell/resolve-uri": "^3.1.0", - "@jridgewell/sourcemap-codec": "^1.4.14" - } - }, - "@kurkle/color": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/@kurkle/color/-/color-0.3.2.tgz", - "integrity": "sha512-fuscdXJ9G1qb7W8VdHi+IwRqij3lBkosAm4ydQtEmbY58OzHXqQhvlxqEkoz0yssNVn38bcpRWgA9PP+OGoisw==" - }, - "@leichtgewicht/ip-codec": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/@leichtgewicht/ip-codec/-/ip-codec-2.0.4.tgz", - "integrity": "sha512-Hcv+nVC0kZnQ3tD9GVu5xSMR4VVYOteQIr/hwFPVEvPdlXqgGEuRjiheChHgdM+JyqdgNcmzZOX/tnl0JOiI7A==", - "dev": true - }, - "@nathanvda/cocoon": { - "version": "1.2.14", - "resolved": "https://registry.npmjs.org/@nathanvda/cocoon/-/cocoon-1.2.14.tgz", - "integrity": "sha512-WcEt2vVp50de2i7rkD4O+96O1iMtMIcTBNGPocrHfcmHDujKOngoLHFF8Ektgoh8PjwFAJMxx8WyGv0BtKTjxQ==", - "requires": { - "jquery": "^3.3.1" - } - }, - "@rails/actioncable": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/@rails/actioncable/-/actioncable-7.1.1.tgz", - "integrity": "sha512-ZRJ9rdwFQQjRbtgJnweY0/4UQyxN6ojEGRdib0JkjnuIciv+4ok/aAeZmBJqNreTMaBqS0eHyA9hCArwN58opg==" - }, - "@rails/activestorage": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/@rails/activestorage/-/activestorage-7.1.1.tgz", - "integrity": "sha512-QGBj+y4fbZt/QMMpjqnpKlzCKpDGTYrvJ+qc0QLis34AfbBLVgRo7kPzmdmeOTtwvWqpcivB9CrjTcV/C/7ruA==", - "requires": { - "spark-md5": "^3.0.1" - } - }, - "@rails/ujs": { - "version": "6.1.7", - "resolved": "https://registry.npmjs.org/@rails/ujs/-/ujs-6.1.7.tgz", - "integrity": "sha512-0e7WQ4LE/+LEfW2zfAw9ppsB6A8RmxbdAUPAF++UT80epY+7emuQDkKXmaK0a9lp6An50RvzezI0cIQjp1A58w==" - }, - "@stimulus/core": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@stimulus/core/-/core-2.0.0.tgz", - "integrity": "sha512-ff70GafKtzc8zQ1/cG+UvL06GcifPWovf2wBEdjLMh9xO2GOYURO3y2RYgzIGYUIBefQwyfX2CLfJdZFJrEPTw==", - "requires": { - "@stimulus/mutation-observers": "^2.0.0" - } - }, - "@stimulus/multimap": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@stimulus/multimap/-/multimap-2.0.0.tgz", - "integrity": "sha512-pMBCewkZCFVB3e5mEMoyO9+9aKzHDITmf3OnPun51YWxlcPdHcwbjqm1ylK63fsoduIE+RowBpFwFqd3poEz4w==" - }, - "@stimulus/mutation-observers": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@stimulus/mutation-observers/-/mutation-observers-2.0.0.tgz", - "integrity": "sha512-kx4VAJdPhIGBQKGIoUDC2tupEKorG3A+ckc2b1UiwInKTMAC1axOHU8ebcwhaJIxRqIrs8//4SJo9YAAOx6FEg==", - "requires": { - "@stimulus/multimap": "^2.0.0" - } - }, - "@stimulus/webpack-helpers": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@stimulus/webpack-helpers/-/webpack-helpers-2.0.0.tgz", - "integrity": "sha512-D6tJWsAC024MwGEIKlUVYU8Ln87mlrmiwHvYAjipg+s8H4eLxUMQ3PZkWyPevfipH+oR3leuHsjYsK1gN5ViQA==" - }, - "@types/body-parser": { - "version": "1.19.3", - "resolved": "https://registry.npmjs.org/@types/body-parser/-/body-parser-1.19.3.tgz", - "integrity": "sha512-oyl4jvAfTGX9Bt6Or4H9ni1Z447/tQuxnZsytsCaExKlmJiU8sFgnIBRzJUpKwB5eWn9HuBYlUlVA74q/yN0eQ==", - "dev": true, - "requires": { - "@types/connect": "*", - "@types/node": "*" - } - }, - "@types/bonjour": { - "version": "3.5.11", - "resolved": "https://registry.npmjs.org/@types/bonjour/-/bonjour-3.5.11.tgz", - "integrity": "sha512-isGhjmBtLIxdHBDl2xGwUzEM8AOyOvWsADWq7rqirdi/ZQoHnLWErHvsThcEzTX8juDRiZtzp2Qkv5bgNh6mAg==", - "dev": true, - "requires": { - "@types/node": "*" - } - }, - "@types/connect": { - "version": "3.4.36", - "resolved": "https://registry.npmjs.org/@types/connect/-/connect-3.4.36.tgz", - "integrity": "sha512-P63Zd/JUGq+PdrM1lv0Wv5SBYeA2+CORvbrXbngriYY0jzLUWfQMQQxOhjONEz/wlHOAxOdY7CY65rgQdTjq2w==", - "dev": true, - "requires": { - "@types/node": "*" - } - }, - "@types/connect-history-api-fallback": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/@types/connect-history-api-fallback/-/connect-history-api-fallback-1.5.1.tgz", - "integrity": "sha512-iaQslNbARe8fctL5Lk+DsmgWOM83lM+7FzP0eQUJs1jd3kBE8NWqBTIT2S8SqQOJjxvt2eyIjpOuYeRXq2AdMw==", - "dev": true, - "requires": { - "@types/express-serve-static-core": "*", - "@types/node": "*" - } - }, - "@types/eslint": { - "version": "8.44.4", - "resolved": "https://registry.npmjs.org/@types/eslint/-/eslint-8.44.4.tgz", - "integrity": "sha512-lOzjyfY/D9QR4hY9oblZ76B90MYTB3RrQ4z2vBIJKj9ROCRqdkYl2gSUx1x1a4IWPjKJZLL4Aw1Zfay7eMnmnA==", - "requires": { - "@types/estree": "*", - "@types/json-schema": "*" - } - }, - "@types/eslint-scope": { - "version": "3.7.5", - "resolved": "https://registry.npmjs.org/@types/eslint-scope/-/eslint-scope-3.7.5.tgz", - "integrity": "sha512-JNvhIEyxVW6EoMIFIvj93ZOywYFatlpu9deeH6eSx6PE3WHYvHaQtmHmQeNw7aA81bYGBPPQqdtBm6b1SsQMmA==", - "requires": { - "@types/eslint": "*", - "@types/estree": "*" - } - }, - "@types/estree": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.2.tgz", - "integrity": "sha512-VeiPZ9MMwXjO32/Xu7+OwflfmeoRwkE/qzndw42gGtgJwZopBnzy2gD//NN1+go1mADzkDcqf/KnFRSjTJ8xJA==" - }, - "@types/express": { - "version": "4.17.19", - "resolved": "https://registry.npmjs.org/@types/express/-/express-4.17.19.tgz", - "integrity": "sha512-UtOfBtzN9OvpZPPbnnYunfjM7XCI4jyk1NvnFhTVz5krYAnW4o5DCoIekvms+8ApqhB4+9wSge1kBijdfTSmfg==", - "dev": true, - "requires": { - "@types/body-parser": "*", - "@types/express-serve-static-core": "^4.17.33", - "@types/qs": "*", - "@types/serve-static": "*" - } - }, - "@types/express-serve-static-core": { - "version": "4.17.37", - "resolved": "https://registry.npmjs.org/@types/express-serve-static-core/-/express-serve-static-core-4.17.37.tgz", - "integrity": "sha512-ZohaCYTgGFcOP7u6aJOhY9uIZQgZ2vxC2yWoArY+FeDXlqeH66ZVBjgvg+RLVAS/DWNq4Ap9ZXu1+SUQiiWYMg==", - "dev": true, - "requires": { - "@types/node": "*", - "@types/qs": "*", - "@types/range-parser": "*", - "@types/send": "*" - } - }, - "@types/http-errors": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/@types/http-errors/-/http-errors-2.0.2.tgz", - "integrity": "sha512-lPG6KlZs88gef6aD85z3HNkztpj7w2R7HmR3gygjfXCQmsLloWNARFkMuzKiiY8FGdh1XDpgBdrSf4aKDiA7Kg==", - "dev": true - }, - "@types/http-proxy": { - "version": "1.17.12", - "resolved": "https://registry.npmjs.org/@types/http-proxy/-/http-proxy-1.17.12.tgz", - "integrity": "sha512-kQtujO08dVtQ2wXAuSFfk9ASy3sug4+ogFR8Kd8UgP8PEuc1/G/8yjYRmp//PcDNJEUKOza/MrQu15bouEUCiw==", - "dev": true, - "requires": { - "@types/node": "*" - } - }, - "@types/json-schema": { - "version": "7.0.12", - "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.12.tgz", - "integrity": "sha512-Hr5Jfhc9eYOQNPYO5WLDq/n4jqijdHNlDXjuAQkkt+mWdQR+XJToOHrsD4cPaMXpn6KO7y2+wM8AZEs8VpBLVA==" - }, - "@types/mime": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/@types/mime/-/mime-1.3.3.tgz", - "integrity": "sha512-Ys+/St+2VF4+xuY6+kDIXGxbNRO0mesVg0bbxEfB97Od1Vjpjx9KD1qxs64Gcb3CWPirk9Xe+PT4YiiHQ9T+eg==", - "dev": true - }, - "@types/node": { - "version": "20.5.7", - "resolved": "https://registry.npmjs.org/@types/node/-/node-20.5.7.tgz", - "integrity": "sha512-dP7f3LdZIysZnmvP3ANJYTSwg+wLLl8p7RqniVlV7j+oXSXAbt9h0WIBFmJy5inWZoX9wZN6eXx+YXd9Rh3RBA==" - }, - "@types/qs": { - "version": "6.9.8", - "resolved": "https://registry.npmjs.org/@types/qs/-/qs-6.9.8.tgz", - "integrity": "sha512-u95svzDlTysU5xecFNTgfFG5RUWu1A9P0VzgpcIiGZA9iraHOdSzcxMxQ55DyeRaGCSxQi7LxXDI4rzq/MYfdg==", - "dev": true - }, - "@types/range-parser": { - "version": "1.2.5", - "resolved": "https://registry.npmjs.org/@types/range-parser/-/range-parser-1.2.5.tgz", - "integrity": "sha512-xrO9OoVPqFuYyR/loIHjnbvvyRZREYKLjxV4+dY6v3FQR3stQ9ZxIGkaclF7YhI9hfjpuTbu14hZEy94qKLtOA==", - "dev": true - }, - "@types/retry": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/@types/retry/-/retry-0.12.0.tgz", - "integrity": "sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA==", - "dev": true - }, - "@types/send": { - "version": "0.17.2", - "resolved": "https://registry.npmjs.org/@types/send/-/send-0.17.2.tgz", - "integrity": "sha512-aAG6yRf6r0wQ29bkS+x97BIs64ZLxeE/ARwyS6wrldMm3C1MdKwCcnnEwMC1slI8wuxJOpiUH9MioC0A0i+GJw==", - "dev": true, - "requires": { - "@types/mime": "^1", - "@types/node": "*" - } - }, - "@types/serve-index": { - "version": "1.9.2", - "resolved": "https://registry.npmjs.org/@types/serve-index/-/serve-index-1.9.2.tgz", - "integrity": "sha512-asaEIoc6J+DbBKXtO7p2shWUpKacZOoMBEGBgPG91P8xhO53ohzHWGCs4ScZo5pQMf5ukQzVT9fhX1WzpHihig==", - "dev": true, - "requires": { - "@types/express": "*" - } - }, - "@types/serve-static": { - "version": "1.15.3", - "resolved": "https://registry.npmjs.org/@types/serve-static/-/serve-static-1.15.3.tgz", - "integrity": "sha512-yVRvFsEMrv7s0lGhzrggJjNOSmZCdgCjw9xWrPr/kNNLp6FaDfMC1KaYl3TSJ0c58bECwNBMoQrZJ8hA8E1eFg==", - "dev": true, - "requires": { - "@types/http-errors": "*", - "@types/mime": "*", - "@types/node": "*" - } - }, - "@types/sockjs": { - "version": "0.3.34", - "resolved": "https://registry.npmjs.org/@types/sockjs/-/sockjs-0.3.34.tgz", - "integrity": "sha512-R+n7qBFnm/6jinlteC9DBL5dGiDGjWAvjo4viUanpnc/dG1y7uDoacXPIQ/PQEg1fI912SMHIa014ZjRpvDw4g==", - "dev": true, - "requires": { - "@types/node": "*" - } - }, - "@types/ws": { - "version": "8.5.7", - "resolved": "https://registry.npmjs.org/@types/ws/-/ws-8.5.7.tgz", - "integrity": "sha512-6UrLjiDUvn40CMrAubXuIVtj2PEfKDffJS7ychvnPU44j+KVeXmdHHTgqcM/dxLUTHxlXHiFM8Skmb8ozGdTnQ==", - "dev": true, - "requires": { - "@types/node": "*" - } - }, - "@webassemblyjs/ast": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.11.6.tgz", - "integrity": "sha512-IN1xI7PwOvLPgjcf180gC1bqn3q/QaOCwYUahIOhbYUu8KA/3tw2RT/T0Gidi1l7Hhj5D/INhJxiICObqpMu4Q==", - "requires": { - "@webassemblyjs/helper-numbers": "1.11.6", - "@webassemblyjs/helper-wasm-bytecode": "1.11.6" - } - }, - "@webassemblyjs/floating-point-hex-parser": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.11.6.tgz", - "integrity": "sha512-ejAj9hfRJ2XMsNHk/v6Fu2dGS+i4UaXBXGemOfQ/JfQ6mdQg/WXtwleQRLLS4OvfDhv8rYnVwH27YJLMyYsxhw==" - }, - "@webassemblyjs/helper-api-error": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-api-error/-/helper-api-error-1.11.6.tgz", - "integrity": "sha512-o0YkoP4pVu4rN8aTJgAyj9hC2Sv5UlkzCHhxqWj8butaLvnpdc2jOwh4ewE6CX0txSfLn/UYaV/pheS2Txg//Q==" - }, - "@webassemblyjs/helper-buffer": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-buffer/-/helper-buffer-1.11.6.tgz", - "integrity": "sha512-z3nFzdcp1mb8nEOFFk8DrYLpHvhKC3grJD2ardfKOzmbmJvEf/tPIqCY+sNcwZIY8ZD7IkB2l7/pqhUhqm7hLA==" - }, - "@webassemblyjs/helper-numbers": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-numbers/-/helper-numbers-1.11.6.tgz", - "integrity": "sha512-vUIhZ8LZoIWHBohiEObxVm6hwP034jwmc9kuq5GdHZH0wiLVLIPcMCdpJzG4C11cHoQ25TFIQj9kaVADVX7N3g==", - "requires": { - "@webassemblyjs/floating-point-hex-parser": "1.11.6", - "@webassemblyjs/helper-api-error": "1.11.6", - "@xtuc/long": "4.2.2" - } - }, - "@webassemblyjs/helper-wasm-bytecode": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-bytecode/-/helper-wasm-bytecode-1.11.6.tgz", - "integrity": "sha512-sFFHKwcmBprO9e7Icf0+gddyWYDViL8bpPjJJl0WHxCdETktXdmtWLGVzoHbqUcY4Be1LkNfwTmXOJUFZYSJdA==" - }, - "@webassemblyjs/helper-wasm-section": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-section/-/helper-wasm-section-1.11.6.tgz", - "integrity": "sha512-LPpZbSOwTpEC2cgn4hTydySy1Ke+XEu+ETXuoyvuyezHO3Kjdu90KK95Sh9xTbmjrCsUwvWwCOQQNta37VrS9g==", - "requires": { - "@webassemblyjs/ast": "1.11.6", - "@webassemblyjs/helper-buffer": "1.11.6", - "@webassemblyjs/helper-wasm-bytecode": "1.11.6", - "@webassemblyjs/wasm-gen": "1.11.6" - } - }, - "@webassemblyjs/ieee754": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ieee754/-/ieee754-1.11.6.tgz", - "integrity": "sha512-LM4p2csPNvbij6U1f19v6WR56QZ8JcHg3QIJTlSwzFcmx6WSORicYj6I63f9yU1kEUtrpG+kjkiIAkevHpDXrg==", - "requires": { - "@xtuc/ieee754": "^1.2.0" - } - }, - "@webassemblyjs/leb128": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/leb128/-/leb128-1.11.6.tgz", - "integrity": "sha512-m7a0FhE67DQXgouf1tbN5XQcdWoNgaAuoULHIfGFIEVKA6tu/edls6XnIlkmS6FrXAquJRPni3ZZKjw6FSPjPQ==", - "requires": { - "@xtuc/long": "4.2.2" - } - }, - "@webassemblyjs/utf8": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/utf8/-/utf8-1.11.6.tgz", - "integrity": "sha512-vtXf2wTQ3+up9Zsg8sa2yWiQpzSsMyXj0qViVP6xKGCUT8p8YJ6HqI7l5eCnWx1T/FYdsv07HQs2wTFbbof/RA==" - }, - "@webassemblyjs/wasm-edit": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-edit/-/wasm-edit-1.11.6.tgz", - "integrity": "sha512-Ybn2I6fnfIGuCR+Faaz7YcvtBKxvoLV3Lebn1tM4o/IAJzmi9AWYIPWpyBfU8cC+JxAO57bk4+zdsTjJR+VTOw==", - "requires": { - "@webassemblyjs/ast": "1.11.6", - "@webassemblyjs/helper-buffer": "1.11.6", - "@webassemblyjs/helper-wasm-bytecode": "1.11.6", - "@webassemblyjs/helper-wasm-section": "1.11.6", - "@webassemblyjs/wasm-gen": "1.11.6", - "@webassemblyjs/wasm-opt": "1.11.6", - "@webassemblyjs/wasm-parser": "1.11.6", - "@webassemblyjs/wast-printer": "1.11.6" - } - }, - "@webassemblyjs/wasm-gen": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-gen/-/wasm-gen-1.11.6.tgz", - "integrity": "sha512-3XOqkZP/y6B4F0PBAXvI1/bky7GryoogUtfwExeP/v7Nzwo1QLcq5oQmpKlftZLbT+ERUOAZVQjuNVak6UXjPA==", - "requires": { - "@webassemblyjs/ast": "1.11.6", - "@webassemblyjs/helper-wasm-bytecode": "1.11.6", - "@webassemblyjs/ieee754": "1.11.6", - "@webassemblyjs/leb128": "1.11.6", - "@webassemblyjs/utf8": "1.11.6" - } - }, - "@webassemblyjs/wasm-opt": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-opt/-/wasm-opt-1.11.6.tgz", - "integrity": "sha512-cOrKuLRE7PCe6AsOVl7WasYf3wbSo4CeOk6PkrjS7g57MFfVUF9u6ysQBBODX0LdgSvQqRiGz3CXvIDKcPNy4g==", - "requires": { - "@webassemblyjs/ast": "1.11.6", - "@webassemblyjs/helper-buffer": "1.11.6", - "@webassemblyjs/wasm-gen": "1.11.6", - "@webassemblyjs/wasm-parser": "1.11.6" - } - }, - "@webassemblyjs/wasm-parser": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-parser/-/wasm-parser-1.11.6.tgz", - "integrity": "sha512-6ZwPeGzMJM3Dqp3hCsLgESxBGtT/OeCvCZ4TA1JUPYgmhAx38tTPR9JaKy0S5H3evQpO/h2uWs2j6Yc/fjkpTQ==", - "requires": { - "@webassemblyjs/ast": "1.11.6", - "@webassemblyjs/helper-api-error": "1.11.6", - "@webassemblyjs/helper-wasm-bytecode": "1.11.6", - "@webassemblyjs/ieee754": "1.11.6", - "@webassemblyjs/leb128": "1.11.6", - "@webassemblyjs/utf8": "1.11.6" - } - }, - "@webassemblyjs/wast-printer": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wast-printer/-/wast-printer-1.11.6.tgz", - "integrity": "sha512-JM7AhRcE+yW2GWYaKeHL5vt4xqee5N2WcezptmgyhNS+ScggqcT1OtXykhAb13Sn5Yas0j2uv9tHgrjwvzAP4A==", - "requires": { - "@webassemblyjs/ast": "1.11.6", - "@xtuc/long": "4.2.2" - } - }, - "@webpack-cli/configtest": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/@webpack-cli/configtest/-/configtest-2.1.1.tgz", - "integrity": "sha512-wy0mglZpDSiSS0XHrVR+BAdId2+yxPSoJW8fsna3ZpYSlufjvxnP4YbKTCBZnNIcGN4r6ZPXV55X4mYExOfLmw==" - }, - "@webpack-cli/info": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/@webpack-cli/info/-/info-2.0.2.tgz", - "integrity": "sha512-zLHQdI/Qs1UyT5UBdWNqsARasIA+AaF8t+4u2aS2nEpBQh2mWIVb8qAklq0eUENnC5mOItrIB4LiS9xMtph18A==" - }, - "@webpack-cli/serve": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/@webpack-cli/serve/-/serve-2.0.5.tgz", - "integrity": "sha512-lqaoKnRYBdo1UgDX8uF24AfGMifWK19TxPmM5FHc2vAGxrJ/qtyUyFBWoY1tISZdelsQ5fBcOusifo5o5wSJxQ==" - }, - "@xtuc/ieee754": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/@xtuc/ieee754/-/ieee754-1.2.0.tgz", - "integrity": "sha512-DX8nKgqcGwsc0eJSqYt5lwP4DH5FlHnmuWWBRy7X0NcaGR0ZtuyeESgMwTYVEtxmsNGY+qit4QYT/MIYTOTPeA==" - }, - "@xtuc/long": { - "version": "4.2.2", - "resolved": "https://registry.npmjs.org/@xtuc/long/-/long-4.2.2.tgz", - "integrity": "sha512-NuHqBY1PB/D8xU6s/thBgOAiAP7HOYDQ32+BFZILJ8ivkUkAHQnWfn6WhL79Owj1qmUnoN/YPhktdIoucipkAQ==" - }, - "accepts": { - "version": "1.3.8", - "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.8.tgz", - "integrity": "sha512-PYAthTa2m2VKxuvSD3DPC/Gy+U+sOA1LAuT8mkmRuvw+NACSaeXEQ+NHcVF7rONl6qcaxV3Uuemwawk+7+SJLw==", - "dev": true, - "requires": { - "mime-types": "~2.1.34", - "negotiator": "0.6.3" - } - }, - "acorn": { - "version": "8.10.0", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.10.0.tgz", - "integrity": "sha512-F0SAmZ8iUtS//m8DmCTA0jlh6TDKkHQyK6xc6V4KDTyZKA9dnvX9/3sRTVQrWm79glUAZbnmmNcdYwUIHWVybw==" - }, - "acorn-import-assertions": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/acorn-import-assertions/-/acorn-import-assertions-1.9.0.tgz", - "integrity": "sha512-cmMwop9x+8KFhxvKrKfPYmN6/pKTYYHBqLa0DfvVZcKMJWNyWLnaqND7dx/qn66R7ewM1UX5XMaDVP5wlVTaVA==" - }, - "ajv": { - "version": "8.12.0", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.12.0.tgz", - "integrity": "sha512-sRu1kpcO9yLtYxBKvqfTeh9KzZEwO3STyX1HT+4CaDzC6HpTGYhIhPIzj9XuKU7KYDwnaeh5hcOwjy1QuJzBPA==", - "dev": true, - "requires": { - "fast-deep-equal": "^3.1.1", - "json-schema-traverse": "^1.0.0", - "require-from-string": "^2.0.2", - "uri-js": "^4.2.2" - } - }, - "ajv-formats": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ajv-formats/-/ajv-formats-2.1.1.tgz", - "integrity": "sha512-Wx0Kx52hxE7C18hkMEggYlEifqWZtYaRgouJor+WMdPnQyEK13vgEWyVNup7SoeeoLMsr4kf5h6dOW11I15MUA==", - "dev": true, - "requires": { - "ajv": "^8.0.0" - } - }, - "ajv-keywords": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-5.1.0.tgz", - "integrity": "sha512-YCS/JNFAUyr5vAuhk1DWm1CBxRHW9LbJ2ozWeemrIqpbsqKjHVxYPyi5GC0rjZIT5JxJ3virVTS8wk4i/Z+krw==", - "dev": true, - "requires": { - "fast-deep-equal": "^3.1.3" - } - }, - "ansi-html-community": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/ansi-html-community/-/ansi-html-community-0.0.8.tgz", - "integrity": "sha512-1APHAyr3+PCamwNw3bXCPp4HFLONZt/yIH0sZp0/469KWNTEy+qN5jQ3GVX6DMZ1UXAi34yVwtTeaG/HpBuuzw==", - "dev": true - }, - "anymatch": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.3.tgz", - "integrity": "sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==", - "dev": true, - "requires": { - "normalize-path": "^3.0.0", - "picomatch": "^2.0.4" - } - }, - "array-flatten": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-2.1.2.tgz", - "integrity": "sha512-hNfzcOV8W4NdualtqBFPyVO+54DSJuZGY9qT4pRroB6S9e3iiido2ISIC5h9R2sPJ8H3FHCIiEnsv1lPXO3KtQ==", - "dev": true - }, - "asynckit": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==" - }, - "axios": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/axios/-/axios-1.6.0.tgz", - "integrity": "sha512-EZ1DYihju9pwVB+jg67ogm+Tmqc6JmhamRN6I4Zt8DfZu5lbcQGw3ozH9lFejSJgs/ibaef3A9PMXPLeefFGJg==", - "requires": { - "follow-redirects": "^1.15.0", - "form-data": "^4.0.0", - "proxy-from-env": "^1.1.0" - } - }, - "balanced-match": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", - "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", - "dev": true - }, - "batch": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/batch/-/batch-0.6.1.tgz", - "integrity": "sha512-x+VAiMRL6UPkx+kudNvxTl6hB2XNNCG2r+7wixVfIYwu/2HKRXimwQyaumLjMveWvT2Hkd/cAJw+QBMfJ/EKVw==", - "dev": true - }, - "binary-extensions": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.2.0.tgz", - "integrity": "sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==", - "dev": true - }, - "body-parser": { - "version": "1.20.1", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.20.1.tgz", - "integrity": "sha512-jWi7abTbYwajOytWCQc37VulmWiRae5RyTpaCyDcS5/lMdtwSz5lOpDE67srw/HYe35f1z3fDQw+3txg7gNtWw==", - "dev": true, - "requires": { - "bytes": "3.1.2", - "content-type": "~1.0.4", - "debug": "2.6.9", - "depd": "2.0.0", - "destroy": "1.2.0", - "http-errors": "2.0.0", - "iconv-lite": "0.4.24", - "on-finished": "2.4.1", - "qs": "6.11.0", - "raw-body": "2.5.1", - "type-is": "~1.6.18", - "unpipe": "1.0.0" - }, - "dependencies": { - "bytes": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", - "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", - "dev": true - } - } - }, - "bonjour-service": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/bonjour-service/-/bonjour-service-1.1.1.tgz", - "integrity": "sha512-Z/5lQRMOG9k7W+FkeGTNjh7htqn/2LMnfOvBZ8pynNZCM9MwkQkI3zeI4oz09uWdcgmgHugVvBqxGg4VQJ5PCg==", - "dev": true, - "requires": { - "array-flatten": "^2.1.2", - "dns-equal": "^1.0.0", - "fast-deep-equal": "^3.1.3", - "multicast-dns": "^7.2.5" - } - }, - "bootstrap": { - "version": "4.6.2", - "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-4.6.2.tgz", - "integrity": "sha512-51Bbp/Uxr9aTuy6ca/8FbFloBUJZLHwnhTcnjIeRn2suQWsWzcuJhGjKDB5eppVte/8oCdOL3VuwxvZDUggwGQ==" - }, - "brace-expansion": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", - "dev": true, - "requires": { - "balanced-match": "^1.0.0", - "concat-map": "0.0.1" - } - }, - "braces": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz", - "integrity": "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==", - "dev": true, - "requires": { - "fill-range": "^7.0.1" - } - }, - "browserslist": { - "version": "4.22.1", - "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.22.1.tgz", - "integrity": "sha512-FEVc202+2iuClEhZhrWy6ZiAcRLvNMyYcxZ8raemul1DYVOVdFsbqckWLdsixQZCpJlwe77Z3UTalE7jsjnKfQ==", - "requires": { - "caniuse-lite": "^1.0.30001541", - "electron-to-chromium": "^1.4.535", - "node-releases": "^2.0.13", - "update-browserslist-db": "^1.0.13" - } - }, - "buffer-from": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz", - "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==" - }, - "bytes": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", - "integrity": "sha512-pMhOfFDPiv9t5jjIXkHosWmkSyQbvsgEVNkz0ERHbuLh2T/7j4Mqqpz523Fe8MVY89KC6Sh/QfS2sM+SjgFDcw==", - "dev": true - }, - "call-bind": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.2.tgz", - "integrity": "sha512-7O+FbCihrB5WGbFYesctwmTKae6rOiIzmz1icreWJ+0aA7LJfuqhEso2T9ncpcFtzMQtzXf2QGGueWJGTYsqrA==", - "dev": true, - "requires": { - "function-bind": "^1.1.1", - "get-intrinsic": "^1.0.2" - } - }, - "caniuse-lite": { - "version": "1.0.30001547", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001547.tgz", - "integrity": "sha512-W7CrtIModMAxobGhz8iXmDfuJiiKg1WADMO/9x7/CLNin5cpSbuBjooyoIUVB5eyCc36QuTVlkVa1iB2S5+/eA==" - }, - "chart.js": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/chart.js/-/chart.js-4.4.0.tgz", - "integrity": "sha512-vQEj6d+z0dcsKLlQvbKIMYFHd3t8W/7L2vfJIbYcfyPcRx92CsHqECpueN8qVGNlKyDcr5wBrYAYKnfu/9Q1hQ==", - "requires": { - "@kurkle/color": "^0.3.0" - } - }, - "chokidar": { - "version": "3.5.3", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.5.3.tgz", - "integrity": "sha512-Dr3sfKRP6oTcjf2JmUmFJfeVMvXBdegxB0iVQ5eb2V10uFJUCAS8OByZdVAyVb8xXNz3GjjTgj9kLWsZTqE6kw==", - "dev": true, - "requires": { - "anymatch": "~3.1.2", - "braces": "~3.0.2", - "fsevents": "~2.3.2", - "glob-parent": "~5.1.2", - "is-binary-path": "~2.1.0", - "is-glob": "~4.0.1", - "normalize-path": "~3.0.0", - "readdirp": "~3.6.0" - } - }, - "chrome-trace-event": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/chrome-trace-event/-/chrome-trace-event-1.0.3.tgz", - "integrity": "sha512-p3KULyQg4S7NIHixdwbGX+nFHkoBiA4YQmyWtjb8XngSKV124nJmRysgAeujbUVb15vh+RvFUfCPqU7rXk+hZg==" - }, - "cleave.js": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/cleave.js/-/cleave.js-1.6.0.tgz", - "integrity": "sha512-ivqesy3j5hQVG3gywPfwKPbi/7ZSftY/UNp5uphnqjr25yI2CP8FS2ODQPzuLXXnNLi29e2+PgPkkiKUXLs/Nw==" - }, - "clone-deep": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/clone-deep/-/clone-deep-4.0.1.tgz", - "integrity": "sha512-neHB9xuzh/wk0dIHweyAXv2aPGZIVk3pLMe+/RNzINf17fe0OG96QroktYAUm7SM1PBnzTabaLboqqxDyMU+SQ==", - "requires": { - "is-plain-object": "^2.0.4", - "kind-of": "^6.0.2", - "shallow-clone": "^3.0.0" - } - }, - "colorette": { - "version": "2.0.20", - "resolved": "https://registry.npmjs.org/colorette/-/colorette-2.0.20.tgz", - "integrity": "sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==" - }, - "combined-stream": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", - "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", - "requires": { - "delayed-stream": "~1.0.0" - } - }, - "commander": { - "version": "2.20.3", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz", - "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==" - }, - "compressible": { - "version": "2.0.18", - "resolved": "https://registry.npmjs.org/compressible/-/compressible-2.0.18.tgz", - "integrity": "sha512-AF3r7P5dWxL8MxyITRMlORQNaOA2IkAFaTr4k7BUumjPtRpGDTZpl0Pb1XCO6JeDCBdp126Cgs9sMxqSjgYyRg==", - "dev": true, - "requires": { - "mime-db": ">= 1.43.0 < 2" - } - }, - "compression": { - "version": "1.7.4", - "resolved": "https://registry.npmjs.org/compression/-/compression-1.7.4.tgz", - "integrity": "sha512-jaSIDzP9pZVS4ZfQ+TzvtiWhdpFhE2RDHz8QJkpX9SIpLq88VueF5jJw6t+6CUQcAoA6t+x89MLrWAqpfDE8iQ==", - "dev": true, - "requires": { - "accepts": "~1.3.5", - "bytes": "3.0.0", - "compressible": "~2.0.16", - "debug": "2.6.9", - "on-headers": "~1.0.2", - "safe-buffer": "5.1.2", - "vary": "~1.1.2" - }, - "dependencies": { - "safe-buffer": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "dev": true - } - } - }, - "concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", - "dev": true - }, - "connect-history-api-fallback": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/connect-history-api-fallback/-/connect-history-api-fallback-2.0.0.tgz", - "integrity": "sha512-U73+6lQFmfiNPrYbXqr6kZ1i1wiRqXnp2nhMsINseWXO8lDau0LGEffJ8kQi4EjLZympVgRdvqjAgiZ1tgzDDA==", - "dev": true - }, - "content-disposition": { - "version": "0.5.4", - "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.4.tgz", - "integrity": "sha512-FveZTNuGw04cxlAiWbzi6zTAL/lhehaWbTtgluJh4/E95DqMwTmha3KZN1aAWA8cFIhHzMZUvLevkw5Rqk+tSQ==", - "dev": true, - "requires": { - "safe-buffer": "5.2.1" - } - }, - "content-type": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.5.tgz", - "integrity": "sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==", - "dev": true - }, - "cookie": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.5.0.tgz", - "integrity": "sha512-YZ3GUyn/o8gfKJlnlX7g7xq4gyO6OSuhGPKaaGssGB2qgDUS0gPgtTvoyZLTt9Ab6dC4hfc9dV5arkvc/OCmrw==", - "dev": true - }, - "cookie-signature": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", - "integrity": "sha512-QADzlaHc8icV8I7vbaJXJwod9HWYp8uCqf1xa4OfNu1T7JVxQIrUgOWtHdNDtPiywmFbiS12VjotIXLrKM3orQ==", - "dev": true - }, - "core-util-is": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz", - "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==", - "dev": true - }, - "cross-spawn": { - "version": "7.0.3", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.3.tgz", - "integrity": "sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w==", - "requires": { - "path-key": "^3.1.0", - "shebang-command": "^2.0.0", - "which": "^2.0.1" - } - }, - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "dev": true, - "requires": { - "ms": "2.0.0" - } - }, - "default-gateway": { - "version": "6.0.3", - "resolved": "https://registry.npmjs.org/default-gateway/-/default-gateway-6.0.3.tgz", - "integrity": "sha512-fwSOJsbbNzZ/CUFpqFBqYfYNLj1NbMPm8MMCIzHjC83iSJRBEGmDUxU+WP661BaBQImeC2yHwXtz+P/O9o+XEg==", - "dev": true, - "requires": { - "execa": "^5.0.0" - } - }, - "define-lazy-prop": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/define-lazy-prop/-/define-lazy-prop-2.0.0.tgz", - "integrity": "sha512-Ds09qNh8yw3khSjiJjiUInaGX9xlqZDY7JVryGxdxV7NPeuqQfplOpQ66yJFZut3jLa5zOwkXw1g9EI2uKh4Og==", - "dev": true - }, - "delayed-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==" - }, - "depd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", - "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==", - "dev": true - }, - "destroy": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.2.0.tgz", - "integrity": "sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==", - "dev": true - }, - "detect-node": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/detect-node/-/detect-node-2.1.0.tgz", - "integrity": "sha512-T0NIuQpnTvFDATNuHN5roPwSBG83rFsuO+MXXH9/3N1eFbn4wcPjttvjMLEPWJ0RGUYgQE7cGgS3tNxbqCGM7g==", - "dev": true - }, - "dns-equal": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/dns-equal/-/dns-equal-1.0.0.tgz", - "integrity": "sha512-z+paD6YUQsk+AbGCEM4PrOXSss5gd66QfcVBFTKR/HpFL9jCqikS94HYwKww6fQyO7IxrIIyUu+g0Ka9tUS2Cg==", - "dev": true - }, - "dns-packet": { - "version": "5.6.1", - "resolved": "https://registry.npmjs.org/dns-packet/-/dns-packet-5.6.1.tgz", - "integrity": "sha512-l4gcSouhcgIKRvyy99RNVOgxXiicE+2jZoNmaNmZ6JXiGajBOJAesk1OBlJuM5k2c+eudGdLxDqXuPCKIj6kpw==", - "dev": true, - "requires": { - "@leichtgewicht/ip-codec": "^2.0.1" - } - }, - "ee-first": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", - "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==", - "dev": true - }, - "electron-to-chromium": { - "version": "1.4.554", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.554.tgz", - "integrity": "sha512-Q0umzPJjfBrrj8unkONTgbKQXzXRrH7sVV7D9ea2yBV3Oaogz991yhbpfvo2LMNkJItmruXTEzVpP9cp7vaIiQ==" - }, - "encodeurl": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", - "integrity": "sha512-TPJXq8JqFaVYm2CWmPvnP2Iyo4ZSM7/QKcSmuMLDObfpH5fi7RUGmd/rTDf+rut/saiDiQEeVTNgAmJEdAOx0w==", - "dev": true - }, - "enhanced-resolve": { - "version": "5.15.0", - "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.15.0.tgz", - "integrity": "sha512-LXYT42KJ7lpIKECr2mAXIaMldcNCh/7E0KBKOu4KSfkHmP+mZmSs+8V5gBAqisWBy0OO4W5Oyys0GO1Y8KtdKg==", - "requires": { - "graceful-fs": "^4.2.4", - "tapable": "^2.2.0" - } - }, - "envinfo": { - "version": "7.10.0", - "resolved": "https://registry.npmjs.org/envinfo/-/envinfo-7.10.0.tgz", - "integrity": "sha512-ZtUjZO6l5mwTHvc1L9+1q5p/R3wTopcfqMW8r5t8SJSKqeVI/LtajORwRFEKpEFuekjD0VBjwu1HMxL4UalIRw==" - }, - "es-module-lexer": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-1.3.1.tgz", - "integrity": "sha512-JUFAyicQV9mXc3YRxPnDlrfBKpqt6hUYzz9/boprUJHs4e4KVr3XwOF70doO6gwXUor6EWZJAyWAfKki84t20Q==" - }, - "escalade": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", - "integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==" - }, - "escape-html": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", - "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==", - "dev": true - }, - "eslint-scope": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", - "integrity": "sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==", - "requires": { - "esrecurse": "^4.3.0", - "estraverse": "^4.1.1" - } - }, - "esrecurse": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", - "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", - "requires": { - "estraverse": "^5.2.0" - }, - "dependencies": { - "estraverse": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", - "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==" - } - } - }, - "estraverse": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.3.0.tgz", - "integrity": "sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==" - }, - "etag": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", - "integrity": "sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==", - "dev": true - }, - "eventemitter3": { - "version": "4.0.7", - "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-4.0.7.tgz", - "integrity": "sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw==", - "dev": true - }, - "events": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/events/-/events-3.3.0.tgz", - "integrity": "sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==" - }, - "execa": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/execa/-/execa-5.1.1.tgz", - "integrity": "sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==", - "dev": true, - "requires": { - "cross-spawn": "^7.0.3", - "get-stream": "^6.0.0", - "human-signals": "^2.1.0", - "is-stream": "^2.0.0", - "merge-stream": "^2.0.0", - "npm-run-path": "^4.0.1", - "onetime": "^5.1.2", - "signal-exit": "^3.0.3", - "strip-final-newline": "^2.0.0" - } - }, - "express": { - "version": "4.18.2", - "resolved": "https://registry.npmjs.org/express/-/express-4.18.2.tgz", - "integrity": "sha512-5/PsL6iGPdfQ/lKM1UuielYgv3BUoJfz1aUwU9vHZ+J7gyvwdQXFEBIEIaxeGf0GIcreATNyBExtalisDbuMqQ==", - "dev": true, - "requires": { - "accepts": "~1.3.8", - "array-flatten": "1.1.1", - "body-parser": "1.20.1", - "content-disposition": "0.5.4", - "content-type": "~1.0.4", - "cookie": "0.5.0", - "cookie-signature": "1.0.6", - "debug": "2.6.9", - "depd": "2.0.0", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "finalhandler": "1.2.0", - "fresh": "0.5.2", - "http-errors": "2.0.0", - "merge-descriptors": "1.0.1", - "methods": "~1.1.2", - "on-finished": "2.4.1", - "parseurl": "~1.3.3", - "path-to-regexp": "0.1.7", - "proxy-addr": "~2.0.7", - "qs": "6.11.0", - "range-parser": "~1.2.1", - "safe-buffer": "5.2.1", - "send": "0.18.0", - "serve-static": "1.15.0", - "setprototypeof": "1.2.0", - "statuses": "2.0.1", - "type-is": "~1.6.18", - "utils-merge": "1.0.1", - "vary": "~1.1.2" - }, - "dependencies": { - "array-flatten": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", - "integrity": "sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg==", - "dev": true - } - } - }, - "fast-deep-equal": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", - "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==" - }, - "fast-json-stable-stringify": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", - "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==" - }, - "fastest-levenshtein": { - "version": "1.0.16", - "resolved": "https://registry.npmjs.org/fastest-levenshtein/-/fastest-levenshtein-1.0.16.tgz", - "integrity": "sha512-eRnCtTTtGZFpQCwhJiUOuxPQWRXVKYDn0b2PeHfXL6/Zi53SLAzAHfVhVWK2AryC/WH05kGfxhFIPvTF0SXQzg==" - }, - "faye-websocket": { - "version": "0.11.4", - "resolved": "https://registry.npmjs.org/faye-websocket/-/faye-websocket-0.11.4.tgz", - "integrity": "sha512-CzbClwlXAuiRQAlUyfqPgvPoNKTckTPGfwZV4ZdAhVcP2lh9KUxJg2b5GkE7XbjKQ3YJnQ9z6D9ntLAlB+tP8g==", - "dev": true, - "requires": { - "websocket-driver": ">=0.5.1" - } - }, - "fill-range": { - "version": "7.0.1", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.0.1.tgz", - "integrity": "sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==", - "dev": true, - "requires": { - "to-regex-range": "^5.0.1" - } - }, - "finalhandler": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.2.0.tgz", - "integrity": "sha512-5uXcUVftlQMFnWC9qu/svkWv3GTd2PfUhK/3PLkYNAe7FbqJMt3515HaxE6eRL74GdsriiwujiawdaB1BpEISg==", - "dev": true, - "requires": { - "debug": "2.6.9", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "on-finished": "2.4.1", - "parseurl": "~1.3.3", - "statuses": "2.0.1", - "unpipe": "~1.0.0" - } - }, - "find-up": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", - "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", - "requires": { - "locate-path": "^5.0.0", - "path-exists": "^4.0.0" - } - }, - "flatpickr": { - "version": "4.6.13", - "resolved": "https://registry.npmjs.org/flatpickr/-/flatpickr-4.6.13.tgz", - "integrity": "sha512-97PMG/aywoYpB4IvbvUJi0RQi8vearvU0oov1WW3k0WZPBMrTQVqekSX5CjSG/M4Q3i6A/0FKXC7RyAoAUUSPw==" - }, - "follow-redirects": { - "version": "1.15.2", - "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.2.tgz", - "integrity": "sha512-VQLG33o04KaQ8uYi2tVNbdrWp1QWxNNea+nmIB4EVM28v0hmP17z7aG1+wAkNzVq4KeXTq3221ye5qTJP91JwA==" - }, - "form-data": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.0.tgz", - "integrity": "sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==", - "requires": { - "asynckit": "^0.4.0", - "combined-stream": "^1.0.8", - "mime-types": "^2.1.12" - } - }, - "forwarded": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", - "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==", - "dev": true - }, - "fresh": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", - "integrity": "sha512-zJ2mQYM18rEFOudeV4GShTGIQ7RbzA7ozbU9I/XBpm7kqgMywgmylMwXHxZJmkVoYkna9d2pVXVXPdYTP9ej8Q==", - "dev": true - }, - "fs-monkey": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/fs-monkey/-/fs-monkey-1.0.5.tgz", - "integrity": "sha512-8uMbBjrhzW76TYgEV27Y5E//W2f/lTFmx78P2w19FZSxarhI/798APGQyuGCwmkNxgwGRhrLfvWyLBvNtuOmew==", - "dev": true - }, - "fs.realpath": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", - "dev": true - }, - "fsevents": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", - "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", - "dev": true, - "optional": true - }, - "function-bind": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", - "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==" - }, - "get-intrinsic": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.1.tgz", - "integrity": "sha512-2DcsyfABl+gVHEfCOaTrWgyt+tb6MSEGmKq+kI5HwLbIYgjgmMcV8KQ41uaKz1xxUcn9tJtgFbQUEVcEbd0FYw==", - "dev": true, - "requires": { - "function-bind": "^1.1.1", - "has": "^1.0.3", - "has-proto": "^1.0.1", - "has-symbols": "^1.0.3" - } - }, - "get-stream": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-6.0.1.tgz", - "integrity": "sha512-ts6Wi+2j3jQjqi70w5AlN8DFnkSwC+MqmxEzdEALB2qXZYV3X/b1CTfgPLGJNMeAWxdPfU8FO1ms3NUfaHCPYg==", - "dev": true - }, - "glob": { - "version": "7.2.3", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", - "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", - "dev": true, - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.1.1", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - }, - "glob-parent": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", - "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", - "dev": true, - "requires": { - "is-glob": "^4.0.1" - } - }, - "glob-to-regexp": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/glob-to-regexp/-/glob-to-regexp-0.4.1.tgz", - "integrity": "sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==" - }, - "graceful-fs": { - "version": "4.2.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.11.tgz", - "integrity": "sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==" - }, - "handle-thing": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/handle-thing/-/handle-thing-2.0.1.tgz", - "integrity": "sha512-9Qn4yBxelxoh2Ow62nP+Ka/kMnOXRi8BXnRaUwezLNhqelnN49xKz4F/dPP8OYLxLxq6JDtZb2i9XznUQbNPTg==", - "dev": true - }, - "has": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", - "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", - "requires": { - "function-bind": "^1.1.1" - } - }, - "has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==" - }, - "has-proto": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.0.1.tgz", - "integrity": "sha512-7qE+iP+O+bgF9clE5+UoBFzE65mlBiVj3tKCrlNQ0Ogwm0BjpT/gK4SlLYDMybDh5I3TCTKnPPa0oMG7JDYrhg==", - "dev": true - }, - "has-symbols": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", - "integrity": "sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==", - "dev": true - }, - "hpack.js": { - "version": "2.1.6", - "resolved": "https://registry.npmjs.org/hpack.js/-/hpack.js-2.1.6.tgz", - "integrity": "sha512-zJxVehUdMGIKsRaNt7apO2Gqp0BdqW5yaiGHXXmbpvxgBYVZnAql+BJb4RO5ad2MgpbZKn5G6nMnegrH1FcNYQ==", - "dev": true, - "requires": { - "inherits": "^2.0.1", - "obuf": "^1.0.0", - "readable-stream": "^2.0.1", - "wbuf": "^1.1.0" - }, - "dependencies": { - "readable-stream": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", - "integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==", - "dev": true, - "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.1.1", - "util-deprecate": "~1.0.1" - } - }, - "safe-buffer": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "dev": true - } - } - }, - "html-entities": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/html-entities/-/html-entities-2.4.0.tgz", - "integrity": "sha512-igBTJcNNNhvZFRtm8uA6xMY6xYleeDwn3PeBCkDz7tHttv4F2hsDI2aPgNERWzvRcNYHNT3ymRaQzllmXj4YsQ==", - "dev": true - }, - "http-deceiver": { - "version": "1.2.7", - "resolved": "https://registry.npmjs.org/http-deceiver/-/http-deceiver-1.2.7.tgz", - "integrity": "sha512-LmpOGxTfbpgtGVxJrj5k7asXHCgNZp5nLfp+hWc8QQRqtb7fUy6kRY3BO1h9ddF6yIPYUARgxGOwB42DnxIaNw==", - "dev": true - }, - "http-errors": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.0.tgz", - "integrity": "sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==", - "dev": true, - "requires": { - "depd": "2.0.0", - "inherits": "2.0.4", - "setprototypeof": "1.2.0", - "statuses": "2.0.1", - "toidentifier": "1.0.1" - } - }, - "http-parser-js": { - "version": "0.5.8", - "resolved": "https://registry.npmjs.org/http-parser-js/-/http-parser-js-0.5.8.tgz", - "integrity": "sha512-SGeBX54F94Wgu5RH3X5jsDtf4eHyRogWX1XGT3b4HuW3tQPM4AaBzoUji/4AAJNXCEOWZ5O0DgZmJw1947gD5Q==", - "dev": true - }, - "http-proxy": { - "version": "1.18.1", - "resolved": "https://registry.npmjs.org/http-proxy/-/http-proxy-1.18.1.tgz", - "integrity": "sha512-7mz/721AbnJwIVbnaSv1Cz3Am0ZLT/UBwkC92VlxhXv/k/BBQfM2fXElQNC27BVGr0uwUpplYPQM9LnaBMR5NQ==", - "dev": true, - "requires": { - "eventemitter3": "^4.0.0", - "follow-redirects": "^1.0.0", - "requires-port": "^1.0.0" - } - }, - "http-proxy-middleware": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/http-proxy-middleware/-/http-proxy-middleware-2.0.6.tgz", - "integrity": "sha512-ya/UeJ6HVBYxrgYotAZo1KvPWlgB48kUJLDePFeneHsVujFaW5WNj2NgWCAE//B1Dl02BIfYlpNgBy8Kf8Rjmw==", - "dev": true, - "requires": { - "@types/http-proxy": "^1.17.8", - "http-proxy": "^1.18.1", - "is-glob": "^4.0.1", - "is-plain-obj": "^3.0.0", - "micromatch": "^4.0.2" - } - }, - "human-signals": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/human-signals/-/human-signals-2.1.0.tgz", - "integrity": "sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw==", - "dev": true - }, - "iconv-lite": { - "version": "0.4.24", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", - "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", - "dev": true, - "requires": { - "safer-buffer": ">= 2.1.2 < 3" - } - }, - "import-local": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/import-local/-/import-local-3.1.0.tgz", - "integrity": "sha512-ASB07uLtnDs1o6EHjKpX34BKYDSqnFerfTOJL2HvMqF70LnxpjkzDB8J44oT9pu4AMPkQwf8jl6szgvNd2tRIg==", - "requires": { - "pkg-dir": "^4.2.0", - "resolve-cwd": "^3.0.0" - } - }, - "inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==", - "dev": true, - "requires": { - "once": "^1.3.0", - "wrappy": "1" - } - }, - "inherits": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", - "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", - "dev": true - }, - "interpret": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/interpret/-/interpret-3.1.1.tgz", - "integrity": "sha512-6xwYfHbajpoF0xLW+iwLkhwgvLoZDfjYfoFNu8ftMoXINzwuymNLd9u/KmwtdT2GbR+/Cz66otEGEVVUHX9QLQ==" - }, - "ipaddr.js": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-2.1.0.tgz", - "integrity": "sha512-LlbxQ7xKzfBusov6UMi4MFpEg0m+mAm9xyNGEduwXMEDuf4WfzB/RZwMVYEd7IKGvh4IUkEXYxtAVu9T3OelJQ==", - "dev": true - }, - "is-binary-path": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-2.1.0.tgz", - "integrity": "sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==", - "dev": true, - "requires": { - "binary-extensions": "^2.0.0" - } - }, - "is-core-module": { - "version": "2.13.0", - "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.13.0.tgz", - "integrity": "sha512-Z7dk6Qo8pOCp3l4tsX2C5ZVas4V+UxwQodwZhLopL91TX8UyyHEXafPcyoeeWuLrwzHcr3igO78wNLwHJHsMCQ==", - "requires": { - "has": "^1.0.3" - } - }, - "is-docker": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/is-docker/-/is-docker-2.2.1.tgz", - "integrity": "sha512-F+i2BKsFrH66iaUFc0woD8sLy8getkwTwtOBjvs56Cx4CgJDeKQeqfz8wAYiSb8JOprWhHH5p77PbmYCvvUuXQ==", - "dev": true - }, - "is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==", - "dev": true - }, - "is-glob": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", - "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", - "dev": true, - "requires": { - "is-extglob": "^2.1.1" - } - }, - "is-number": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", - "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", - "dev": true - }, - "is-plain-obj": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-3.0.0.tgz", - "integrity": "sha512-gwsOE28k+23GP1B6vFl1oVh/WOzmawBrKwo5Ev6wMKzPkaXaCDIQKzLnvsA42DRlbVTWorkgTKIviAKCWkfUwA==", - "dev": true - }, - "is-plain-object": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", - "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", - "requires": { - "isobject": "^3.0.1" - } - }, - "is-stream": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", - "integrity": "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==", - "dev": true - }, - "is-wsl": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/is-wsl/-/is-wsl-2.2.0.tgz", - "integrity": "sha512-fKzAra0rGJUUBwGBgNkHZuToZcn+TtXHpeCgmkMJMMYx1sQDYaCSyjJBSCa2nH1DGm7s3n1oBnohoVTBaN7Lww==", - "dev": true, - "requires": { - "is-docker": "^2.0.0" - } - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", - "dev": true - }, - "isexe": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==" - }, - "isobject": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", - "integrity": "sha512-WhB9zCku7EGTj/HQQRz5aUQEUeoQZH2bWcltRErOpymJ4boYE6wL9Tbr23krRPSZ+C5zqNSrSw+Cc7sZZ4b7vg==" - }, - "izitoast": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/izitoast/-/izitoast-1.4.0.tgz", - "integrity": "sha512-Oc1X2wiQtPp39i5VpIjf3GJf5sfCtHKXZ5szx7RareyEeFLUlcEW0FSfBni28+Ul6KNKZRKzhVuWzSP4Xngh0w==" - }, - "jest-worker": { - "version": "27.5.1", - "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.5.1.tgz", - "integrity": "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==", - "requires": { - "@types/node": "*", - "merge-stream": "^2.0.0", - "supports-color": "^8.0.0" - } - }, - "jquery": { - "version": "3.7.1", - "resolved": "https://registry.npmjs.org/jquery/-/jquery-3.7.1.tgz", - "integrity": "sha512-m4avr8yL8kmFN8psrbFFFmB/If14iN5o9nw/NgnnM+kybDJpRsAynV2BsfpTYrTRysYUdADVD7CkUUizgkpLfg==" - }, - "jquery.nicescroll": { - "version": "3.7.6", - "resolved": "https://registry.npmjs.org/jquery.nicescroll/-/jquery.nicescroll-3.7.6.tgz", - "integrity": "sha512-H4XOzQDw/fJIFftYGemNDAr9sz52zr35+JEubsTNGrTAtxQra4qnu6UnOe+avEHVPy8HnyoHgIpvPXedGSCfTw==", - "requires": { - "jquery": ">=1.8.3" - } - }, - "json-parse-even-better-errors": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz", - "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==" - }, - "json-schema-traverse": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", - "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==", - "dev": true - }, - "kind-of": { - "version": "6.0.3", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.3.tgz", - "integrity": "sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw==" - }, - "launch-editor": { - "version": "2.6.1", - "resolved": "https://registry.npmjs.org/launch-editor/-/launch-editor-2.6.1.tgz", - "integrity": "sha512-eB/uXmFVpY4zezmGp5XtU21kwo7GBbKB+EQ+UZeWtGb9yAM5xt/Evk+lYH3eRNAtId+ej4u7TYPFZ07w4s7rRw==", - "dev": true, - "requires": { - "picocolors": "^1.0.0", - "shell-quote": "^1.8.1" - } - }, - "loader-runner": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/loader-runner/-/loader-runner-4.3.0.tgz", - "integrity": "sha512-3R/1M+yS3j5ou80Me59j7F9IMs4PXs3VqRrm0TU3AbKPxlmpoY1TNscJV/oGJXo8qCatFGTfDbY6W6ipGOYXfg==" - }, - "locate-path": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", - "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", - "requires": { - "p-locate": "^4.1.0" - } - }, - "media-typer": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", - "integrity": "sha512-dq+qelQ9akHpcOl/gUVRTxVIOkAJ1wR3QAvb4RsVjS8oVoFjDGTc679wJYmUmknUF5HwMLOgb5O+a3KxfWapPQ==", - "dev": true - }, - "memfs": { - "version": "3.5.3", - "resolved": "https://registry.npmjs.org/memfs/-/memfs-3.5.3.tgz", - "integrity": "sha512-UERzLsxzllchadvbPs5aolHh65ISpKpM+ccLbOJ8/vvpBKmAWf+la7dXFy7Mr0ySHbdHrFv5kGFCUHHe6GFEmw==", - "dev": true, - "requires": { - "fs-monkey": "^1.0.4" - } - }, - "merge-descriptors": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", - "integrity": "sha512-cCi6g3/Zr1iqQi6ySbseM1Xvooa98N0w31jzUYrXPX2xqObmFGHJ0tQ5u74H3mVh7wLouTseZyYIq39g8cNp1w==", - "dev": true - }, - "merge-stream": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", - "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==" - }, - "methods": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", - "integrity": "sha512-iclAHeNqNm68zFtnZ0e+1L2yUIdvzNoauKU4WBA3VvH/vPFieF7qfRlwUZU+DA9P9bPXIS90ulxoUoCH23sV2w==", - "dev": true - }, - "micromatch": { - "version": "4.0.5", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.5.tgz", - "integrity": "sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA==", - "dev": true, - "requires": { - "braces": "^3.0.2", - "picomatch": "^2.3.1" - } - }, - "mime": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", - "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", - "dev": true - }, - "mime-db": { - "version": "1.52.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", - "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==" - }, - "mime-types": { - "version": "2.1.35", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", - "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", - "requires": { - "mime-db": "1.52.0" - } - }, - "mimic-fn": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-2.1.0.tgz", - "integrity": "sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg==", - "dev": true - }, - "minimalistic-assert": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz", - "integrity": "sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A==", - "dev": true - }, - "minimatch": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", - "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", - "dev": true, - "requires": { - "brace-expansion": "^1.1.7" - } - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", - "dev": true - }, - "multicast-dns": { - "version": "7.2.5", - "resolved": "https://registry.npmjs.org/multicast-dns/-/multicast-dns-7.2.5.tgz", - "integrity": "sha512-2eznPJP8z2BFLX50tf0LuODrpINqP1RVIm/CObbTcBRITQgmC/TjcREF1NeTBzIcR5XO/ukWo+YHOjBbFwIupg==", - "dev": true, - "requires": { - "dns-packet": "^5.2.2", - "thunky": "^1.0.2" - } - }, - "negotiator": { - "version": "0.6.3", - "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.3.tgz", - "integrity": "sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==", - "dev": true - }, - "neo-async": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.2.tgz", - "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==" - }, - "node-forge": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/node-forge/-/node-forge-1.3.1.tgz", - "integrity": "sha512-dPEtOeMvF9VMcYV/1Wb8CPoVAXtp6MKMlcbAt4ddqmGqUJ6fQZFXkNZNkNlfevtNkGtaSoXf/vNNNSvgrdXwtA==", - "dev": true - }, - "node-releases": { - "version": "2.0.13", - "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.13.tgz", - "integrity": "sha512-uYr7J37ae/ORWdZeQ1xxMJe3NtdmqMC/JZK+geofDrkLUApKRHPd18/TxtBOJ4A0/+uUIliorNrfYV6s1b02eQ==" - }, - "normalize-path": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", - "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", - "dev": true - }, - "npm-run-path": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-4.0.1.tgz", - "integrity": "sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw==", - "dev": true, - "requires": { - "path-key": "^3.0.0" - } - }, - "object-inspect": { - "version": "1.12.3", - "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.12.3.tgz", - "integrity": "sha512-geUvdk7c+eizMNUDkRpW1wJwgfOiOeHbxBR/hLXK1aT6zmVSO0jsQcs7fj6MGw89jC/cjGfLcNOrtMYtGqm81g==", - "dev": true - }, - "obuf": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/obuf/-/obuf-1.1.2.tgz", - "integrity": "sha512-PX1wu0AmAdPqOL1mWhqmlOd8kOIZQwGZw6rh7uby9fTc5lhaOWFLX3I6R1hrF9k3zUY40e6igsLGkDXK92LJNg==", - "dev": true - }, - "on-finished": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.4.1.tgz", - "integrity": "sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==", - "dev": true, - "requires": { - "ee-first": "1.1.1" - } - }, - "on-headers": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/on-headers/-/on-headers-1.0.2.tgz", - "integrity": "sha512-pZAE+FJLoyITytdqK0U5s+FIpjN0JP3OzFi/u8Rx+EV5/W+JTWGXG8xFzevE7AjBfDqHv/8vL8qQsIhHnqRkrA==", - "dev": true - }, - "once": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==", - "dev": true, - "requires": { - "wrappy": "1" - } - }, - "onetime": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/onetime/-/onetime-5.1.2.tgz", - "integrity": "sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==", - "dev": true, - "requires": { - "mimic-fn": "^2.1.0" - } - }, - "open": { - "version": "8.4.2", - "resolved": "https://registry.npmjs.org/open/-/open-8.4.2.tgz", - "integrity": "sha512-7x81NCL719oNbsq/3mh+hVrAWmFuEYUqrq/Iw3kUzH8ReypT9QQ0BLoJS7/G9k6N81XjW4qHWtjWwe/9eLy1EQ==", - "dev": true, - "requires": { - "define-lazy-prop": "^2.0.0", - "is-docker": "^2.1.1", - "is-wsl": "^2.2.0" - } - }, - "p-limit": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", - "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", - "requires": { - "p-try": "^2.0.0" - } - }, - "p-locate": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz", - "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==", - "requires": { - "p-limit": "^2.2.0" - } - }, - "p-retry": { - "version": "4.6.2", - "resolved": "https://registry.npmjs.org/p-retry/-/p-retry-4.6.2.tgz", - "integrity": "sha512-312Id396EbJdvRONlngUx0NydfrIQ5lsYu0znKVUzVvArzEIt08V1qhtyESbGVd1FGX7UKtiFp5uwKZdM8wIuQ==", - "dev": true, - "requires": { - "@types/retry": "0.12.0", - "retry": "^0.13.1" - } - }, - "p-try": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz", - "integrity": "sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==" - }, - "parseurl": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", - "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==", - "dev": true - }, - "path-exists": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", - "integrity": "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==" - }, - "path-is-absolute": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==", - "dev": true - }, - "path-key": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", - "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==" - }, - "path-parse": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz", - "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==" - }, - "path-to-regexp": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", - "integrity": "sha512-5DFkuoqlv1uYQKxy8omFBeJPQcdoE07Kv2sferDCrAq1ohOU+MSDswDIbnx3YAM60qIOnYa53wBhXW0EbMonrQ==", - "dev": true - }, - "picocolors": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.0.0.tgz", - "integrity": "sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==" - }, - "picomatch": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", - "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", - "dev": true - }, - "pkg-dir": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-4.2.0.tgz", - "integrity": "sha512-HRDzbaKjC+AOWVXxAU/x54COGeIv9eb+6CkDSQoNTt4XyWoIJvuPsXizxu/Fr23EiekbtZwmh1IcIG/l/a10GQ==", - "requires": { - "find-up": "^4.0.0" - } - }, - "popper.js": { - "version": "1.16.1", - "resolved": "https://registry.npmjs.org/popper.js/-/popper.js-1.16.1.tgz", - "integrity": "sha512-Wb4p1J4zyFTbM+u6WuO4XstYx4Ky9Cewe4DWrel7B0w6VVICvPwdOpotjzcf6eD8TsckVnIMNONQyPIUFOUbCQ==" - }, - "process-nextick-args": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", - "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==", - "dev": true - }, - "proxy-addr": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz", - "integrity": "sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==", - "dev": true, - "requires": { - "forwarded": "0.2.0", - "ipaddr.js": "1.9.1" - }, - "dependencies": { - "ipaddr.js": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", - "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==", - "dev": true - } - } - }, - "proxy-from-env": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", - "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==" - }, - "punycode": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.0.tgz", - "integrity": "sha512-rRV+zQD8tVFys26lAGR9WUuS4iUAngJScM+ZRSKtvl5tKeZ2t5bvdNFdNHBW9FWR4guGHlgmsZ1G7BSm2wTbuA==" - }, - "qs": { - "version": "6.11.0", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.11.0.tgz", - "integrity": "sha512-MvjoMCJwEarSbUYk5O+nmoSzSutSsTwF85zcHPQ9OrlFoZOYIjaqBAJIqIXjptyD5vThxGq52Xu/MaJzRkIk4Q==", - "dev": true, - "requires": { - "side-channel": "^1.0.4" - } - }, - "randombytes": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz", - "integrity": "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==", - "requires": { - "safe-buffer": "^5.1.0" - } - }, - "range-parser": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", - "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==", - "dev": true - }, - "raw-body": { - "version": "2.5.1", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.5.1.tgz", - "integrity": "sha512-qqJBtEyVgS0ZmPGdCFPWJ3FreoqvG4MVQln/kCgF7Olq95IbOp0/BWyMwbdtn4VTvkM8Y7khCQ2Xgk/tcrCXig==", - "dev": true, - "requires": { - "bytes": "3.1.2", - "http-errors": "2.0.0", - "iconv-lite": "0.4.24", - "unpipe": "1.0.0" - }, - "dependencies": { - "bytes": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", - "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", - "dev": true - } - } - }, - "readable-stream": { - "version": "3.6.2", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", - "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", - "dev": true, - "requires": { - "inherits": "^2.0.3", - "string_decoder": "^1.1.1", - "util-deprecate": "^1.0.1" - } - }, - "readdirp": { - "version": "3.6.0", - "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", - "integrity": "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==", - "dev": true, - "requires": { - "picomatch": "^2.2.1" - } - }, - "rechoir": { - "version": "0.8.0", - "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.8.0.tgz", - "integrity": "sha512-/vxpCXddiX8NGfGO/mTafwjq4aFa/71pvamip0++IQk3zG8cbCj0fifNPrjjF1XMXUne91jL9OoxmdykoEtifQ==", - "requires": { - "resolve": "^1.20.0" - } - }, - "require-from-string": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz", - "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==", - "dev": true - }, - "requires-port": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/requires-port/-/requires-port-1.0.0.tgz", - "integrity": "sha512-KigOCHcocU3XODJxsu8i/j8T9tzT4adHiecwORRQ0ZZFcp7ahwXuRU1m+yuO90C5ZUyGeGfocHDI14M3L3yDAQ==", - "dev": true - }, - "resolve": { - "version": "1.22.8", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.8.tgz", - "integrity": "sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw==", - "requires": { - "is-core-module": "^2.13.0", - "path-parse": "^1.0.7", - "supports-preserve-symlinks-flag": "^1.0.0" - } - }, - "resolve-cwd": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/resolve-cwd/-/resolve-cwd-3.0.0.tgz", - "integrity": "sha512-OrZaX2Mb+rJCpH/6CpSqt9xFVpN++x01XnN2ie9g6P5/3xelLAkXWVADpdz1IHD/KFfEXyE6V0U01OQ3UO2rEg==", - "requires": { - "resolve-from": "^5.0.0" - } - }, - "resolve-from": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-5.0.0.tgz", - "integrity": "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==" - }, - "retry": { - "version": "0.13.1", - "resolved": "https://registry.npmjs.org/retry/-/retry-0.13.1.tgz", - "integrity": "sha512-XQBQ3I8W1Cge0Seh+6gjj03LbmRFWuoszgK9ooCpwYIrhhoO80pfq4cUkU5DkknwfOfFteRwlZ56PYOGYyFWdg==", - "dev": true - }, - "rimraf": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", - "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", - "dev": true, - "requires": { - "glob": "^7.1.3" - } - }, - "safe-buffer": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", - "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==" - }, - "safer-buffer": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", - "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", - "dev": true - }, - "schema-utils": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.3.0.tgz", - "integrity": "sha512-pN/yOAvcC+5rQ5nERGuwrjLlYvLTbCibnZ1I7B1LaiAz9BRBlE9GMgE/eqV30P7aJQUf7Ddimy/RsbYO/GrVGg==", - "requires": { - "@types/json-schema": "^7.0.8", - "ajv": "^6.12.5", - "ajv-keywords": "^3.5.2" - }, - "dependencies": { - "ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "requires": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - } - }, - "ajv-keywords": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", - "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==" - }, - "json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==" - } - } - }, - "select-hose": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/select-hose/-/select-hose-2.0.0.tgz", - "integrity": "sha512-mEugaLK+YfkijB4fx0e6kImuJdCIt2LxCRcbEYPqRGCs4F2ogyfZU5IAZRdjCP8JPq2AtdNoC/Dux63d9Kiryg==", - "dev": true - }, - "select2": { - "version": "4.0.13", - "resolved": "https://registry.npmjs.org/select2/-/select2-4.0.13.tgz", - "integrity": "sha512-1JeB87s6oN/TDxQQYCvS5EFoQyvV6eYMZZ0AeA4tdFDYWN3BAGZ8npr17UBFddU0lgAt3H0yjX3X6/ekOj1yjw==" - }, - "selfsigned": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/selfsigned/-/selfsigned-2.1.1.tgz", - "integrity": "sha512-GSL3aowiF7wa/WtSFwnUrludWFoNhftq8bUkH9pkzjpN2XSPOAYEgg6e0sS9s0rZwgJzJiQRPU18A6clnoW5wQ==", - "dev": true, - "requires": { - "node-forge": "^1" - } - }, - "send": { - "version": "0.18.0", - "resolved": "https://registry.npmjs.org/send/-/send-0.18.0.tgz", - "integrity": "sha512-qqWzuOjSFOuqPjFe4NOsMLafToQQwBSOEpS+FwEt3A2V3vKubTquT3vmLTQpFgMXp8AlFWFuP1qKaJZOtPpVXg==", - "dev": true, - "requires": { - "debug": "2.6.9", - "depd": "2.0.0", - "destroy": "1.2.0", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "fresh": "0.5.2", - "http-errors": "2.0.0", - "mime": "1.6.0", - "ms": "2.1.3", - "on-finished": "2.4.1", - "range-parser": "~1.2.1", - "statuses": "2.0.1" - }, - "dependencies": { - "ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", - "dev": true - } - } - }, - "serialize-javascript": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-6.0.1.tgz", - "integrity": "sha512-owoXEFjWRllis8/M1Q+Cw5k8ZH40e3zhp/ovX+Xr/vi1qj6QesbyXXViFbpNvWvPNAD62SutwEXavefrLJWj7w==", - "requires": { - "randombytes": "^2.1.0" - } - }, - "serve-index": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/serve-index/-/serve-index-1.9.1.tgz", - "integrity": "sha512-pXHfKNP4qujrtteMrSBb0rc8HJ9Ms/GrXwcUtUtD5s4ewDJI8bT3Cz2zTVRMKtri49pLx2e0Ya8ziP5Ya2pZZw==", - "dev": true, - "requires": { - "accepts": "~1.3.4", - "batch": "0.6.1", - "debug": "2.6.9", - "escape-html": "~1.0.3", - "http-errors": "~1.6.2", - "mime-types": "~2.1.17", - "parseurl": "~1.3.2" - }, - "dependencies": { - "depd": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", - "integrity": "sha512-7emPTl6Dpo6JRXOXjLRxck+FlLRX5847cLKEn00PLAgc3g2hTZZgr+e4c2v6QpSmLeFP3n5yUo7ft6avBK/5jQ==", - "dev": true - }, - "http-errors": { - "version": "1.6.3", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", - "integrity": "sha512-lks+lVC8dgGyh97jxvxeYTWQFvh4uw4yC12gVl63Cg30sjPX4wuGcdkICVXDAESr6OJGjqGA8Iz5mkeN6zlD7A==", - "dev": true, - "requires": { - "depd": "~1.1.2", - "inherits": "2.0.3", - "setprototypeof": "1.1.0", - "statuses": ">= 1.4.0 < 2" - } - }, - "inherits": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "integrity": "sha512-x00IRNXNy63jwGkJmzPigoySHbaqpNuzKbBOmzK+g2OdZpQ9w+sxCN+VSB3ja7IAge2OP2qpfxTjeNcyjmW1uw==", - "dev": true - }, - "setprototypeof": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", - "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==", - "dev": true - }, - "statuses": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", - "integrity": "sha512-OpZ3zP+jT1PI7I8nemJX4AKmAX070ZkYPVWV/AaKTJl+tXCTGyVdC1a4SL8RUQYEwk/f34ZX8UTykN68FwrqAA==", - "dev": true - } - } - }, - "serve-static": { - "version": "1.15.0", - "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.15.0.tgz", - "integrity": "sha512-XGuRDNjXUijsUL0vl6nSD7cwURuzEgglbOaFuZM9g3kwDXOWVTck0jLzjPzGD+TazWbboZYu52/9/XPdUgne9g==", - "dev": true, - "requires": { - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "parseurl": "~1.3.3", - "send": "0.18.0" - } - }, - "setprototypeof": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", - "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==", - "dev": true - }, - "shallow-clone": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/shallow-clone/-/shallow-clone-3.0.1.tgz", - "integrity": "sha512-/6KqX+GVUdqPuPPd2LxDDxzX6CAbjJehAAOKlNpqqUpAqPM6HeL8f+o3a+JsyGjn2lv0WY8UsTgUJjU9Ok55NA==", - "requires": { - "kind-of": "^6.0.2" - } - }, - "shebang-command": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", - "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", - "requires": { - "shebang-regex": "^3.0.0" - } - }, - "shebang-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", - "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==" - }, - "shell-quote": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/shell-quote/-/shell-quote-1.8.1.tgz", - "integrity": "sha512-6j1W9l1iAs/4xYBI1SYOVZyFcCis9b4KCLQ8fgAGG07QvzaRLVVRQvAy85yNmmZSjYjg4MWh4gNvlPujU/5LpA==", - "dev": true - }, - "side-channel": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.4.tgz", - "integrity": "sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==", - "dev": true, - "requires": { - "call-bind": "^1.0.0", - "get-intrinsic": "^1.0.2", - "object-inspect": "^1.9.0" - } - }, - "signal-exit": { - "version": "3.0.7", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", - "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==", - "dev": true - }, - "sockjs": { - "version": "0.3.24", - "resolved": "https://registry.npmjs.org/sockjs/-/sockjs-0.3.24.tgz", - "integrity": "sha512-GJgLTZ7vYb/JtPSSZ10hsOYIvEYsjbNU+zPdIHcUaWVNUEPivzxku31865sSSud0Da0W4lEeOPlmw93zLQchuQ==", - "dev": true, - "requires": { - "faye-websocket": "^0.11.3", - "uuid": "^8.3.2", - "websocket-driver": "^0.7.4" - } - }, - "source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" - }, - "source-map-support": { - "version": "0.5.21", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.21.tgz", - "integrity": "sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==", - "requires": { - "buffer-from": "^1.0.0", - "source-map": "^0.6.0" - } - }, - "spark-md5": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/spark-md5/-/spark-md5-3.0.2.tgz", - "integrity": "sha512-wcFzz9cDfbuqe0FZzfi2or1sgyIrsDwmPwfZC4hiNidPdPINjeUwNfv5kldczoEAcjl9Y1L3SM7Uz2PUEQzxQw==" - }, - "spdy": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/spdy/-/spdy-4.0.2.tgz", - "integrity": "sha512-r46gZQZQV+Kl9oItvl1JZZqJKGr+oEkB08A6BzkiR7593/7IbtuncXHd2YoYeTsG4157ZssMu9KYvUHLcjcDoA==", - "dev": true, - "requires": { - "debug": "^4.1.0", - "handle-thing": "^2.0.0", - "http-deceiver": "^1.2.7", - "select-hose": "^2.0.0", - "spdy-transport": "^3.0.0" - }, - "dependencies": { - "debug": { - "version": "4.3.4", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.4.tgz", - "integrity": "sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ==", - "dev": true, - "requires": { - "ms": "2.1.2" - } - }, - "ms": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", - "dev": true - } - } - }, - "spdy-transport": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/spdy-transport/-/spdy-transport-3.0.0.tgz", - "integrity": "sha512-hsLVFE5SjA6TCisWeJXFKniGGOpBgMLmerfO2aCyCU5s7nJ/rpAepqmFifv/GCbSbueEeAJJnmSQ2rKC/g8Fcw==", - "dev": true, - "requires": { - "debug": "^4.1.0", - "detect-node": "^2.0.4", - "hpack.js": "^2.1.6", - "obuf": "^1.1.2", - "readable-stream": "^3.0.6", - "wbuf": "^1.7.3" - }, - "dependencies": { - "debug": { - "version": "4.3.4", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.4.tgz", - "integrity": "sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ==", - "dev": true, - "requires": { - "ms": "2.1.2" - } - }, - "ms": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", - "dev": true - } - } - }, - "statuses": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", - "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", - "dev": true - }, - "stimulus": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/stimulus/-/stimulus-2.0.0.tgz", - "integrity": "sha512-xipy7BS5TVpg4fX6S8LhrYZp7cmHGjmk09WSAiVx1gF5S5g43IWsuetfUhIk8HfHUG+4MQ9nY0FQz4dRFLs/8w==", - "requires": { - "@stimulus/core": "^2.0.0", - "@stimulus/webpack-helpers": "^2.0.0" - } - }, - "string_decoder": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", - "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", - "dev": true, - "requires": { - "safe-buffer": "~5.1.0" - }, - "dependencies": { - "safe-buffer": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "dev": true - } - } - }, - "strip-final-newline": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-final-newline/-/strip-final-newline-2.0.0.tgz", - "integrity": "sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA==", - "dev": true - }, - "supports-color": { - "version": "8.1.1", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", - "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", - "requires": { - "has-flag": "^4.0.0" - } - }, - "supports-preserve-symlinks-flag": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", - "integrity": "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==" - }, - "sweetalert2": { - "version": "11.7.32", - "resolved": "https://registry.npmjs.org/sweetalert2/-/sweetalert2-11.7.32.tgz", - "integrity": "sha512-44tNNe2oLe7T94mT6dus4hc9G7qg6jZU/K5qZzpNS6e5HGPrSF6Kie6oZ7B5puIJydB34V2h/8f5EhIFivYo4A==" - }, - "tapable": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.2.1.tgz", - "integrity": "sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ==" - }, - "terser": { - "version": "5.21.0", - "resolved": "https://registry.npmjs.org/terser/-/terser-5.21.0.tgz", - "integrity": "sha512-WtnFKrxu9kaoXuiZFSGrcAvvBqAdmKx0SFNmVNYdJamMu9yyN3I/QF0FbH4QcqJQ+y1CJnzxGIKH0cSj+FGYRw==", - "requires": { - "@jridgewell/source-map": "^0.3.3", - "acorn": "^8.8.2", - "commander": "^2.20.0", - "source-map-support": "~0.5.20" - } - }, - "terser-webpack-plugin": { - "version": "5.3.9", - "resolved": "https://registry.npmjs.org/terser-webpack-plugin/-/terser-webpack-plugin-5.3.9.tgz", - "integrity": "sha512-ZuXsqE07EcggTWQjXUj+Aot/OMcD0bMKGgF63f7UxYcu5/AJF53aIpK1YoP5xR9l6s/Hy2b+t1AM0bLNPRuhwA==", - "requires": { - "@jridgewell/trace-mapping": "^0.3.17", - "jest-worker": "^27.4.5", - "schema-utils": "^3.1.1", - "serialize-javascript": "^6.0.1", - "terser": "^5.16.8" - } - }, - "thunky": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/thunky/-/thunky-1.1.0.tgz", - "integrity": "sha512-eHY7nBftgThBqOyHGVN+l8gF0BucP09fMo0oO/Lb0w1OF80dJv+lDVpXG60WMQvkcxAkNybKsrEIE3ZtKGmPrA==", - "dev": true - }, - "to-regex-range": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", - "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", - "dev": true, - "requires": { - "is-number": "^7.0.0" - } - }, - "toidentifier": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", - "integrity": "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==", - "dev": true - }, - "type-is": { - "version": "1.6.18", - "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz", - "integrity": "sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==", - "dev": true, - "requires": { - "media-typer": "0.3.0", - "mime-types": "~2.1.24" - } - }, - "unpipe": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", - "integrity": "sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==", - "dev": true - }, - "update-browserslist-db": { - "version": "1.0.13", - "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.0.13.tgz", - "integrity": "sha512-xebP81SNcPuNpPP3uzeW1NYXxI3rxyJzF3pD6sH4jE7o/IX+WtSpwnVU+qIsDPyk0d3hmFQ7mjqc6AtV604hbg==", - "requires": { - "escalade": "^3.1.1", - "picocolors": "^1.0.0" - } - }, - "uri-js": { - "version": "4.4.1", - "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", - "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", - "requires": { - "punycode": "^2.1.0" - } - }, - "util-deprecate": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==", - "dev": true - }, - "utils-merge": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", - "integrity": "sha512-pMZTvIkT1d+TFGvDOqodOclx0QWkkgi6Tdoa8gC8ffGAAqz9pzPTZWAybbsHHoED/ztMtkv/VoYTYyShUn81hA==", - "dev": true - }, - "uuid": { - "version": "8.3.2", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz", - "integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==", - "dev": true - }, - "vary": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", - "integrity": "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==", - "dev": true - }, - "watchpack": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.4.0.tgz", - "integrity": "sha512-Lcvm7MGST/4fup+ifyKi2hjyIAwcdI4HRgtvTpIUxBRhB+RFtUh8XtDOxUfctVCnhVi+QQj49i91OyvzkJl6cg==", - "requires": { - "glob-to-regexp": "^0.4.1", - "graceful-fs": "^4.1.2" - } - }, - "waypoints": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/waypoints/-/waypoints-4.0.1.tgz", - "integrity": "sha512-PbydbsTvCFYoE1DaRAKBM4xPQi+7ULcULZ7vK79NLM55da5g46oyY62Xv9X5Z9F7O/qXmcS/XJ7Ae2pYij4bpw==" - }, - "wbuf": { - "version": "1.7.3", - "resolved": "https://registry.npmjs.org/wbuf/-/wbuf-1.7.3.tgz", - "integrity": "sha512-O84QOnr0icsbFGLS0O3bI5FswxzRr8/gHwWkDlQFskhSPryQXvrTMxjxGP4+iWYoauLoBvfDpkrOauZ+0iZpDA==", - "dev": true, - "requires": { - "minimalistic-assert": "^1.0.0" - } - }, - "webpack": { - "version": "5.88.2", - "resolved": "https://registry.npmjs.org/webpack/-/webpack-5.88.2.tgz", - "integrity": "sha512-JmcgNZ1iKj+aiR0OvTYtWQqJwq37Pf683dY9bVORwVbUrDhLhdn/PlO2sHsFHPkj7sHNQF3JwaAkp49V+Sq1tQ==", - "requires": { - "@types/eslint-scope": "^3.7.3", - "@types/estree": "^1.0.0", - "@webassemblyjs/ast": "^1.11.5", - "@webassemblyjs/wasm-edit": "^1.11.5", - "@webassemblyjs/wasm-parser": "^1.11.5", - "acorn": "^8.7.1", - "acorn-import-assertions": "^1.9.0", - "browserslist": "^4.14.5", - "chrome-trace-event": "^1.0.2", - "enhanced-resolve": "^5.15.0", - "es-module-lexer": "^1.2.1", - "eslint-scope": "5.1.1", - "events": "^3.2.0", - "glob-to-regexp": "^0.4.1", - "graceful-fs": "^4.2.9", - "json-parse-even-better-errors": "^2.3.1", - "loader-runner": "^4.2.0", - "mime-types": "^2.1.27", - "neo-async": "^2.6.2", - "schema-utils": "^3.2.0", - "tapable": "^2.1.1", - "terser-webpack-plugin": "^5.3.7", - "watchpack": "^2.4.0", - "webpack-sources": "^3.2.3" - } - }, - "webpack-cli": { - "version": "5.1.4", - "resolved": "https://registry.npmjs.org/webpack-cli/-/webpack-cli-5.1.4.tgz", - "integrity": "sha512-pIDJHIEI9LR0yxHXQ+Qh95k2EvXpWzZ5l+d+jIo+RdSm9MiHfzazIxwwni/p7+x4eJZuvG1AJwgC4TNQ7NRgsg==", - "requires": { - "@discoveryjs/json-ext": "^0.5.0", - "@webpack-cli/configtest": "^2.1.1", - "@webpack-cli/info": "^2.0.2", - "@webpack-cli/serve": "^2.0.5", - "colorette": "^2.0.14", - "commander": "^10.0.1", - "cross-spawn": "^7.0.3", - "envinfo": "^7.7.3", - "fastest-levenshtein": "^1.0.12", - "import-local": "^3.0.2", - "interpret": "^3.1.1", - "rechoir": "^0.8.0", - "webpack-merge": "^5.7.3" - }, - "dependencies": { - "commander": { - "version": "10.0.1", - "resolved": "https://registry.npmjs.org/commander/-/commander-10.0.1.tgz", - "integrity": "sha512-y4Mg2tXshplEbSGzx7amzPwKKOCGuoSRP/CjEdwwk0FOGlUbq6lKuoyDZTNZkmxHdJtp54hdfY/JUrdL7Xfdug==" - } - } - }, - "webpack-dev-middleware": { - "version": "5.3.3", - "resolved": "https://registry.npmjs.org/webpack-dev-middleware/-/webpack-dev-middleware-5.3.3.tgz", - "integrity": "sha512-hj5CYrY0bZLB+eTO+x/j67Pkrquiy7kWepMHmUMoPsmcUaeEnQJqFzHJOyxgWlq746/wUuA64p9ta34Kyb01pA==", - "dev": true, - "requires": { - "colorette": "^2.0.10", - "memfs": "^3.4.3", - "mime-types": "^2.1.31", - "range-parser": "^1.2.1", - "schema-utils": "^4.0.0" - }, - "dependencies": { - "schema-utils": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-4.2.0.tgz", - "integrity": "sha512-L0jRsrPpjdckP3oPug3/VxNKt2trR8TcabrM6FOAAlvC/9Phcmm+cuAgTlxBqdBR1WJx7Naj9WHw+aOmheSVbw==", - "dev": true, - "requires": { - "@types/json-schema": "^7.0.9", - "ajv": "^8.9.0", - "ajv-formats": "^2.1.1", - "ajv-keywords": "^5.1.0" - } - } - } - }, - "webpack-dev-server": { - "version": "4.15.1", - "resolved": "https://registry.npmjs.org/webpack-dev-server/-/webpack-dev-server-4.15.1.tgz", - "integrity": "sha512-5hbAst3h3C3L8w6W4P96L5vaV0PxSmJhxZvWKYIdgxOQm8pNZ5dEOmmSLBVpP85ReeyRt6AS1QJNyo/oFFPeVA==", - "dev": true, - "requires": { - "@types/bonjour": "^3.5.9", - "@types/connect-history-api-fallback": "^1.3.5", - "@types/express": "^4.17.13", - "@types/serve-index": "^1.9.1", - "@types/serve-static": "^1.13.10", - "@types/sockjs": "^0.3.33", - "@types/ws": "^8.5.5", - "ansi-html-community": "^0.0.8", - "bonjour-service": "^1.0.11", - "chokidar": "^3.5.3", - "colorette": "^2.0.10", - "compression": "^1.7.4", - "connect-history-api-fallback": "^2.0.0", - "default-gateway": "^6.0.3", - "express": "^4.17.3", - "graceful-fs": "^4.2.6", - "html-entities": "^2.3.2", - "http-proxy-middleware": "^2.0.3", - "ipaddr.js": "^2.0.1", - "launch-editor": "^2.6.0", - "open": "^8.0.9", - "p-retry": "^4.5.0", - "rimraf": "^3.0.2", - "schema-utils": "^4.0.0", - "selfsigned": "^2.1.1", - "serve-index": "^1.9.1", - "sockjs": "^0.3.24", - "spdy": "^4.0.2", - "webpack-dev-middleware": "^5.3.1", - "ws": "^8.13.0" - }, - "dependencies": { - "schema-utils": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-4.2.0.tgz", - "integrity": "sha512-L0jRsrPpjdckP3oPug3/VxNKt2trR8TcabrM6FOAAlvC/9Phcmm+cuAgTlxBqdBR1WJx7Naj9WHw+aOmheSVbw==", - "dev": true, - "requires": { - "@types/json-schema": "^7.0.9", - "ajv": "^8.9.0", - "ajv-formats": "^2.1.1", - "ajv-keywords": "^5.1.0" - } - } - } - }, - "webpack-merge": { - "version": "5.9.0", - "resolved": "https://registry.npmjs.org/webpack-merge/-/webpack-merge-5.9.0.tgz", - "integrity": "sha512-6NbRQw4+Sy50vYNTw7EyOn41OZItPiXB8GNv3INSoe3PSFaHJEz3SHTrYVaRm2LilNGnFUzh0FAwqPEmU/CwDg==", - "requires": { - "clone-deep": "^4.0.1", - "wildcard": "^2.0.0" - } - }, - "webpack-sources": { - "version": "3.2.3", - "resolved": "https://registry.npmjs.org/webpack-sources/-/webpack-sources-3.2.3.tgz", - "integrity": "sha512-/DyMEOrDgLKKIG0fmvtz+4dUX/3Ghozwgm6iPp8KRhvn+eQf9+Q7GWxVNMk3+uCPWfdXYC4ExGBckIXdFEfH1w==" - }, - "websocket-driver": { - "version": "0.7.4", - "resolved": "https://registry.npmjs.org/websocket-driver/-/websocket-driver-0.7.4.tgz", - "integrity": "sha512-b17KeDIQVjvb0ssuSDF2cYXSg2iztliJ4B9WdsuB6J952qCPKmnVq4DyW5motImXHDC1cBT/1UezrJVsKw5zjg==", - "dev": true, - "requires": { - "http-parser-js": ">=0.5.1", - "safe-buffer": ">=5.1.0", - "websocket-extensions": ">=0.1.1" - } - }, - "websocket-extensions": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/websocket-extensions/-/websocket-extensions-0.1.4.tgz", - "integrity": "sha512-OqedPIGOfsDlo31UNwYbCFMSaO9m9G/0faIHj5/dZFDMFqPTcx6UwqyOy3COEaEOg/9VsGIpdqn62W5KhoKSpg==", - "dev": true - }, - "which": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", - "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", - "requires": { - "isexe": "^2.0.0" - } - }, - "wildcard": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/wildcard/-/wildcard-2.0.1.tgz", - "integrity": "sha512-CC1bOL87PIWSBhDcTrdeLo6eGT7mCFtrg0uIJtqJUFyK+eJnzl8A1niH56uu7KMa5XFrtiV+AQuHO3n7DsHnLQ==" - }, - "wrappy": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==", - "dev": true - }, - "ws": { - "version": "8.14.2", - "resolved": "https://registry.npmjs.org/ws/-/ws-8.14.2.tgz", - "integrity": "sha512-wEBG1ftX4jcglPxgFCMJmZ2PLtSbJ2Peg6TmpJFTbe9GZYOQCDPdMYu/Tm0/bGZkw8paZnJY45J4K2PZrLYq8g==", - "dev": true - } - } -} diff --git a/package.json b/package.json index 05a6021e..a496b3fa 100644 --- a/package.json +++ b/package.json @@ -9,6 +9,7 @@ "@hotwired/stimulus": "^3.1.1", "@hotwired/turbo-rails": "^8.0.0", "@nathanvda/cocoon": "^1.2.14", + "@popperjs/core": "^2.11.8", "@rails/actioncable": "^7.0.8", "@rails/activestorage": "^7.1.0", "@rails/ujs": "^6.1.6", diff --git a/yarn.lock b/yarn.lock index 77e121ef..f3da1862 100644 --- a/yarn.lock +++ b/yarn.lock @@ -82,6 +82,11 @@ dependencies: jquery "^3.3.1" +"@popperjs/core@^2.11.8": + version "2.11.8" + resolved "https://registry.yarnpkg.com/@popperjs/core/-/core-2.11.8.tgz#6b79032e760a0899cd4204710beede972a3a185f" + integrity sha512-P1st0aksCrn9sGZhp8GMYwBnQsbvAWsZAX44oXNNvLHGqAOcoVxmjZiohstwQ7SqKnbR47akdNi+uleWD8+g6A== + "@rails/actioncable@^7.0": version "7.0.7" resolved "https://registry.yarnpkg.com/@rails/actioncable/-/actioncable-7.0.7.tgz#03b5faa8642a80211708e8f1754cf424e9228718" From a95d4c73e0477ec9cfd89fa5994e05982ea66c23 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Tue, 20 Aug 2024 17:37:27 -0300 Subject: [PATCH 13/45] update the code of forecast --- app/controllers/stocks_controller.rb | 34 +++++++++++++++++++++++----- lib/forecasts/basic_stock.rb | 29 ++++++++++++++++-------- 2 files changed, 47 insertions(+), 16 deletions(-) diff --git a/app/controllers/stocks_controller.rb b/app/controllers/stocks_controller.rb index 0afe1e11..9bf8a514 100644 --- a/app/controllers/stocks_controller.rb +++ b/app/controllers/stocks_controller.rb @@ -16,17 +16,39 @@ def index end protected - + def collection @default_status_filter = params['status'] @default_situation_balance_filter = params['balance_situation'] - - stocks = Stock.where(account_id: current_tenant).includes([:product]) + + # Fetch stocks with necessary associations + stocks = Stock.where(account_id: current_tenant) + .includes(:product) .only_positive_price(true) .filter_by_status(params['status']) .filter_by_total_balance_situation(params['balance_situation']) - #.sort_by(&:calculate_basic_forecast) - #.reverse! - @pagy, @stocks = pagy_array(stocks) + + # Fetch all relevant items in a single query + start_date = 1.month.ago.to_date + end_date = Date.today + + items_sold = Item.joins(:bling_order_item) + .where(account_id: current_tenant, + bling_order_item: { date: start_date..end_date }) + .group(:sku) + .sum(:quantity) + + # Calculate forecasts for each stock + stocks_with_forecasts = stocks.map do |stock| + sold_quantity = items_sold[stock.sku] || 0 + forecast = [sold_quantity - stock.total_balance, 0].max + [stock, forecast] + end + + # Sort stocks based on forecasts (in descending order) + sorted_stocks = stocks_with_forecasts.sort_by { |_, forecast| -forecast }.map(&:first) + + # Paginate the sorted stocks + @pagy, @stocks = pagy_array(sorted_stocks) end end diff --git a/lib/forecasts/basic_stock.rb b/lib/forecasts/basic_stock.rb index 71c632bd..73919dd0 100644 --- a/lib/forecasts/basic_stock.rb +++ b/lib/forecasts/basic_stock.rb @@ -1,5 +1,3 @@ -# frozen_string_literal: true - module Forecasts # This class is simple as it is. # Born to answer this question: @@ -7,28 +5,39 @@ module Forecasts # How many products I need to add to my actual stock? Assuming I expect the same demand # for the next 30 days" class BasicStock - attr_accessor :stock, :sku, :date, :account_id, :items, :options + attr_reader :stock, :sku, :start_date, :end_date, :account_id, :options NO_NEED_TO_INCREASE_STOCK = 0 def initialize(stock, options = {}) @stock = stock @sku = stock.sku - @date = Date.today - 1.month + @end_date = options[:end_date] || Date.today + @start_date = options[:start_date] || @end_date - 1.month @account_id = stock.account_id @options = options - @items = Item.joins(:bling_order_item).where(bling_order_item: { date: [date..] }, account_id:, sku:) end + def self.bulk_calculate(stocks, items_sold) + stocks.map do |stock| + sold_quantity = items_sold[stock.sku] || 0 + forecast = [sold_quantity - stock.total_balance, 0].max + [stock, forecast] + end + end + + def calculate stock_to_repair_quantity = count_sold - stock.total_balance - return NO_NEED_TO_INCREASE_STOCK if stock_to_repair_quantity.negative? - - stock_to_repair_quantity + [stock_to_repair_quantity, NO_NEED_TO_INCREASE_STOCK].max end def count_sold - @count_sold ||= items.sum(:quantity) + @count_sold ||= Item.joins(:bling_order_item) + .where(bling_order_item: { date: start_date..end_date }, + account_id: account_id, + sku: sku) + .sum(:quantity) end end -end +end \ No newline at end of file From f69969399978f6f0676e5efa709fa9b552724d7e Mon Sep 17 00:00:00 2001 From: snyk-bot Date: Wed, 21 Aug 2024 09:33:23 +0000 Subject: [PATCH 14/45] fix: upgrade sweetalert2 from 11.7.32 to 11.12.3 Snyk has created this PR to upgrade sweetalert2 from 11.7.32 to 11.12.3. See this package in yarn: sweetalert2 See this project in Snyk: https://app.snyk.io/org/puppe1990/project/5f79e54e-03ca-4987-b88f-a022f6e0ec5e?utm_source=github&utm_medium=referral&page=upgrade-pr --- package.json | 2 +- yarn.lock | 8 ++++---- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/package.json b/package.json index a496b3fa..c14c764e 100644 --- a/package.json +++ b/package.json @@ -24,7 +24,7 @@ "popper.js": "^1.16.1", "select2": "^4.0.7-rc.0", "stimulus": "^2.0.0", - "sweetalert2": "^11.7.32", + "sweetalert2": "^11.12.3", "waypoints": "^4.0.1", "webpack": "^5.88.2", "webpack-cli": "^5.1.4" diff --git a/yarn.lock b/yarn.lock index f3da1862..992cbe65 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2016,10 +2016,10 @@ supports-preserve-symlinks-flag@^1.0.0: resolved "https://registry.yarnpkg.com/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz#6eda4bd344a3c94aea376d4cc31bc77311039e09" integrity sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w== -sweetalert2@^11.7.32: - version "11.7.32" - resolved "https://registry.yarnpkg.com/sweetalert2/-/sweetalert2-11.7.32.tgz#366fde9eaa1fc8d7a8993400d7582715647a31cf" - integrity sha512-44tNNe2oLe7T94mT6dus4hc9G7qg6jZU/K5qZzpNS6e5HGPrSF6Kie6oZ7B5puIJydB34V2h/8f5EhIFivYo4A== +sweetalert2@^11.12.3: + version "11.12.4" + resolved "https://registry.yarnpkg.com/sweetalert2/-/sweetalert2-11.12.4.tgz#2f7cc2663dab7845f33d5abd6ce3f642a09b91dd" + integrity sha512-ZSpyaLbAmn4b7xjnV9x9BFD1UOrCAhIzm1D8dZ443kGxtVKqbTIA5SgXs4xeEtmFfEXUyC3RBgpSlu1AXmCiHA== tapable@^2.1.1, tapable@^2.2.0: version "2.2.1" From 748a950d9f8e0f642eed077d181f7d2aa7b23818 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Thu, 22 Aug 2024 17:27:49 -0300 Subject: [PATCH 15/45] create abc curve in report --- app/controllers/reports_controller.rb | 36 +++++++++++++++++-- .../reports/top_selling_products.html.erb | 20 ++++++++++- 2 files changed, 53 insertions(+), 3 deletions(-) diff --git a/app/controllers/reports_controller.rb b/app/controllers/reports_controller.rb index ddad1518..7f1fc789 100644 --- a/app/controllers/reports_controller.rb +++ b/app/controllers/reports_controller.rb @@ -32,8 +32,15 @@ def top_selling_products .where(bling_order_items: { situation_id: [BlingOrderItem::Status::PAID] }) .where(account_id: current_tenant.id) .group('items.sku') - .select('items.sku, SUM(items.quantity) AS total_quantity') - .order('total_quantity DESC') + .select('items.sku, SUM(items.value) AS total_value, COUNT(*) AS total_quantity') + .order('total_value DESC') + + @total_value = @items.sum(&:total_value) + + respond_to do |format| + format.html + format.csv { send_data generate_csv, filename: "top_selling_products_#{Date.today}.csv" } + end end private @@ -48,4 +55,29 @@ def date_range end @date_range = initial_date..final_date end + + def generate_csv + CSV.generate(headers: true) do |csv| + csv << ['SKU', 'Total Quantity', 'Total Value', 'Cumulative Percentage', 'ABC Classification'] + + cumulative_value = 0 + @items.each do |item| + cumulative_value += item.total_value + percentage = (cumulative_value.to_f / @total_value * 100).round(2) + classification = case percentage + when 0..80 then 'Curva A' + when 80..95 then 'Curva B' + else 'Curva C' + end + + csv << [ + item.sku, + item.total_quantity, + item.total_value, + percentage, + classification + ] + end + end + end end diff --git a/app/views/reports/top_selling_products.html.erb b/app/views/reports/top_selling_products.html.erb index 8aadc1f0..ac309702 100644 --- a/app/views/reports/top_selling_products.html.erb +++ b/app/views/reports/top_selling_products.html.erb @@ -28,20 +28,38 @@
+
+ Download: + <%= link_to 'CSV', top_selling_products_path(format: :csv, selling_products: { initial_date: @initial_date, final_date: @final_date }), class: 'btn btn-sm btn-secondary' %>
+ + + + + <% cumulative_value = 0 %> <% @items.each do |item| %> + <% cumulative_value += item.total_value %> + <% percentage = (cumulative_value.to_f / @total_value * 100).round(2) %> + <% classification = case percentage + when 0..80 then 'Curva A' + when 80..95 then 'Curva B' + else 'Curva C' + end %> + + + <% end %>
SKU Total QuantityTotal ValueCumulative PercentageABC Classification
<%= item.sku %> <%= item.total_quantity %><%= number_to_currency(item.total_value, unit: "R$", separator: ",", delimiter: ".") %><%= number_to_percentage(percentage, precision: 2) %><%= classification %>
-
+ \ No newline at end of file From fe78434af7fce00cb004f2fa2f238611a95e6152 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Thu, 22 Aug 2024 17:46:48 -0300 Subject: [PATCH 16/45] update the layout --- .../reports/top_selling_products.html.erb | 167 ++++++++++++------ 1 file changed, 110 insertions(+), 57 deletions(-) diff --git a/app/views/reports/top_selling_products.html.erb b/app/views/reports/top_selling_products.html.erb index ac309702..bab6938e 100644 --- a/app/views/reports/top_selling_products.html.erb +++ b/app/views/reports/top_selling_products.html.erb @@ -1,65 +1,118 @@ -
-
-

Pesquisar por data

-
-
- <%= form_tag(top_selling_products_path, method: :get) do %> -
-
- Data inicial +
+

Produtos Mais Vendidos

+

Analise os produtos mais vendidos em um período específico.

+ +
+
+
+
+

Filtrar por Data

+
+
+ <%= form_tag(top_selling_products_path, method: :get, id: 'search-form', class: 'form-inline') do %> +
+ <%= label_tag 'selling_products[initial_date]', 'Data Inicial', class: 'mr-2' %> + <%= date_field_tag 'selling_products[initial_date]', @initial_date || (Date.today - 7.days), class: 'form-control', id: 'initial_date' %>
- <%= date_field_tag('selling_products[initial_date]', @initial_date || (Date.today - 7.days), class: 'form-control') %> -
-
-
-
-
- Data final +
+ <%= label_tag 'selling_products[final_date]', 'Data Final', class: 'mr-2' %> + <%= date_field_tag 'selling_products[final_date]', @final_date || Date.today, class: 'form-control', id: 'final_date' %>
- <%= date_field_tag('selling_products[final_date]', @final_date || Date.today, class: 'form-control') %> -
+ <%= button_tag 'Pesquisar', class: 'btn btn-primary mr-2' %> + <%= button_tag 'Últimos 15 Dias', id: 'last15DaysBtn', type: 'button', class: 'btn btn-secondary mr-2' %> + <%= button_tag 'Últimos 30 Dias', id: 'last30DaysBtn', type: 'button', class: 'btn btn-secondary' %> + <% end %> +
-
- <%= button_tag('Pesquisar...', class: 'btn btn-primary btn-block', style: 'margin-top: 38px;') %> - <% end %> +
+
+ +
+
+
+
+

Resultados

+
+ <%= link_to 'Baixar CSV', top_selling_products_path(format: :csv, selling_products: { initial_date: @initial_date, final_date: @final_date }), class: 'btn btn-icon icon-left btn-primary' %> +
+
+
+
+ + + + + + + + + + + + <% cumulative_value = 0 %> + <% @items.each do |item| %> + <% cumulative_value += item.total_value %> + <% percentage = (cumulative_value.to_f / @total_value * 100).round(2) %> + <% classification = case percentage + when 0..80 then 'Curva A' + when 80..95 then 'Curva B' + else 'Curva C' + end %> + + + + + + + + <% end %> + +
SKUQuantidade TotalValor TotalPorcentagem CumulativaClassificação ABC
<%= item.sku %><%= item.total_quantity %><%= number_to_currency(item.total_value, unit: "R$", separator: ",", delimiter: ".") %><%= number_to_percentage(percentage, precision: 2) %><%= classification %>
+
+
-
+ + +<%= content_for :javascript do %> + +<% end %> \ No newline at end of file From ca3d96da4a98ce3d184dd9ada8473ad98c3de962 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Fri, 23 Aug 2024 15:44:01 -0300 Subject: [PATCH 17/45] add new job --- app/jobs/flexible_order_items_job.rb | 56 ++++++++++++++++++++++++++++ 1 file changed, 56 insertions(+) create mode 100644 app/jobs/flexible_order_items_job.rb diff --git a/app/jobs/flexible_order_items_job.rb b/app/jobs/flexible_order_items_job.rb new file mode 100644 index 00000000..c51c9d6b --- /dev/null +++ b/app/jobs/flexible_order_items_job.rb @@ -0,0 +1,56 @@ +# frozen_string_literal: true + +class FlexibleOrderItemsJob < BlingOrderItemCreatorBaseJob + queue_as :default + + attr_accessor :account_id, :statuses, :start_date, :end_date + + def perform(account_id, statuses, options = {}) + @account_id = account_id + @statuses = Array(statuses) + set_date_range(options) + + options.merge!(date_range_options) + + all_orders = [] + + @statuses.each do |status| + orders = fetch_orders(status, options) + all_orders.concat(orders) + end + + create_orders(all_orders) + end + + private + + def set_date_range(options) + @start_date = options.delete(:start_date) + @end_date = options.delete(:end_date) + end + + def fetch_orders(status, options) + response = Services::Bling::Order.call( + order_command: 'find_orders', + tenant: @account_id, + situation: status, + options: options + ) + response['data'] + end + + def date_range_options + return {} unless date_range_present? + + { + dataEmissao: { + inicial: @start_date.to_date.iso8601, + final: @end_date.to_date.iso8601 + } + } + end + + def date_range_present? + @start_date.present? && @end_date.present? + end + end \ No newline at end of file From 939e0d7e2109cbf37d274d5f9fa08188bd60ea73 Mon Sep 17 00:00:00 2001 From: snyk-bot Date: Sat, 24 Aug 2024 10:32:52 +0000 Subject: [PATCH 18/45] fix: Gemfile & Gemfile.lock to reduce vulnerabilities The following vulnerabilities are fixed with an upgrade: - https://snyk.io/vuln/SNYK-RUBY-REXML-7814166 - https://snyk.io/vuln/SNYK-RUBY-REXML-7577227 - https://snyk.io/vuln/SNYK-RUBY-RACK-1061917 - https://snyk.io/vuln/SNYK-RUBY-REXML-7577228 - https://snyk.io/vuln/SNYK-RUBY-REXML-7462086 --- Gemfile | 2 +- Gemfile.lock | 18 +++++++++--------- 2 files changed, 10 insertions(+), 10 deletions(-) diff --git a/Gemfile b/Gemfile index 241a6a6d..74eba967 100644 --- a/Gemfile +++ b/Gemfile @@ -142,7 +142,7 @@ gem 'rack-cors', require: 'rack/cors' gem 'rails-i18n', '~> 7.0.9' gem 'rqrcode_png', git: "https://github.com/DCarper/rqrcode_png.git" gem 'serviceworker-rails' -gem 'rubocop-rails', '>= 2.25.1', require: false +gem 'rubocop-rails', '>= 2.26.0', require: false gem 'rubocop-rspec', '>= 2.24.1', require: false gem 'rubocop-performance', '>= 1.20.0', require: false gem 'bling_api', git: 'https://github.com/Purple-Stock/bling_api' diff --git a/Gemfile.lock b/Gemfile.lock index 3821e3a0..d6d3f32b 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -334,8 +334,8 @@ GEM racc (~> 1.4) orm_adapter (0.5.0) pagy (6.0.4) - parallel (1.25.1) - parser (3.3.3.0) + parallel (1.26.3) + parser (3.3.4.2) ast (~> 2.4.1) racc path_expander (1.1.1) @@ -416,7 +416,7 @@ GEM railties (>= 5.2) reverse_markdown (2.1.1) nokogiri - rexml (3.3.1) + rexml (3.3.6) strscan rodf (1.2.0) builder (>= 3.0) @@ -448,18 +448,18 @@ GEM rspec-mocks (~> 3.13) rspec-support (~> 3.13) rspec-support (3.13.1) - rubocop (1.64.1) + rubocop (1.65.1) json (~> 2.3) language_server-protocol (>= 3.17.0) parallel (~> 1.10) parser (>= 3.3.0.2) rainbow (>= 2.2.2, < 4.0) - regexp_parser (>= 1.8, < 3.0) + regexp_parser (>= 2.4, < 3.0) rexml (>= 3.2.5, < 4.0) rubocop-ast (>= 1.31.1, < 2.0) ruby-progressbar (~> 1.7) unicode-display_width (>= 2.4.0, < 3.0) - rubocop-ast (1.31.3) + rubocop-ast (1.32.1) parser (>= 3.3.1.0) rubocop-capybara (2.20.0) rubocop (~> 1.41) @@ -468,10 +468,10 @@ GEM rubocop-performance (1.21.0) rubocop (>= 1.48.1, < 2.0) rubocop-ast (>= 1.31.1, < 2.0) - rubocop-rails (2.25.1) + rubocop-rails (2.26.0) activesupport (>= 4.2.0) rack (>= 1.1) - rubocop (>= 1.33.0, < 2.0) + rubocop (>= 1.52.0, < 2.0) rubocop-ast (>= 1.31.1, < 2.0) rubocop-rspec (2.30.0) rubocop (~> 1.40) @@ -661,7 +661,7 @@ DEPENDENCIES rqrcode_png! rspec-rails (>= 6.1.4) rubocop-performance (>= 1.20.0) - rubocop-rails (>= 2.25.1) + rubocop-rails (>= 2.26.0) rubocop-rspec (>= 2.24.1) rubycritic rubyzip From c8e40ca018dea14270795a8347286387a67fecf9 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Mon, 26 Aug 2024 16:48:41 -0300 Subject: [PATCH 19/45] create a new job to update the status on the project data --- app/jobs/find_orders_by_status_job.rb | 78 +++++++++++++++++++++++++++ 1 file changed, 78 insertions(+) create mode 100644 app/jobs/find_orders_by_status_job.rb diff --git a/app/jobs/find_orders_by_status_job.rb b/app/jobs/find_orders_by_status_job.rb new file mode 100644 index 00000000..cfe30833 --- /dev/null +++ b/app/jobs/find_orders_by_status_job.rb @@ -0,0 +1,78 @@ +require 'retryable' + +class ImprovedFindOrdersByStatusJob < ApplicationJob + queue_as :default + + MAX_RETRIES = 3 + RETRY_DELAY = 5 # seconds + + def perform(status, tenant_id) + orders = BlingOrderItem.where(account_id: tenant_id, situation_id: status) + bling_datum = BlingDatum.find_by(account_id: tenant_id) + + if bling_datum.nil? + Rails.logger.error("No BlingDatum found for account_id: #{tenant_id}") + return + end + + orders.find_each do |order| + process_order(order, tenant_id) + end + end + + private + + def process_order(order, tenant_id) + Retryable.retryable( + tries: MAX_RETRIES, + sleep: RETRY_DELAY, + on: [StandardError], + matching: /TOO_MANY_REQUESTS/, + exception_cb: Proc.new { |exception| + Rails.logger.warn("Retrying after TOO_MANY_REQUESTS error for order #{order.bling_order_id}. #{exception.message}") + } + ) do + result = Services::Bling::FindOrder.call( + id: order.bling_order_id, + order_command: 'find_order', + tenant: tenant_id + ) + + if result.is_a?(Hash) && result['data'].present? + update_order(order, result['data']) + elsif result.is_a?(Hash) && result['error'].present? && result['error']['type'] == 'RESOURCE_NOT_FOUND' + delete_order(order) + else + Rails.logger.error("Failed to fetch order #{order.bling_order_id}: #{result}") + raise StandardError, result['error']['message'] if result.is_a?(Hash) && result['error'].present? + end + end + rescue StandardError => e + Rails.logger.error("Failed to process order #{order.bling_order_id} after #{MAX_RETRIES} retries: #{e.message}") + end + + def update_order(order, data) + order_data = data['pedido'] || data + + if order_data.is_a?(Hash) && order_data['situacao'].is_a?(Hash) + order.update!( + situation_id: order_data['situacao']['id'].to_s, + date: order_data['data'], + value: order_data['total'], + # Add more fields as needed + ) + Rails.logger.info("Successfully updated order #{order.bling_order_id}") + else + Rails.logger.error("Invalid order data for order #{order.bling_order_id}: #{order_data}") + end + rescue StandardError => e + Rails.logger.error("Failed to update order #{order.bling_order_id}: #{e.message}") + end + + def delete_order(order) + order.destroy + Rails.logger.info("Deleted order #{order.bling_order_id} as it was not found in Bling API") + rescue StandardError => e + Rails.logger.error("Failed to delete order #{order.bling_order_id}: #{e.message}") + end +end \ No newline at end of file From 7586e28c581ca0dd4624702bc9d5b531e443cdee Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Mon, 26 Aug 2024 17:04:24 -0300 Subject: [PATCH 20/45] create a new job to update status and respective cron jobs --- app/jobs/update_bling_order_status_job.rb | 64 +++++++++++++++++++++++ config/environments/development.rb | 8 +++ config/environments/production.rb | 8 +++ config/environments/staging.rb | 8 +++ 4 files changed, 88 insertions(+) create mode 100644 app/jobs/update_bling_order_status_job.rb diff --git a/app/jobs/update_bling_order_status_job.rb b/app/jobs/update_bling_order_status_job.rb new file mode 100644 index 00000000..6e3b14e7 --- /dev/null +++ b/app/jobs/update_bling_order_status_job.rb @@ -0,0 +1,64 @@ +require 'retryable' + +class UpdateBlingOrderStatusJob < ApplicationJob + queue_as :default + + MAX_RETRIES = 3 + RETRY_DELAY = 5 # seconds + + def perform(current_status, new_status, tenant_id, batch_size = 100) + Rails.logger.info("Starting to update orders from status #{current_status} to #{new_status} for account #{tenant_id}") + + BlingOrderItem.where(account_id: tenant_id, situation_id: current_status) + .find_in_batches(batch_size: batch_size) do |batch| + update_batch(batch, new_status, tenant_id) + end + + Rails.logger.info("Finished updating orders for account #{tenant_id}") + end + + private + + def update_batch(batch, new_status, tenant_id) + order_ids = batch.map(&:bling_order_id) + + Retryable.retryable( + tries: MAX_RETRIES, + sleep: RETRY_DELAY, + on: [StandardError], + matching: /TOO_MANY_REQUESTS/, + exception_cb: Proc.new { |exception| + Rails.logger.warn("Retrying after error: #{exception.message}") + } + ) do + result = Services::Bling::UpdateOrderStatus.call( + tenant: tenant_id, + order_ids: order_ids, + new_status: new_status + ) + + process_results(result[:results], batch, new_status) + end + rescue StandardError => e + Rails.logger.error("Failed to update batch after #{MAX_RETRIES} retries: #{e.message}") + end + + def process_results(results, batch, new_status) + results.each do |result| + order = batch.find { |o| o.bling_order_id == result[:order_id] } + if result[:status] == 'success' + update_local_order(order, new_status) + else + Rails.logger.error("Failed to update order #{result[:order_id]}: #{result[:error]}") + end + end + end + + def update_local_order(order, new_status) + old_status = order.situation_id + order.update!(situation_id: new_status) + Rails.logger.info("Updated order #{order.bling_order_id} status from #{old_status} to #{new_status}") + rescue StandardError => e + Rails.logger.error("Failed to update local order #{order.bling_order_id}: #{e.message}") + end +end \ No newline at end of file diff --git a/config/environments/development.rb b/config/environments/development.rb index aa91589f..04a934fa 100644 --- a/config/environments/development.rb +++ b/config/environments/development.rb @@ -232,6 +232,14 @@ args: ['15', '9', 1], set: { priority: 2 }, description: 'Update new orders to fulfilled status' + }, + + change_printed_to_pending: { + cron: '0 17 * * *', + class: 'UpdateBlingOrderStatusJob', + args: ['95745', '94871', 1], + set: { priority: 2 }, + description: 'Change all printed orders to pending status daily at 17:00' } } end diff --git a/config/environments/production.rb b/config/environments/production.rb index ae845224..6684ba1d 100644 --- a/config/environments/production.rb +++ b/config/environments/production.rb @@ -250,6 +250,14 @@ args: ['15', '9', 1], set: { priority: 2 }, description: 'Update new orders to fulfilled status' + }, + + change_printed_to_pending: { + cron: '0 17 * * *', + class: 'UpdateBlingOrderStatusJob', + args: ['95745', '94871', 1], + set: { priority: 2 }, + description: 'Change all printed orders to pending status daily at 17:00' } } end diff --git a/config/environments/staging.rb b/config/environments/staging.rb index 14edaa02..8cb2677f 100644 --- a/config/environments/staging.rb +++ b/config/environments/staging.rb @@ -250,6 +250,14 @@ args: ['15', '9', 1], set: { priority: 2 }, description: 'Update new orders to fulfilled status' + }, + + change_printed_to_pending: { + cron: '0 17 * * *', + class: 'UpdateBlingOrderStatusJob', + args: ['95745', '94871', 1], + set: { priority: 2 }, + description: 'Change all printed orders to pending status daily at 17:00' } } end From e3b1860ed7c9417673ce146537a8b4fdcd779569 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Mon, 26 Aug 2024 17:07:34 -0300 Subject: [PATCH 21/45] update code --- app/jobs/find_orders_by_status_job.rb | 142 +++++++++++----------- app/jobs/update_bling_order_status_job.rb | 116 +++++++++--------- 2 files changed, 127 insertions(+), 131 deletions(-) diff --git a/app/jobs/find_orders_by_status_job.rb b/app/jobs/find_orders_by_status_job.rb index cfe30833..a3091d78 100644 --- a/app/jobs/find_orders_by_status_job.rb +++ b/app/jobs/find_orders_by_status_job.rb @@ -1,78 +1,76 @@ -require 'retryable' - -class ImprovedFindOrdersByStatusJob < ApplicationJob - queue_as :default - - MAX_RETRIES = 3 - RETRY_DELAY = 5 # seconds - - def perform(status, tenant_id) - orders = BlingOrderItem.where(account_id: tenant_id, situation_id: status) - bling_datum = BlingDatum.find_by(account_id: tenant_id) - - if bling_datum.nil? - Rails.logger.error("No BlingDatum found for account_id: #{tenant_id}") - return +class FindOrdersByStatusJob < ApplicationJob + queue_as :default + + MAX_RETRIES = 3 + RETRY_DELAY = 5 # seconds + + def perform(status, tenant_id) + orders = BlingOrderItem.where(account_id: tenant_id, situation_id: status) + bling_datum = BlingDatum.find_by(account_id: tenant_id) + + if bling_datum.nil? + Rails.logger.error("No BlingDatum found for account_id: #{tenant_id}") + return + end + + orders.find_each do |order| + process_order(order, tenant_id) + end end - - orders.find_each do |order| - process_order(order, tenant_id) + + private + + def process_order(order, tenant_id) + retry_count = 0 + begin + result = Services::Bling::FindOrder.call( + id: order.bling_order_id, + order_command: 'find_order', + tenant: tenant_id + ) + + if result.is_a?(Hash) && result['data'].present? + update_order(order, result['data']) + elsif result.is_a?(Hash) && result['error'].present? && result['error']['type'] == 'RESOURCE_NOT_FOUND' + delete_order(order) + else + Rails.logger.error("Failed to fetch order #{order.bling_order_id}: #{result}") + raise StandardError, result['error']['message'] if result.is_a?(Hash) && result['error'].present? + end + rescue StandardError => e + if e.message.match?(/TOO_MANY_REQUESTS/) && retry_count < MAX_RETRIES + retry_count += 1 + Rails.logger.warn("Retrying after TOO_MANY_REQUESTS error for order #{order.bling_order_id}. Attempt #{retry_count} of #{MAX_RETRIES}. #{e.message}") + sleep(RETRY_DELAY) + retry + else + Rails.logger.error("Failed to process order #{order.bling_order_id} after #{retry_count} retries: #{e.message}") + end + end end - end - - private - - def process_order(order, tenant_id) - Retryable.retryable( - tries: MAX_RETRIES, - sleep: RETRY_DELAY, - on: [StandardError], - matching: /TOO_MANY_REQUESTS/, - exception_cb: Proc.new { |exception| - Rails.logger.warn("Retrying after TOO_MANY_REQUESTS error for order #{order.bling_order_id}. #{exception.message}") - } - ) do - result = Services::Bling::FindOrder.call( - id: order.bling_order_id, - order_command: 'find_order', - tenant: tenant_id - ) - - if result.is_a?(Hash) && result['data'].present? - update_order(order, result['data']) - elsif result.is_a?(Hash) && result['error'].present? && result['error']['type'] == 'RESOURCE_NOT_FOUND' - delete_order(order) + + def update_order(order, data) + order_data = data['pedido'] || data + + if order_data.is_a?(Hash) && order_data['situacao'].is_a?(Hash) + order.update!( + situation_id: order_data['situacao']['id'].to_s, + date: order_data['data'], + value: order_data['total'], + # Add more fields as needed + ) + Rails.logger.info("Successfully updated order #{order.bling_order_id}") else - Rails.logger.error("Failed to fetch order #{order.bling_order_id}: #{result}") - raise StandardError, result['error']['message'] if result.is_a?(Hash) && result['error'].present? + Rails.logger.error("Invalid order data for order #{order.bling_order_id}: #{order_data}") end + rescue StandardError => e + Rails.logger.error("Failed to update order #{order.bling_order_id}: #{e.message}") end - rescue StandardError => e - Rails.logger.error("Failed to process order #{order.bling_order_id} after #{MAX_RETRIES} retries: #{e.message}") - end - - def update_order(order, data) - order_data = data['pedido'] || data - - if order_data.is_a?(Hash) && order_data['situacao'].is_a?(Hash) - order.update!( - situation_id: order_data['situacao']['id'].to_s, - date: order_data['data'], - value: order_data['total'], - # Add more fields as needed - ) - Rails.logger.info("Successfully updated order #{order.bling_order_id}") - else - Rails.logger.error("Invalid order data for order #{order.bling_order_id}: #{order_data}") + + def delete_order(order) + order.destroy + Rails.logger.info("Deleted order #{order.bling_order_id} as it was not found in Bling API") + rescue StandardError => e + Rails.logger.error("Failed to delete order #{order.bling_order_id}: #{e.message}") end - rescue StandardError => e - Rails.logger.error("Failed to update order #{order.bling_order_id}: #{e.message}") - end - - def delete_order(order) - order.destroy - Rails.logger.info("Deleted order #{order.bling_order_id} as it was not found in Bling API") - rescue StandardError => e - Rails.logger.error("Failed to delete order #{order.bling_order_id}: #{e.message}") - end -end \ No newline at end of file + end \ No newline at end of file diff --git a/app/jobs/update_bling_order_status_job.rb b/app/jobs/update_bling_order_status_job.rb index 6e3b14e7..7f513525 100644 --- a/app/jobs/update_bling_order_status_job.rb +++ b/app/jobs/update_bling_order_status_job.rb @@ -1,64 +1,62 @@ -require 'retryable' - class UpdateBlingOrderStatusJob < ApplicationJob - queue_as :default - - MAX_RETRIES = 3 - RETRY_DELAY = 5 # seconds - - def perform(current_status, new_status, tenant_id, batch_size = 100) - Rails.logger.info("Starting to update orders from status #{current_status} to #{new_status} for account #{tenant_id}") - - BlingOrderItem.where(account_id: tenant_id, situation_id: current_status) - .find_in_batches(batch_size: batch_size) do |batch| - update_batch(batch, new_status, tenant_id) + queue_as :default + + MAX_RETRIES = 3 + RETRY_DELAY = 5 # seconds + + def perform(current_status, new_status, tenant_id, batch_size = 100) + Rails.logger.info("Starting to update orders from status #{current_status} to #{new_status} for account #{tenant_id}") + + BlingOrderItem.where(account_id: tenant_id, situation_id: current_status) + .find_in_batches(batch_size: batch_size) do |batch| + update_batch(batch, new_status, tenant_id) + end + + Rails.logger.info("Finished updating orders for account #{tenant_id}") end - - Rails.logger.info("Finished updating orders for account #{tenant_id}") - end - - private - - def update_batch(batch, new_status, tenant_id) - order_ids = batch.map(&:bling_order_id) - - Retryable.retryable( - tries: MAX_RETRIES, - sleep: RETRY_DELAY, - on: [StandardError], - matching: /TOO_MANY_REQUESTS/, - exception_cb: Proc.new { |exception| - Rails.logger.warn("Retrying after error: #{exception.message}") - } - ) do - result = Services::Bling::UpdateOrderStatus.call( - tenant: tenant_id, - order_ids: order_ids, - new_status: new_status - ) - - process_results(result[:results], batch, new_status) + + private + + def update_batch(batch, new_status, tenant_id) + order_ids = batch.map(&:bling_order_id) + + retry_count = 0 + begin + result = Services::Bling::UpdateOrderStatus.call( + tenant: tenant_id, + order_ids: order_ids, + new_status: new_status + ) + + process_results(result[:results], batch, new_status) + rescue StandardError => e + if e.message.match?(/TOO_MANY_REQUESTS/) && retry_count < MAX_RETRIES + retry_count += 1 + Rails.logger.warn("Retrying after error: #{e.message}. Attempt #{retry_count} of #{MAX_RETRIES}") + sleep(RETRY_DELAY) + retry + else + Rails.logger.error("Failed to update batch after #{retry_count} retries: #{e.message}") + end + end end - rescue StandardError => e - Rails.logger.error("Failed to update batch after #{MAX_RETRIES} retries: #{e.message}") - end - - def process_results(results, batch, new_status) - results.each do |result| - order = batch.find { |o| o.bling_order_id == result[:order_id] } - if result[:status] == 'success' - update_local_order(order, new_status) - else - Rails.logger.error("Failed to update order #{result[:order_id]}: #{result[:error]}") + + def process_results(results, batch, new_status) + results.each do |result| + order = batch.find { |o| o.bling_order_id == result[:order_id] } + if result[:status] == 'success' + update_local_order(order, new_status) + else + Rails.logger.error("Failed to update order #{result[:order_id]}: #{result[:error]}") + end end end - end - - def update_local_order(order, new_status) - old_status = order.situation_id - order.update!(situation_id: new_status) - Rails.logger.info("Updated order #{order.bling_order_id} status from #{old_status} to #{new_status}") - rescue StandardError => e - Rails.logger.error("Failed to update local order #{order.bling_order_id}: #{e.message}") - end -end \ No newline at end of file + + def update_local_order(order, new_status) + old_status = order.situation_id + order.update!(situation_id: new_status) + Rails.logger.info("Updated order #{order.bling_order_id} status from #{old_status} to #{new_status}") + rescue StandardError => e + Rails.logger.error("Failed to update local order #{order.bling_order_id}: #{e.message}") + end + end \ No newline at end of file From 29c8a7f34b0651f6446a44fd807393f5a5061d48 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Mon, 26 Aug 2024 18:02:16 -0300 Subject: [PATCH 22/45] update cron --- config/environments/development.rb | 2 +- config/environments/production.rb | 2 +- config/environments/staging.rb | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/config/environments/development.rb b/config/environments/development.rb index 04a934fa..f0862be2 100644 --- a/config/environments/development.rb +++ b/config/environments/development.rb @@ -228,7 +228,7 @@ change_in_progress_to_fulfilled: { cron: '*/10 * * * *', - class: 'ChangeOrderStatusJob', + class: 'UpdateBlingOrderStatusJob', args: ['15', '9', 1], set: { priority: 2 }, description: 'Update new orders to fulfilled status' diff --git a/config/environments/production.rb b/config/environments/production.rb index 6684ba1d..8ac5c339 100644 --- a/config/environments/production.rb +++ b/config/environments/production.rb @@ -246,7 +246,7 @@ change_in_progress_to_fulfilled: { cron: '*/10 * * * *', - class: 'ChangeOrderStatusJob', + class: 'UpdateBlingOrderStatusJob', args: ['15', '9', 1], set: { priority: 2 }, description: 'Update new orders to fulfilled status' diff --git a/config/environments/staging.rb b/config/environments/staging.rb index 8cb2677f..a1153ebc 100644 --- a/config/environments/staging.rb +++ b/config/environments/staging.rb @@ -246,7 +246,7 @@ change_in_progress_to_fulfilled: { cron: '*/10 * * * *', - class: 'ChangeOrderStatusJob', + class: 'UpdateBlingOrderStatusJob', args: ['15', '9', 1], set: { priority: 2 }, description: 'Update new orders to fulfilled status' From 60a8dc6be9aec290d6630e08a212305127bcb264 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Tue, 27 Aug 2024 14:48:27 -0300 Subject: [PATCH 23/45] add new field to abc curve --- app/controllers/reports_controller.rb | 10 ++++++---- app/views/reports/top_selling_products.html.erb | 10 +++++++--- 2 files changed, 13 insertions(+), 7 deletions(-) diff --git a/app/controllers/reports_controller.rb b/app/controllers/reports_controller.rb index 7f1fc789..b7e12b79 100644 --- a/app/controllers/reports_controller.rb +++ b/app/controllers/reports_controller.rb @@ -58,13 +58,14 @@ def date_range def generate_csv CSV.generate(headers: true) do |csv| - csv << ['SKU', 'Total Quantity', 'Total Value', 'Cumulative Percentage', 'ABC Classification'] + csv << ['SKU', 'Total Quantity', 'Total Value', 'Proportional Percentage', 'Cumulative Percentage', 'ABC Classification'] cumulative_value = 0 @items.each do |item| + proportional_percentage = (item.total_value.to_f / @total_value * 100).round(2) cumulative_value += item.total_value - percentage = (cumulative_value.to_f / @total_value * 100).round(2) - classification = case percentage + cumulative_percentage = (cumulative_value.to_f / @total_value * 100).round(2) + classification = case cumulative_percentage when 0..80 then 'Curva A' when 80..95 then 'Curva B' else 'Curva C' @@ -74,7 +75,8 @@ def generate_csv item.sku, item.total_quantity, item.total_value, - percentage, + proportional_percentage, + cumulative_percentage, classification ] end diff --git a/app/views/reports/top_selling_products.html.erb b/app/views/reports/top_selling_products.html.erb index bab6938e..79f959dc 100644 --- a/app/views/reports/top_selling_products.html.erb +++ b/app/views/reports/top_selling_products.html.erb @@ -44,6 +44,7 @@ SKU Quantidade Total Valor Total + Porcentagem Proporcional Porcentagem Cumulativa Classificação ABC @@ -51,9 +52,10 @@ <% cumulative_value = 0 %> <% @items.each do |item| %> + <% proportional_percentage = (item.total_value.to_f / @total_value * 100).round(2) %> <% cumulative_value += item.total_value %> - <% percentage = (cumulative_value.to_f / @total_value * 100).round(2) %> - <% classification = case percentage + <% cumulative_percentage = (cumulative_value.to_f / @total_value * 100).round(2) %> + <% classification = case cumulative_percentage when 0..80 then 'Curva A' when 80..95 then 'Curva B' else 'Curva C' @@ -62,7 +64,8 @@ <%= item.sku %> <%= item.total_quantity %> <%= number_to_currency(item.total_value, unit: "R$", separator: ",", delimiter: ".") %> - <%= number_to_percentage(percentage, precision: 2) %> + <%= number_to_percentage(proportional_percentage, precision: 2) %> + <%= number_to_percentage(cumulative_percentage, precision: 2) %> <%= classification %> <% end %> @@ -74,6 +77,7 @@ + <%= content_for :javascript do %> diff --git a/app/views/orders_control/show_pending_orders.html.erb b/app/views/orders_control/show_pending_orders.html.erb index d3c8d7df..d5b89802 100644 --- a/app/views/orders_control/show_pending_orders.html.erb +++ b/app/views/orders_control/show_pending_orders.html.erb @@ -20,8 +20,8 @@ <% end %>
- <% if @pending_order_items.present? %> - <% @pending_order_items.group_by { |item| item.bling_order_item.store_name }.each do |loja_name, items| %> + <% if @all_items.present? %> + <% @all_items.group_by { |item| item.bling_order_item.store_name }.each do |loja_name, items| %>
@@ -37,6 +37,11 @@
Pedido: <%= item.bling_order_item.bling_order_id %>, Quantidade: <%= item.quantity %> unidades
Ver Pedido no Bling +

Status: <%= item.pending? ? 'Pendente' : 'Não Pendente' %>

+ <% if item.bling_order_item.situation_id == BlingOrderItem::Status::PENDING %> + <%= link_to 'Marcar como Pendente', update_status_item_path(item, status: 'pendente'), method: :patch, class: 'btn btn-success' %> + <%= link_to 'Marcar como Não Pendente', update_status_item_path(item, status: 'nao_pendente'), method: :patch, class: 'btn btn-danger' %> + <% end %>
<% end %> diff --git a/app/views/productions/_production_product_fields.html.erb b/app/views/productions/_production_product_fields.html.erb index d6b86b56..5d96a93b 100644 --- a/app/views/productions/_production_product_fields.html.erb +++ b/app/views/productions/_production_product_fields.html.erb @@ -1,10 +1,10 @@
-
+
<%= f.label :product_id, ProductionProduct.human_attribute_name(:product), class: 'form-label' %> - <%= f.collection_select :product_id, Product.all, :id, :name, { include_blank: true }, { class: 'form-control', required: true } %> + <%= f.collection_select :product_id, Product.all, :id, :sku, { include_blank: true }, { class: 'form-control select2', required: true } %>
-
+
<%= f.label :quantity, ProductionProduct.human_attribute_name(:quantity), class: 'form-label' %> <%= f.number_field :quantity, class: 'form-control', min: 1, required: true %>
diff --git a/app/views/productions/edit.html.erb b/app/views/productions/edit.html.erb index d3b9946b..d19c60a4 100644 --- a/app/views/productions/edit.html.erb +++ b/app/views/productions/edit.html.erb @@ -1,44 +1,92 @@

-<%= form_with(model: @production, local: true, html: { class: 'needs-validation', novalidate: '' }) do |form| %> +

Verify Production

- -
-
- <%= form.label :tailor_id, t('productions.form.tailor_selection'), class: 'form-label' %> - <%= form.collection_select :tailor_id, @tailors, :id, :name, { include_blank: true }, { class: 'form-control' } %> +<%- model_class = Production -%> +
+
+

<%= t '.title', :default => t("Edit #{model_class.model_name.human.titleize}") %>

+
+ + +
- -
-
- <%= form.label :cut_date, t('productions.form.cut_date'), class: 'form-label' %> - <%= form.date_field :cut_date, class: 'form-control' %> -
-
- <%= form.label :deliver_date, t('productions.form.deliver_date'), class: 'form-label' %> - <%= form.date_field :deliver_date, class: 'form-control' %> -
-
+
+
+
+

Edit Production

+
+
+ <%= form_with(model: @production, local: true) do |form| %> +
+
+ <%= form.label :tailor_id, model_class.human_attribute_name(:tailor), class: 'form-label' %> + <%= form.collection_select :tailor_id, @tailors, :id, :name, { prompt: 'Select a tailor' }, { class: 'form-control' } %> +
+
+ <%= form.label :cut_date, model_class.human_attribute_name(:cut_date), class: 'form-label' %> + <%= form.date_field :cut_date, class: 'form-control', readonly: true %> +
+
+ <%= form.label :expected_delivery_date, model_class.human_attribute_name(:expected_delivery_date), class: 'form-label' %> + <%= form.date_field :expected_delivery_date, class: 'form-control' %> +
+
- -
- <%= form.fields_for :production_products do |pp_form| %> - <%= render 'production_product_fields', f: pp_form %> - <% end %> - <%= link_to_add_association t('productions.form.add_product'), form, :production_products, class: 'btn btn-primary' %> -
+
+
+ <%= form.label :consider, model_class.human_attribute_name(:consider), class: 'form-check-label' %> + <%= form.check_box :consider, class: 'form-check-input' %> +
+
-
- <%= form.check_box :consider, class: 'form-check-input' %> - <%= form.label :consider, t('productions.form.consider'), class: 'form-check-label' %> -
+
+
+ <%= form.label :confirmed, model_class.human_attribute_name(:confirmed), class: 'form-check-label' %> + <%= form.check_box :confirmed, class: 'form-check-input' %> +
+
+ <%= form.label :paid, model_class.human_attribute_name(:paid), class: 'form-check-label' %> + <%= form.check_box :paid, class: 'form-check-input' %> +
+
+ +
+
+ <%= form.label :observation, model_class.human_attribute_name(:observation), class: 'form-label' %> + <%= form.text_area :observation, class: 'form-control' %> +
+
- -
-
- <%= form.submit @production.new_record? ? t('helpers.submit.create') : t('helpers.submit.update'), class: 'btn btn-success' %> +

Products

+
+ <%= form.fields_for :production_products do |pp_form| %> +
+
+ <%= pp_form.label :product_id, Product.model_name.human, class: 'form-label' %> + <%= pp_form.collection_select :product_id, Product.all, :id, :name, { include_blank: true }, { class: 'form-control', required: true } %> +
+
+ <%= pp_form.label :quantity, ProductionProduct.human_attribute_name(:quantity), class: 'form-label' %> + <%= pp_form.number_field :quantity, class: 'form-control', readonly: true %> +
+
+ <%= pp_form.label :pieces_delivered, ProductionProduct.human_attribute_name(:pieces_delivered), class: 'form-label' %> + <%= pp_form.number_field :pieces_delivered, class: 'form-control' %> +
+
+ <%= pp_form.label :pieces_missing, ProductionProduct.human_attribute_name(:pieces_missing), class: 'form-label' %> + <%= pp_form.number_field :pieces_missing, class: 'form-control', readonly: true %> +
+
+ <% end %> +
+ + <%= form.submit t('helpers.submit.update'), class: 'btn btn-primary' %> + <%= link_to t('.cancel', :default => t("helpers.links.cancel")), production_path(@production), class: 'btn btn-secondary' %> + <% end %> +
- -<% end %> +
diff --git a/app/views/productions/index.html.erb b/app/views/productions/index.html.erb index 9e1a853f..5b376262 100644 --- a/app/views/productions/index.html.erb +++ b/app/views/productions/index.html.erb @@ -12,14 +12,15 @@
<%= turbo_frame_tag :productions do %>
- - +
+ + @@ -28,12 +29,16 @@ + - + + From f5e9e68260160fd2e9f218d70a51c03dde6afaa2 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Mon, 2 Sep 2024 13:23:15 -0300 Subject: [PATCH 28/45] update the edit of productions --- app/views/productions/edit.html.erb | 10 +++------- 1 file changed, 3 insertions(+), 7 deletions(-) diff --git a/app/views/productions/edit.html.erb b/app/views/productions/edit.html.erb index d19c60a4..a28a6a25 100644 --- a/app/views/productions/edit.html.erb +++ b/app/views/productions/edit.html.erb @@ -63,22 +63,18 @@
<%= form.fields_for :production_products do |pp_form| %>
-
+
<%= pp_form.label :product_id, Product.model_name.human, class: 'form-label' %> <%= pp_form.collection_select :product_id, Product.all, :id, :name, { include_blank: true }, { class: 'form-control', required: true } %>
-
+
<%= pp_form.label :quantity, ProductionProduct.human_attribute_name(:quantity), class: 'form-label' %> <%= pp_form.number_field :quantity, class: 'form-control', readonly: true %>
-
+
<%= pp_form.label :pieces_delivered, ProductionProduct.human_attribute_name(:pieces_delivered), class: 'form-label' %> <%= pp_form.number_field :pieces_delivered, class: 'form-control' %>
-
- <%= pp_form.label :pieces_missing, ProductionProduct.human_attribute_name(:pieces_missing), class: 'form-label' %> - <%= pp_form.number_field :pieces_missing, class: 'form-control', readonly: true %> -
<% end %>
From 48afcf7a0cfbf406e6f868a8e38289dccaa05655 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Mon, 2 Sep 2024 13:28:54 -0300 Subject: [PATCH 29/45] fix to send the account_id to the tailor model --- app/controllers/tailors_controller.rb | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/app/controllers/tailors_controller.rb b/app/controllers/tailors_controller.rb index bcaec2a0..4fb59a72 100644 --- a/app/controllers/tailors_controller.rb +++ b/app/controllers/tailors_controller.rb @@ -44,6 +44,7 @@ def set_tailor end def tailor_params - params.require(:tailor).permit(:name, :production_id) + params['tailor']['account_id'] = current_tenant.id + params.require(:tailor).permit(:name, :production_id, :account_id) end end From 9ea2eb8d4279bb61e8751dc17a362ed761f004cc Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Mon, 2 Sep 2024 13:32:03 -0300 Subject: [PATCH 30/45] add the translantions --- config/locales/pt-BR.models.productions.yml | 52 ++++++++++++++++++--- 1 file changed, 46 insertions(+), 6 deletions(-) diff --git a/config/locales/pt-BR.models.productions.yml b/config/locales/pt-BR.models.productions.yml index c27cc325..416afc36 100644 --- a/config/locales/pt-BR.models.productions.yml +++ b/config/locales/pt-BR.models.productions.yml @@ -2,27 +2,67 @@ pt-BR: activerecord: models: production: "Produção" + production_product: "Produto da Produção" attributes: production: tailor: "Costureiro" cut_date: "Data de Corte" - deliver_date: "Data de Entrega" + delivery_date: "Data de Entrega" + expected_delivery_date: "Data Prevista de Entrega" consider: "Considerar" + confirmed: "Confirmado" + paid: "Pago" + observation: "Observação" + pieces_delivered: "Peças Entregues" + pieces_missing: "Peças Faltando" + production_product: + product: "Produto" + quantity: "Quantidade" + pieces_delivered: "Peças Entregues" + pieces_missing: "Peças Faltando" productions: index: title: "Produções" product_summary: "Resumo da Produção" no_tailor: "Nenhum" no_products: "Nenhum produto" + show: + title: "Detalhes da Produção" + tailor_details: "Detalhes do Costureiro" + production_data: "Dados da Produção" + product_details: "Detalhes dos Produtos" + totals: "Totais" + new: + title: "Nova Produção" + new_production: "Criar Nova Produção" + products: "Produtos" + add_product: "Adicionar Produto" + edit: + title: "Editar Produção" actions: show: "Mostrar" edit: "Editar" destroy: "Excluir" confirm: "Você tem certeza?" - new: - title: "Nova Produção" - edit: - title: "Editar Produção" + create: + production_created: "Produção criada com sucesso." + creation_failed: "Falha ao criar a produção." + update: + production_updated: "Produção atualizada com sucesso." + destroy: + production_destroyed: "Produção excluída com sucesso." + destruction_failed: "Falha ao excluir a produção." helpers: + submit: + create: "Criar %{model}" + update: "Atualizar %{model}" links: - new: "Novo" + new: "Nova Produção" + back: "Voltar" + edit: "Editar" + cancel: "Cancelar" + titles: + new: "Nova %{model}" + edit: "Editar %{model}" + actions: + remove: "Remover" From 0ed079bdff7cd3002dda3288691e700b049e2b15 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Mon, 2 Sep 2024 13:32:29 -0300 Subject: [PATCH 31/45] update the package.json --- package.json | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/package.json b/package.json index ae00fb77..b9e82a30 100644 --- a/package.json +++ b/package.json @@ -34,7 +34,7 @@ "webpack-dev-server": "^4.11.1" }, "engines": { - "node": "20.9.0", - "yarn": "1.22.19" + "node": "22.2.0", + "yarn": "1.22.22" } -} +} \ No newline at end of file From 76068e6251f3653640e2e8a1b64e2c4b557e52df Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Mon, 2 Sep 2024 13:47:59 -0300 Subject: [PATCH 32/45] update github workflow --- .github/workflows/main.yml | 4 ++-- app/controllers/orders_control_controller.rb | 11 +++++++---- 2 files changed, 9 insertions(+), 6 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index e1caa711..cd99aaa2 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -35,10 +35,10 @@ jobs: - name: Set up Node.js uses: actions/setup-node@v4 with: - node-version: '20.9.0' + node-version: '22.2.0' cache: 'yarn' - run: | - npm install -g yarn@1.22.19 + npm install -g yarn@1.22.22 yarn install --check-files - name: Set up Ruby diff --git a/app/controllers/orders_control_controller.rb b/app/controllers/orders_control_controller.rb index bcc4723a..26ff5355 100644 --- a/app/controllers/orders_control_controller.rb +++ b/app/controllers/orders_control_controller.rb @@ -24,21 +24,24 @@ def show_orders_products_stock def show_pending_orders situation_id = params[:situation_id] store_id = params[:store_id] - + if situation_id.present? cleaned_situation_ids = situation_id.split(',').map(&:to_i) else cleaned_situation_ids = BlingOrderItem::Status::PENDING end - + pending_items = Item.includes(:bling_order_item).where(bling_order_items: { situation_id: cleaned_situation_ids }) - + if store_id.present? @pending_order_items = pending_items.where(bling_order_items: { store_id: store_id }) else @pending_order_items = pending_items end - + + @pending_order_items.each(&:mark_as_pending) + #Item.where.not(id: @pending_order_items.ids).each(&:mark_as_not_pending) + respond_to do |format| format.html # show.html.erb format.csv { send_data generate_csv(@pending_order_items), filename: "pending-orders-#{Date.today}.csv" } From 1fc1a3bbd2db6e17d07de054ab5d06e6d3e33fc9 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Mon, 2 Sep 2024 13:50:18 -0300 Subject: [PATCH 33/45] remove --- app/controllers/orders_control_controller.rb | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/app/controllers/orders_control_controller.rb b/app/controllers/orders_control_controller.rb index 26ff5355..bcc4723a 100644 --- a/app/controllers/orders_control_controller.rb +++ b/app/controllers/orders_control_controller.rb @@ -24,24 +24,21 @@ def show_orders_products_stock def show_pending_orders situation_id = params[:situation_id] store_id = params[:store_id] - + if situation_id.present? cleaned_situation_ids = situation_id.split(',').map(&:to_i) else cleaned_situation_ids = BlingOrderItem::Status::PENDING end - + pending_items = Item.includes(:bling_order_item).where(bling_order_items: { situation_id: cleaned_situation_ids }) - + if store_id.present? @pending_order_items = pending_items.where(bling_order_items: { store_id: store_id }) else @pending_order_items = pending_items end - - @pending_order_items.each(&:mark_as_pending) - #Item.where.not(id: @pending_order_items.ids).each(&:mark_as_not_pending) - + respond_to do |format| format.html # show.html.erb format.csv { send_data generate_csv(@pending_order_items), filename: "pending-orders-#{Date.today}.csv" } From 4ec673bf94aac0fdd114431fde2569aa563056c2 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Mon, 2 Sep 2024 14:15:57 -0300 Subject: [PATCH 34/45] update to ruby 3.3.4 --- .github/workflows/main.yml | 2 +- .ruby-version | 2 +- Gemfile | 2 +- Gemfile.lock | 3 ++- 4 files changed, 5 insertions(+), 4 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index cd99aaa2..3ffa499a 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -44,7 +44,7 @@ jobs: - name: Set up Ruby uses: ruby/setup-ruby@v1 with: - ruby-version: 3.2.2 + ruby-version: 3.3.4 # runs 'bundle install' and cache installed gems automatically bundler-cache: true diff --git a/.ruby-version b/.ruby-version index be94e6f5..2c6109e5 100644 --- a/.ruby-version +++ b/.ruby-version @@ -1 +1 @@ -3.2.2 +3.3.4 \ No newline at end of file diff --git a/Gemfile b/Gemfile index 74eba967..64f9baed 100644 --- a/Gemfile +++ b/Gemfile @@ -1,7 +1,7 @@ source 'https://rubygems.org' git_source(:github) { |repo| "https://github.com/#{repo}.git" } -ruby '3.2.2' +ruby '3.3.4' # dotenv-rails must be on the top gem 'dotenv-rails', '>= 3.0.0', groups: %i[development test] diff --git a/Gemfile.lock b/Gemfile.lock index d6d3f32b..abd41e72 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -609,6 +609,7 @@ GEM PLATFORMS arm64-darwin-22 + arm64-darwin-23 x86_64-linux DEPENDENCIES @@ -685,7 +686,7 @@ DEPENDENCIES webmock (>= 3.20.0) RUBY VERSION - ruby 3.2.2p53 + ruby 3.3.4p94 BUNDLED WITH 2.4.6 From 146e0f9e1c453f236e043cc9069e2b33bae6a27a Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Mon, 2 Sep 2024 16:09:45 -0300 Subject: [PATCH 35/45] add new field --- app/controllers/productions_controller.rb | 2 +- app/helpers/application_helper.rb | 5 +++++ app/views/productions/_form.html.erb | 8 +++++++- app/views/productions/edit.html.erb | 10 +++++++--- app/views/productions/new.html.erb | 10 +++++++--- app/views/productions/show.html.erb | 12 ++++++++++-- config/locales/pt-BR.models.productions.yml | 1 + ...181724_add_service_order_number_to_productions.rb | 5 +++++ 8 files changed, 43 insertions(+), 10 deletions(-) create mode 100644 db/migrate/20240902181724_add_service_order_number_to_productions.rb diff --git a/app/controllers/productions_controller.rb b/app/controllers/productions_controller.rb index db6027ba..3ea9a343 100644 --- a/app/controllers/productions_controller.rb +++ b/app/controllers/productions_controller.rb @@ -66,7 +66,7 @@ def set_tailors def production_params params.require(:production).permit( - :tailor_id, :cut_date, :expected_delivery_date, + :cut_date, :tailor_id, :service_order_number, :expected_delivery_date, :confirmed, :paid, :consider, :observation, production_products_attributes: [:id, :product_id, :quantity, :pieces_delivered, :pieces_missing, :_destroy] ) diff --git a/app/helpers/application_helper.rb b/app/helpers/application_helper.rb index 44c1c3e2..224e3a15 100644 --- a/app/helpers/application_helper.rb +++ b/app/helpers/application_helper.rb @@ -65,6 +65,11 @@ def pt_datetime_format(time) time.to_datetime.strftime('%d-%m-%Y %H:%M:%S') end + def pt_only_date_format(time) + return 'N/A' if time.nil? + time.to_datetime.strftime('%d-%m-%Y') + end + # date format "%d/%m/%Y %H:%m" def display_status(status) if status diff --git a/app/views/productions/_form.html.erb b/app/views/productions/_form.html.erb index 3ac131a6..25cb546f 100644 --- a/app/views/productions/_form.html.erb +++ b/app/views/productions/_form.html.erb @@ -1,6 +1,6 @@ <%# app/views/productions/_form.html.erb %> -<%= form_with(model: [@account, production], local: true) do |form| %> +<%= form_with(model: production, local: true) do |form| %> <% if production.errors.any? %>

<%= pluralize(production.errors.count, "error") %> prohibited this production from being saved:

@@ -12,6 +12,11 @@
<% end %> +
+ <%= form.label :service_order_number %> + <%= form.text_field :service_order_number, class: 'form-control' %> +
+
<%= form.label :number %> <%= form.number_field :number, class: 'form-control' %> @@ -79,6 +84,7 @@
<%= form.submit class: 'btn btn-primary' %> + <%= link_to 'Verify', verify_account_production_path(@account, production), class: 'btn btn-secondary', method: :get if production.persisted? %> <% end %> <%# app/views/productions/_production_product_fields.html.erb %> diff --git a/app/views/productions/edit.html.erb b/app/views/productions/edit.html.erb index a28a6a25..efe3870c 100644 --- a/app/views/productions/edit.html.erb +++ b/app/views/productions/edit.html.erb @@ -20,15 +20,19 @@
<%= form_with(model: @production, local: true) do |form| %>
-
+
+ <%= form.label :service_order_number, model_class.human_attribute_name(:service_order_number), class: 'form-label' %> + <%= form.text_field :service_order_number, class: 'form-control' %> +
+
<%= form.label :tailor_id, model_class.human_attribute_name(:tailor), class: 'form-label' %> <%= form.collection_select :tailor_id, @tailors, :id, :name, { prompt: 'Select a tailor' }, { class: 'form-control' } %>
-
+
<%= form.label :cut_date, model_class.human_attribute_name(:cut_date), class: 'form-label' %> <%= form.date_field :cut_date, class: 'form-control', readonly: true %>
-
+
<%= form.label :expected_delivery_date, model_class.human_attribute_name(:expected_delivery_date), class: 'form-label' %> <%= form.date_field :expected_delivery_date, class: 'form-control' %>
diff --git a/app/views/productions/new.html.erb b/app/views/productions/new.html.erb index c8ec4b5c..78a71262 100644 --- a/app/views/productions/new.html.erb +++ b/app/views/productions/new.html.erb @@ -11,15 +11,19 @@
<%= form_with(model: @production, local: true) do |form| %>
-
+
+ <%= form.label :service_order_number, model_class.human_attribute_name(:service_order_number), class: 'form-label' %> + <%= form.text_field :service_order_number, class: 'form-control' %> +
+
<%= form.label :tailor_id, model_class.human_attribute_name(:tailor), class: 'form-label' %> <%= form.collection_select :tailor_id, @tailors, :id, :name, { prompt: 'Select a tailor' }, { class: 'form-control select2' } %>
-
+
<%= form.label :cut_date, model_class.human_attribute_name(:cut_date), class: 'form-label' %> <%= form.date_field :cut_date, class: 'form-control' %>
-
+
<%= form.label :expected_delivery_date, model_class.human_attribute_name(:expected_delivery_date), class: 'form-label' %> <%= form.date_field :expected_delivery_date, class: 'form-control' %>
diff --git a/app/views/productions/show.html.erb b/app/views/productions/show.html.erb index d74856d2..74a2091a 100644 --- a/app/views/productions/show.html.erb +++ b/app/views/productions/show.html.erb @@ -28,12 +28,20 @@
+
<%= model_class.human_attribute_name(:service_order_number) %>:
+
<%= @production.service_order_number %>
<%= model_class.human_attribute_name(:cut_date) %>:
-
<%= @production.cut_date %>
+
<%= pt_only_date_format(@production.cut_date) %>
<%= model_class.human_attribute_name(:expected_delivery_date) %>:
-
<%= @production.expected_delivery_date %>
+
<%= pt_only_date_format(@production.expected_delivery_date) %>
<%= model_class.human_attribute_name(:consider)%>:
<%= @production.consider ? 'Sim' : 'Não' %>
+
<%= model_class.human_attribute_name(:confirmed) %>:
+
<%= @production.confirmed ? 'Sim' : 'Não' %>
+
<%= model_class.human_attribute_name(:paid) %>:
+
<%= @production.paid ? 'Sim' : 'Não' %>
+
<%= model_class.human_attribute_name(:observation) %>:
+
<%= @production.observation %>
diff --git a/config/locales/pt-BR.models.productions.yml b/config/locales/pt-BR.models.productions.yml index 416afc36..0e3b0165 100644 --- a/config/locales/pt-BR.models.productions.yml +++ b/config/locales/pt-BR.models.productions.yml @@ -5,6 +5,7 @@ pt-BR: production_product: "Produto da Produção" attributes: production: + service_order_number: "Número da Ordem de Serviço" tailor: "Costureiro" cut_date: "Data de Corte" delivery_date: "Data de Entrega" diff --git a/db/migrate/20240902181724_add_service_order_number_to_productions.rb b/db/migrate/20240902181724_add_service_order_number_to_productions.rb new file mode 100644 index 00000000..715a2991 --- /dev/null +++ b/db/migrate/20240902181724_add_service_order_number_to_productions.rb @@ -0,0 +1,5 @@ +class AddServiceOrderNumberToProductions < ActiveRecord::Migration[7.0] + def change + add_column :productions, :service_order_number, :string + end +end From ff2128b52a814e5b426939c578b617963f8787a5 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Tue, 3 Sep 2024 15:01:29 -0300 Subject: [PATCH 36/45] update the missing pieces view --- app/controllers/productions_controller.rb | 7 +++ app/helpers/application_helper.rb | 4 +- app/models/bling_order_item.rb | 2 + app/models/localization.rb | 21 ++++++- app/models/production.rb | 3 + app/models/production_product.rb | 16 ++--- app/views/productions/index.html.erb | 1 + app/views/productions/missing_pieces.html.erb | 36 +++++++++++ app/views/productions/show.html.erb | 1 + app/views/shared/_sidebar.html.erb | 3 + config/locales/pt-BR.models.productions.yml | 5 ++ config/locales/sidebar.pt-BR.yml | 1 + config/routes.rb | 6 +- db/schema.rb | 62 ++++++++++++++++--- spec/factories/bling_order_items.rb | 48 +++++++------- spec/factories/productions.rb | 31 +++++++--- spec/models/bling_order_item_spec.rb | 46 +++++++------- spec/models/production_spec.rb | 31 +++++++--- 18 files changed, 240 insertions(+), 84 deletions(-) create mode 100644 app/views/productions/missing_pieces.html.erb diff --git a/app/controllers/productions_controller.rb b/app/controllers/productions_controller.rb index 3ea9a343..3edc27db 100644 --- a/app/controllers/productions_controller.rb +++ b/app/controllers/productions_controller.rb @@ -54,6 +54,13 @@ def destroy end end + def missing_pieces + @productions_with_missing_pieces = Production.includes(:tailor, production_products: :product) + .where(id: ProductionProduct.select(:production_id) + .where('quantity > COALESCE(pieces_delivered, 0)')) + .distinct + end + private def set_production diff --git a/app/helpers/application_helper.rb b/app/helpers/application_helper.rb index 224e3a15..2c0d37e8 100644 --- a/app/helpers/application_helper.rb +++ b/app/helpers/application_helper.rb @@ -80,7 +80,9 @@ def display_status(status) end def localize(object, options = {}) - super(object, options) if object + return nil if object.nil? + format = options[:format] || :default + I18n.localize(object, format: format) end alias l localize diff --git a/app/models/bling_order_item.rb b/app/models/bling_order_item.rb index a2f34efa..ae83d1c8 100644 --- a/app/models/bling_order_item.rb +++ b/app/models/bling_order_item.rb @@ -5,6 +5,7 @@ # id :bigint not null, primary key # aliquotaIPI :decimal(, ) # alteration_date :datetime +# city :string(10485760) # codigo :string # collected_alteration_date :date # date :datetime @@ -13,6 +14,7 @@ # descricaoDetalhada :text # items :jsonb # quantidade :integer +# state :string(10485760) # unidade :string # valor :decimal(, ) # value :decimal(, ) diff --git a/app/models/localization.rb b/app/models/localization.rb index 9ae14d2d..0e847715 100644 --- a/app/models/localization.rb +++ b/app/models/localization.rb @@ -1,4 +1,23 @@ +# == Schema Information +# +# Table name: localizations +# +# id :bigint not null, primary key +# address :string +# city :string +# complement :string +# country_name :string +# name :string +# neighborhood :string +# number :string +# state :string +# zip_code :string +# created_at :datetime not null +# updated_at :datetime not null +# account_id :integer +# bling_order_item_id :bigint +# class Localization < ApplicationRecord belongs_to :account belongs_to :bling_order_item, optional: false -end \ No newline at end of file +end diff --git a/app/models/production.rb b/app/models/production.rb index c85c89b5..c3f0c72e 100644 --- a/app/models/production.rb +++ b/app/models/production.rb @@ -7,6 +7,7 @@ # consider :boolean default(FALSE) # cut_date :datetime # deliver_date :datetime +# delivery_date :date # expected_delivery_date :date # observation :text # paid :boolean @@ -21,6 +22,7 @@ # # index_productions_on_account_id (account_id) # index_productions_on_cut_date (cut_date) +# index_productions_on_delivery_date (delivery_date) # index_productions_on_expected_delivery_date (expected_delivery_date) # index_productions_on_tailor_id (tailor_id) # @@ -41,6 +43,7 @@ class Production < ApplicationRecord validates :cut_date, presence: true validates :tailor, presence: true validates :account, presence: true + validates :service_order_number, presence: true, uniqueness: { scope: :account_id } # Add a method to calculate total pieces delivered def total_pieces_delivered diff --git a/app/models/production_product.rb b/app/models/production_product.rb index f947a477..81045b90 100644 --- a/app/models/production_product.rb +++ b/app/models/production_product.rb @@ -2,14 +2,14 @@ # # Table name: production_products # -# id :bigint not null, primary key -# pieces_delivered :integer -# pieces_missing :integer -# quantity :integer -# created_at :datetime not null -# updated_at :datetime not null -# product_id :bigint not null -# production_id :bigint not null +# id :bigint not null, primary key +# pieces_delivered :integer +# pieces_missing :integer +# quantity :integer +# created_at :datetime not null +# updated_at :datetime not null +# product_id :bigint not null +# production_id :bigint not null # # Indexes # diff --git a/app/views/productions/index.html.erb b/app/views/productions/index.html.erb index 5b376262..39bbcd68 100644 --- a/app/views/productions/index.html.erb +++ b/app/views/productions/index.html.erb @@ -7,6 +7,7 @@
<%= link_to t('helpers.links.new'), new_production_path, class: 'btn btn-primary mb-3' %> + <%= link_to t('productions.missing_pieces.title'), missing_pieces_productions_path, class: 'btn btn btn-info mb-3 ml-2' %>
diff --git a/app/views/productions/missing_pieces.html.erb b/app/views/productions/missing_pieces.html.erb new file mode 100644 index 00000000..6e8abcc5 --- /dev/null +++ b/app/views/productions/missing_pieces.html.erb @@ -0,0 +1,36 @@ +

+
+

Peças Faltantes

+ +
+ <% @productions_with_missing_pieces.each do |production| %> +
+
+
+

+ <%= t('.service_order', number: production.service_order_number.presence || 'N/A') %> +

+
+
+

<%= Production.human_attribute_name(:tailor) %>: <%= production.tailor.name %>

+

<%= Production.human_attribute_name(:cut_date) %>: <%= l(production.cut_date) if production.cut_date %>

+

<%= Production.human_attribute_name(:expected_delivery_date) %>: <%= l(production.expected_delivery_date) if production.expected_delivery_date %>

+
<%= t('.missing_pieces') %>:
+
    + <% production.production_products.each do |pp| %> + <% pieces_missing = pp.quantity - (pp.pieces_delivered || 0) %> + <% if pieces_missing > 0 %> +
  • <%= "#{pp.product.name}: #{pieces_missing}" %>
  • + <% end %> + <% end %> +
+
+ +
+
+ <% end %> +
+
\ No newline at end of file diff --git a/app/views/productions/show.html.erb b/app/views/productions/show.html.erb index 74a2091a..34e70bb0 100644 --- a/app/views/productions/show.html.erb +++ b/app/views/productions/show.html.erb @@ -88,6 +88,7 @@
<%= link_to t('.back', :default => t("helpers.links.back")), productions_path, :class => 'btn btn-secondary' %> <%= link_to t('.edit', :default => t("helpers.links.edit")), edit_production_path(@production), :class => 'btn btn-warning' %> + <%= link_to t('productions.missing_pieces.title'), missing_pieces_productions_path, class: 'btn btn-info' %> <%= link_to t('.destroy', :default => t("helpers.links.destroy")), production_path(@production), :method => 'delete', :data => { :confirm => t('.confirm', :default => t("helpers.links.confirm", :default => 'Are you sure?')) }, :class => 'btn btn-danger' %> diff --git a/app/views/shared/_sidebar.html.erb b/app/views/shared/_sidebar.html.erb index 68711a51..1c58845a 100644 --- a/app/views/shared/_sidebar.html.erb +++ b/app/views/shared/_sidebar.html.erb @@ -30,6 +30,9 @@
  • <%= link_to t("productions.create"), new_production_path, class: 'nav-link' %>
  • +
  • + <%= link_to t("productions.missing_pieces"), missing_pieces_productions_path, class: 'nav-link' %> +
  • <%= link_to t("tailors.list"), tailors_path, class: 'nav-link' %>
  • diff --git a/config/locales/pt-BR.models.productions.yml b/config/locales/pt-BR.models.productions.yml index 0e3b0165..2af08616 100644 --- a/config/locales/pt-BR.models.productions.yml +++ b/config/locales/pt-BR.models.productions.yml @@ -53,6 +53,11 @@ pt-BR: destroy: production_destroyed: "Produção excluída com sucesso." destruction_failed: "Falha ao excluir a produção." + missing_pieces: + title: "Produções com Peças Faltantes" + production_number: "Produção #%{number}" + missing_pieces: "Peças Faltantes" + service_order: "Ordem de Serviço #%{number}" helpers: submit: create: "Criar %{model}" diff --git a/config/locales/sidebar.pt-BR.yml b/config/locales/sidebar.pt-BR.yml index 16c75e3e..dba334c1 100644 --- a/config/locales/sidebar.pt-BR.yml +++ b/config/locales/sidebar.pt-BR.yml @@ -13,6 +13,7 @@ pt-BR: productions: one: Produção two: Produções + missing_pieces: "Peças Faltantes" list: Lista de Produções create: Criar Produção tailors: diff --git a/config/routes.rb b/config/routes.rb index 2210d9e4..5a1e60db 100644 --- a/config/routes.rb +++ b/config/routes.rb @@ -5,9 +5,11 @@ mount GoodJob::Engine => 'good_job' resources :productions do + collection do + get 'missing_pieces' + end member do - get :verify - patch :verify, to: 'productions#update' + patch :verify end end diff --git a/db/schema.rb b/db/schema.rb index 2063864f..abe68994 100644 --- a/db/schema.rb +++ b/db/schema.rb @@ -10,8 +10,7 @@ # # It's strongly recommended that you check this file into your version control system. - -ActiveRecord::Schema[7.0].define(version: 2024_02_09_142949) do +ActiveRecord::Schema[7.0].define(version: 2024_09_01_200830) do # These are extensions that must be enabled in order to support this database enable_extension "pgcrypto" enable_extension "plpgsql" @@ -37,7 +36,7 @@ t.string "record_type", null: false t.bigint "record_id", null: false t.bigint "blob_id", null: false - t.datetime "created_at", precision: nil, null: false + t.datetime "created_at", null: false t.index ["blob_id"], name: "index_active_storage_attachments_on_blob_id" t.index ["record_type", "record_id", "name", "blob_id"], name: "index_active_storage_attachments_uniqueness", unique: true end @@ -49,7 +48,7 @@ t.text "metadata" t.bigint "byte_size", null: false t.string "checksum" - t.datetime "created_at", precision: nil, null: false + t.datetime "created_at", null: false t.string "service_name", null: false t.index ["key"], name: "index_active_storage_blobs_on_key", unique: true end @@ -92,12 +91,16 @@ t.string "marketplace_code_id" t.integer "bling_id" t.bigint "account_id" - t.decimal "value" t.jsonb "items" + t.decimal "value" t.date "collected_alteration_date" t.string "original_situation_id" + t.string "city", limit: 10485760 + t.string "state", limit: 10485760 t.index ["account_id"], name: "index_bling_order_items_on_account_id" + t.index ["bling_order_id"], name: "bling_order_id_index_on_bling_order_items" t.index ["bling_order_id"], name: "index_bling_order_items_on_bling_order_id", unique: true + t.index ["situation_id", "store_id"], name: "situation_id_index_on_bling_order_items" end create_table "categories", force: :cascade do |t| @@ -163,13 +166,17 @@ t.datetime "finished_at" t.text "error" t.integer "error_event", limit: 2 + t.text "error_backtrace", array: true + t.uuid "process_id" t.index ["active_job_id", "created_at"], name: "index_good_job_executions_on_active_job_id_and_created_at" + t.index ["process_id", "created_at"], name: "index_good_job_executions_on_process_id_and_created_at" end create_table "good_job_processes", id: :uuid, default: -> { "gen_random_uuid()" }, force: :cascade do |t| t.datetime "created_at", null: false t.datetime "updated_at", null: false t.jsonb "state" + t.integer "lock_type", limit: 2 end create_table "good_job_settings", id: :uuid, default: -> { "gen_random_uuid()" }, force: :cascade do |t| @@ -202,6 +209,8 @@ t.text "job_class" t.integer "error_event", limit: 2 t.text "labels", array: true + t.uuid "locked_by_id" + t.datetime "locked_at" t.index ["active_job_id", "created_at"], name: "index_good_jobs_on_active_job_id_and_created_at" t.index ["batch_callback_id"], name: "index_good_jobs_on_batch_callback_id", where: "(batch_callback_id IS NOT NULL)" t.index ["batch_id"], name: "index_good_jobs_on_batch_id", where: "(batch_id IS NOT NULL)" @@ -210,7 +219,10 @@ t.index ["cron_key", "cron_at"], name: "index_good_jobs_on_cron_key_and_cron_at_cond", unique: true, where: "(cron_key IS NOT NULL)" t.index ["finished_at"], name: "index_good_jobs_jobs_on_finished_at", where: "((retried_good_job_id IS NULL) AND (finished_at IS NOT NULL))" t.index ["labels"], name: "index_good_jobs_on_labels", where: "(labels IS NOT NULL)", using: :gin + t.index ["locked_by_id"], name: "index_good_jobs_on_locked_by_id", where: "(locked_by_id IS NOT NULL)" + t.index ["priority", "created_at"], name: "index_good_job_jobs_for_candidate_lookup", where: "(finished_at IS NULL)" t.index ["priority", "created_at"], name: "index_good_jobs_jobs_on_priority_created_at_when_unfinished", order: { priority: "DESC NULLS LAST" }, where: "(finished_at IS NULL)" + t.index ["priority", "scheduled_at"], name: "index_good_jobs_on_priority_scheduled_at_unfinished_unlocked", where: "((finished_at IS NULL) AND (locked_by_id IS NULL))" t.index ["queue_name", "scheduled_at"], name: "index_good_jobs_on_queue_name_and_scheduled_at", where: "(finished_at IS NULL)" t.index ["scheduled_at"], name: "index_good_jobs_on_scheduled_at", where: "(finished_at IS NULL)" end @@ -245,6 +257,23 @@ t.bigint "bling_order_item_id" t.datetime "created_at", null: false t.datetime "updated_at", null: false + t.boolean "pending", default: false + end + + create_table "localizations", force: :cascade do |t| + t.string "name" + t.string "address" + t.string "number" + t.string "complement" + t.string "city" + t.string "state" + t.string "zip_code" + t.string "neighborhood" + t.string "country_name" + t.integer "account_id" + t.bigint "bling_order_item_id" + t.datetime "created_at", null: false + t.datetime "updated_at", null: false end create_table "post_data", force: :cascade do |t| @@ -254,7 +283,7 @@ t.string "post_code" t.string "post_type" t.float "value" - t.datetime "send_date", precision: nil + t.datetime "send_date" t.datetime "created_at", null: false t.datetime "updated_at", null: false end @@ -265,6 +294,8 @@ t.integer "quantity" t.datetime "created_at", null: false t.datetime "updated_at", null: false + t.integer "pieces_delivered" + t.integer "pieces_missing" t.index ["product_id"], name: "index_production_products_on_product_id" t.index ["production_id"], name: "index_production_products_on_production_id" end @@ -277,7 +308,17 @@ t.integer "account_id" t.bigint "tailor_id" t.boolean "consider", default: false + t.date "delivery_date" + t.integer "pieces_delivered" + t.integer "pieces_missing" + t.date "expected_delivery_date" + t.boolean "confirmed" + t.boolean "paid" + t.text "observation" t.index ["account_id"], name: "index_productions_on_account_id" + t.index ["cut_date"], name: "index_productions_on_cut_date" + t.index ["delivery_date"], name: "index_productions_on_delivery_date" + t.index ["expected_delivery_date"], name: "index_productions_on_expected_delivery_date" t.index ["tailor_id"], name: "index_productions_on_tailor_id" end @@ -374,7 +415,7 @@ create_table "simplo_clients", force: :cascade do |t| t.string "name" t.integer "age" - t.datetime "order_date", precision: nil + t.datetime "order_date" t.datetime "created_at", null: false t.datetime "updated_at", null: false end @@ -388,7 +429,7 @@ t.float "valor_total" t.float "peso" t.float "desconto" - t.datetime "data_pedido", precision: nil + t.datetime "data_pedido" t.datetime "created_at", null: false t.datetime "updated_at", null: false t.string "order_id" @@ -485,8 +526,8 @@ t.string "email", default: "", null: false t.string "encrypted_password", default: "", null: false t.string "reset_password_token" - t.datetime "reset_password_sent_at", precision: nil - t.datetime "remember_created_at", precision: nil + t.datetime "reset_password_sent_at" + t.datetime "remember_created_at" t.datetime "created_at", null: false t.datetime "updated_at", null: false t.string "first_name" @@ -505,6 +546,7 @@ add_foreign_key "group_products", "products" add_foreign_key "production_products", "productions" add_foreign_key "production_products", "products" + add_foreign_key "productions", "accounts" add_foreign_key "productions", "tailors" add_foreign_key "products", "categories" add_foreign_key "purchase_products", "products" diff --git a/spec/factories/bling_order_items.rb b/spec/factories/bling_order_items.rb index 5c8c13e6..bce90489 100644 --- a/spec/factories/bling_order_items.rb +++ b/spec/factories/bling_order_items.rb @@ -2,32 +2,38 @@ # # Table name: bling_order_items # -# id :bigint not null, primary key -# aliquotaIPI :decimal(, ) -# alteration_date :datetime -# codigo :string -# date :datetime -# desconto :decimal(, ) -# descricao :text -# descricaoDetalhada :text -# items :jsonb -# quantidade :integer -# unidade :string -# valor :decimal(, ) -# value :decimal(, ) -# created_at :datetime not null -# updated_at :datetime not null -# account_id :bigint -# bling_id :integer -# bling_order_id :string -# marketplace_code_id :string -# situation_id :string -# store_id :string +# id :bigint not null, primary key +# aliquotaIPI :decimal(, ) +# alteration_date :datetime +# city :string(10485760) +# codigo :string +# collected_alteration_date :date +# date :datetime +# desconto :decimal(, ) +# descricao :text +# descricaoDetalhada :text +# items :jsonb +# quantidade :integer +# state :string(10485760) +# unidade :string +# valor :decimal(, ) +# value :decimal(, ) +# created_at :datetime not null +# updated_at :datetime not null +# account_id :bigint +# bling_id :integer +# bling_order_id :string +# marketplace_code_id :string +# original_situation_id :string +# situation_id :string +# store_id :string # # Indexes # +# bling_order_id_index_on_bling_order_items (bling_order_id) # index_bling_order_items_on_account_id (account_id) # index_bling_order_items_on_bling_order_id (bling_order_id) UNIQUE +# situation_id_index_on_bling_order_items (situation_id,store_id) # FactoryBot.define do factory :bling_order_item do diff --git a/spec/factories/productions.rb b/spec/factories/productions.rb index 13c18e50..32e5f320 100644 --- a/spec/factories/productions.rb +++ b/spec/factories/productions.rb @@ -2,22 +2,33 @@ # # Table name: productions # -# id :bigint not null, primary key -# consider :boolean default(FALSE) -# cut_date :datetime -# deliver_date :datetime -# created_at :datetime not null -# updated_at :datetime not null -# account_id :integer -# tailor_id :bigint +# id :bigint not null, primary key +# confirmed :boolean +# consider :boolean default(FALSE) +# cut_date :datetime +# deliver_date :datetime +# delivery_date :date +# expected_delivery_date :date +# observation :text +# paid :boolean +# pieces_delivered :integer +# pieces_missing :integer +# created_at :datetime not null +# updated_at :datetime not null +# account_id :integer +# tailor_id :bigint # # Indexes # -# index_productions_on_account_id (account_id) -# index_productions_on_tailor_id (tailor_id) +# index_productions_on_account_id (account_id) +# index_productions_on_cut_date (cut_date) +# index_productions_on_delivery_date (delivery_date) +# index_productions_on_expected_delivery_date (expected_delivery_date) +# index_productions_on_tailor_id (tailor_id) # # Foreign Keys # +# fk_rails_... (account_id => accounts.id) # fk_rails_... (tailor_id => tailors.id) # FactoryBot.define do diff --git a/spec/models/bling_order_item_spec.rb b/spec/models/bling_order_item_spec.rb index 9405c41e..da17301a 100644 --- a/spec/models/bling_order_item_spec.rb +++ b/spec/models/bling_order_item_spec.rb @@ -2,34 +2,38 @@ # # Table name: bling_order_items # -# id :bigint not null, primary key -# aliquotaIPI :decimal(, ) -# alteration_date :datetime -# codigo :string +# id :bigint not null, primary key +# aliquotaIPI :decimal(, ) +# alteration_date :datetime +# city :string(10485760) +# codigo :string # collected_alteration_date :date -# date :datetime -# desconto :decimal(, ) -# descricao :text -# descricaoDetalhada :text -# items :jsonb -# quantidade :integer -# unidade :string -# valor :decimal(, ) -# value :decimal(, ) -# created_at :datetime not null -# updated_at :datetime not null -# account_id :bigint -# bling_id :integer -# bling_order_id :string -# marketplace_code_id :string +# date :datetime +# desconto :decimal(, ) +# descricao :text +# descricaoDetalhada :text +# items :jsonb +# quantidade :integer +# state :string(10485760) +# unidade :string +# valor :decimal(, ) +# value :decimal(, ) +# created_at :datetime not null +# updated_at :datetime not null +# account_id :bigint +# bling_id :integer +# bling_order_id :string +# marketplace_code_id :string # original_situation_id :string -# situation_id :string -# store_id :string +# situation_id :string +# store_id :string # # Indexes # +# bling_order_id_index_on_bling_order_items (bling_order_id) # index_bling_order_items_on_account_id (account_id) # index_bling_order_items_on_bling_order_id (bling_order_id) UNIQUE +# situation_id_index_on_bling_order_items (situation_id,store_id) # require 'rails_helper' diff --git a/spec/models/production_spec.rb b/spec/models/production_spec.rb index 4320f6ef..85129a3e 100644 --- a/spec/models/production_spec.rb +++ b/spec/models/production_spec.rb @@ -2,22 +2,33 @@ # # Table name: productions # -# id :bigint not null, primary key -# consider :boolean default(FALSE) -# cut_date :datetime -# deliver_date :datetime -# created_at :datetime not null -# updated_at :datetime not null -# account_id :integer -# tailor_id :bigint +# id :bigint not null, primary key +# confirmed :boolean +# consider :boolean default(FALSE) +# cut_date :datetime +# deliver_date :datetime +# delivery_date :date +# expected_delivery_date :date +# observation :text +# paid :boolean +# pieces_delivered :integer +# pieces_missing :integer +# created_at :datetime not null +# updated_at :datetime not null +# account_id :integer +# tailor_id :bigint # # Indexes # -# index_productions_on_account_id (account_id) -# index_productions_on_tailor_id (tailor_id) +# index_productions_on_account_id (account_id) +# index_productions_on_cut_date (cut_date) +# index_productions_on_delivery_date (delivery_date) +# index_productions_on_expected_delivery_date (expected_delivery_date) +# index_productions_on_tailor_id (tailor_id) # # Foreign Keys # +# fk_rails_... (account_id => accounts.id) # fk_rails_... (tailor_id => tailors.id) # require 'rails_helper' From c00a9c733d279217a814d482b0ea7f54000aba04 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Tue, 3 Sep 2024 16:17:21 -0300 Subject: [PATCH 37/45] and tailor filter and fix the translations --- app/controllers/productions_controller.rb | 4 ++++ app/views/productions/missing_pieces.html.erb | 13 ++++++++++++- app/views/shared/_sidebar.html.erb | 2 +- config/locales/pt-BR.models.productions.yml | 13 ++++++++----- config/locales/sidebar.pt-BR.yml | 2 +- 5 files changed, 26 insertions(+), 8 deletions(-) diff --git a/app/controllers/productions_controller.rb b/app/controllers/productions_controller.rb index 3edc27db..a9402d0f 100644 --- a/app/controllers/productions_controller.rb +++ b/app/controllers/productions_controller.rb @@ -59,6 +59,10 @@ def missing_pieces .where(id: ProductionProduct.select(:production_id) .where('quantity > COALESCE(pieces_delivered, 0)')) .distinct + + if params[:tailor_id].present? + @productions_with_missing_pieces = @productions_with_missing_pieces.where(tailor_id: params[:tailor_id]) + end end private diff --git a/app/views/productions/missing_pieces.html.erb b/app/views/productions/missing_pieces.html.erb index 6e8abcc5..c21f709d 100644 --- a/app/views/productions/missing_pieces.html.erb +++ b/app/views/productions/missing_pieces.html.erb @@ -1,6 +1,17 @@

    -

    Peças Faltantes

    +

    <%= t('productions.missing_pieces.title') %>

    + + <%= form_tag missing_pieces_productions_path, method: :get, class: 'mb-4' do %> +
    + <%= label_tag :tailor_id, t('.filter_by_tailor') %> + <%= select_tag :tailor_id, + options_from_collection_for_select(Tailor.all, :id, :name, params[:tailor_id]), + include_blank: t('.all_tailors'), + class: 'form-control' %> +
    + <%= submit_tag t('productions.missing_pieces.apply_filter'), class: 'btn btn-primary' %> + <% end %>
    <% @productions_with_missing_pieces.each do |production| %> diff --git a/app/views/shared/_sidebar.html.erb b/app/views/shared/_sidebar.html.erb index 1c58845a..3a2f573a 100644 --- a/app/views/shared/_sidebar.html.erb +++ b/app/views/shared/_sidebar.html.erb @@ -31,7 +31,7 @@ <%= link_to t("productions.create"), new_production_path, class: 'nav-link' %>
  • - <%= link_to t("productions.missing_pieces"), missing_pieces_productions_path, class: 'nav-link' %> + <%= link_to t("productions.side_missing_pieces"), missing_pieces_productions_path, class: 'nav-link' %>
  • <%= link_to t("tailors.list"), tailors_path, class: 'nav-link' %> diff --git a/config/locales/pt-BR.models.productions.yml b/config/locales/pt-BR.models.productions.yml index 2af08616..f59c3173 100644 --- a/config/locales/pt-BR.models.productions.yml +++ b/config/locales/pt-BR.models.productions.yml @@ -27,6 +27,14 @@ pt-BR: product_summary: "Resumo da Produção" no_tailor: "Nenhum" no_products: "Nenhum produto" + missing_pieces: + title: "Produções com Peças Faltantes" + filter_by_tailor: "Filtrar por Costureiro" + all_tailors: "Todos os Costureiros" + apply_filter: "Aplicar Filtro" + production_number: "Produção #%{number}" + missing_pieces: "Peças Faltantes" + service_order: "Ordem de Serviço #%{number}" show: title: "Detalhes da Produção" tailor_details: "Detalhes do Costureiro" @@ -53,11 +61,6 @@ pt-BR: destroy: production_destroyed: "Produção excluída com sucesso." destruction_failed: "Falha ao excluir a produção." - missing_pieces: - title: "Produções com Peças Faltantes" - production_number: "Produção #%{number}" - missing_pieces: "Peças Faltantes" - service_order: "Ordem de Serviço #%{number}" helpers: submit: create: "Criar %{model}" diff --git a/config/locales/sidebar.pt-BR.yml b/config/locales/sidebar.pt-BR.yml index dba334c1..fdc71d5e 100644 --- a/config/locales/sidebar.pt-BR.yml +++ b/config/locales/sidebar.pt-BR.yml @@ -13,7 +13,7 @@ pt-BR: productions: one: Produção two: Produções - missing_pieces: "Peças Faltantes" + side_missing_pieces: "Peças Faltantes" list: Lista de Produções create: Criar Produção tailors: From e5dac530d81ab7d66aa2d365605d2cc15b140bf6 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Tue, 3 Sep 2024 17:09:37 -0300 Subject: [PATCH 38/45] change the fields to the rule of business --- app/controllers/productions_controller.rb | 3 ++- app/models/production.rb | 7 ++----- app/models/production_product.rb | 3 +-- app/views/productions/edit.html.erb | 13 ++++++++----- app/views/productions/index.html.erb | 4 ++-- app/views/productions/missing_pieces.html.erb | 2 +- app/views/productions/show.html.erb | 4 +++- config/locales/pt-BR.models.productions.yml | 1 + ...20240903193442_remove_columns_from_production.rb | 7 +++++++ ...93443_add_delivery_date_to_production_product.rb | 5 +++++ ...remove_pieces_missing_from_production_product.rb | 5 +++++ spec/factories/productions.rb | 5 +---- spec/models/production_spec.rb | 5 +---- 13 files changed, 39 insertions(+), 25 deletions(-) create mode 100644 db/migrate/20240903193442_remove_columns_from_production.rb create mode 100644 db/migrate/20240903193443_add_delivery_date_to_production_product.rb create mode 100644 db/migrate/20240903193444_remove_pieces_missing_from_production_product.rb diff --git a/app/controllers/productions_controller.rb b/app/controllers/productions_controller.rb index a9402d0f..5a4d2b38 100644 --- a/app/controllers/productions_controller.rb +++ b/app/controllers/productions_controller.rb @@ -79,7 +79,8 @@ def production_params params.require(:production).permit( :cut_date, :tailor_id, :service_order_number, :expected_delivery_date, :confirmed, :paid, :consider, :observation, - production_products_attributes: [:id, :product_id, :quantity, :pieces_delivered, :pieces_missing, :_destroy] + production_products_attributes: [:id, :product_id, :quantity, :pieces_delivered, :delivery_date, + :_destroy] ) end end \ No newline at end of file diff --git a/app/models/production.rb b/app/models/production.rb index c3f0c72e..26226bb5 100644 --- a/app/models/production.rb +++ b/app/models/production.rb @@ -6,13 +6,11 @@ # confirmed :boolean # consider :boolean default(FALSE) # cut_date :datetime -# deliver_date :datetime -# delivery_date :date # expected_delivery_date :date # observation :text # paid :boolean -# pieces_delivered :integer # pieces_missing :integer +# service_order_number :string # created_at :datetime not null # updated_at :datetime not null # account_id :integer @@ -22,7 +20,6 @@ # # index_productions_on_account_id (account_id) # index_productions_on_cut_date (cut_date) -# index_productions_on_delivery_date (delivery_date) # index_productions_on_expected_delivery_date (expected_delivery_date) # index_productions_on_tailor_id (tailor_id) # @@ -43,7 +40,7 @@ class Production < ApplicationRecord validates :cut_date, presence: true validates :tailor, presence: true validates :account, presence: true - validates :service_order_number, presence: true, uniqueness: { scope: :account_id } + validates :service_order_number, uniqueness: { scope: :account_id } # Add a method to calculate total pieces delivered def total_pieces_delivered diff --git a/app/models/production_product.rb b/app/models/production_product.rb index 81045b90..e8bb72f3 100644 --- a/app/models/production_product.rb +++ b/app/models/production_product.rb @@ -3,8 +3,8 @@ # Table name: production_products # # id :bigint not null, primary key +# delivery_date :date # pieces_delivered :integer -# pieces_missing :integer # quantity :integer # created_at :datetime not null # updated_at :datetime not null @@ -27,7 +27,6 @@ class ProductionProduct < ApplicationRecord validates :quantity, presence: true, numericality: { greater_than_or_equal_to: 0 } validates :pieces_delivered, numericality: { greater_than_or_equal_to: 0 }, allow_nil: true - validates :pieces_missing, numericality: { greater_than_or_equal_to: 0 }, allow_nil: true before_save :set_default_pieces_delivered diff --git a/app/views/productions/edit.html.erb b/app/views/productions/edit.html.erb index efe3870c..fde7d0a9 100644 --- a/app/views/productions/edit.html.erb +++ b/app/views/productions/edit.html.erb @@ -37,7 +37,6 @@ <%= form.date_field :expected_delivery_date, class: 'form-control' %>
  • -
    <%= form.label :consider, model_class.human_attribute_name(:consider), class: 'form-check-label' %> @@ -63,22 +62,26 @@
    -

    Products

    +

    <%= t('productions.edit.products') %>

    <%= form.fields_for :production_products do |pp_form| %>
    -
    +
    <%= pp_form.label :product_id, Product.model_name.human, class: 'form-label' %> <%= pp_form.collection_select :product_id, Product.all, :id, :name, { include_blank: true }, { class: 'form-control', required: true } %>
    -
    +
    <%= pp_form.label :quantity, ProductionProduct.human_attribute_name(:quantity), class: 'form-label' %> <%= pp_form.number_field :quantity, class: 'form-control', readonly: true %>
    -
    +
    <%= pp_form.label :pieces_delivered, ProductionProduct.human_attribute_name(:pieces_delivered), class: 'form-label' %> <%= pp_form.number_field :pieces_delivered, class: 'form-control' %>
    +
    + <%= pp_form.label :delivery_date, ProductionProduct.human_attribute_name(:delivery_date), class: 'form-label' %> + <%= pp_form.date_field :delivery_date, class: 'form-control' %> +
    <% end %>
    diff --git a/app/views/productions/index.html.erb b/app/views/productions/index.html.erb index 39bbcd68..9578edae 100644 --- a/app/views/productions/index.html.erb +++ b/app/views/productions/index.html.erb @@ -19,7 +19,7 @@
    - + @@ -37,7 +37,7 @@ - + + @@ -67,6 +68,7 @@ + <% end %> @@ -76,6 +78,7 @@ +
    <%= model_class.human_attribute_name(:tailor) %> <%= t 'productions.index.product_summary' %> <%= model_class.human_attribute_name(:cut_date) %> <%= model_class.human_attribute_name(:deliver_date) %> <%= model_class.human_attribute_name(:consider) %><%= model_class.human_attribute_name(:confirmed) %> <%= t 'helpers.actions' %>
    <%= production.tailor&.name || t('productions.index.no_tailor') %> - <% production_products_summary = production.production_products.map { |pp| "#{pp.product.name}: #{pp.quantity}" }.join(', ') %> - <%= production_products_summary.presence || t('productions.index.no_products') %> +
      + <% production.production_products.each do |pp| %> +
    • <%= "#{pp.product.name}: #{pp.quantity}" %>
    • + <% end %> +
    <%= I18n.l(production.cut_date, format: :long) if production.cut_date %> <%= I18n.l(production.deliver_date, format: :long) if production.deliver_date %> <%= production.consider ? 'Sim' : 'Não' %><%= production.confirmed ? 'Verified' : 'Not Verified' %> <%= link_to icon('fas fa-pencil-alt'), edit_production_path(production), title: t('edit'), class: 'btn btn-primary', data: { toggle: 'tooltip', turbo: false } %> <%= link_to icon('fas fa-eye'), production, title: t('show'), class: 'btn btn-info', data: { toggle: 'tooltip', turbo: false } %> @@ -48,4 +53,4 @@ - + \ No newline at end of file diff --git a/app/views/productions/new.html.erb b/app/views/productions/new.html.erb index caafd5b4..c8ec4b5c 100644 --- a/app/views/productions/new.html.erb +++ b/app/views/productions/new.html.erb @@ -1,62 +1,70 @@ -

    <%= t('productions.new.title') %>

    +

    +<%- model_class = Production -%> +

    <%= t('.title', :default => t("helpers.titles.new", :model => model_class.model_name.human.titleize)) %>

    -<%= form_with(model: [@account, @production], local: true, html: { class: 'needs-validation', novalidate: '' }) do |form| %> - <% if @production.errors.any? %> -
    -

    <%= pluralize(@production.errors.count, "error") %> prohibited this production from being saved:

    -
      - <% @production.errors.full_messages.each do |message| %> -
    • <%= message %>
    • - <% end %> -
    -
    - <% end %> +
    +
    +
    +
    +

    <%= t('.new_production') %>

    +
    +
    + <%= form_with(model: @production, local: true) do |form| %> +
    +
    + <%= form.label :tailor_id, model_class.human_attribute_name(:tailor), class: 'form-label' %> + <%= form.collection_select :tailor_id, @tailors, :id, :name, { prompt: 'Select a tailor' }, { class: 'form-control select2' } %> +
    +
    + <%= form.label :cut_date, model_class.human_attribute_name(:cut_date), class: 'form-label' %> + <%= form.date_field :cut_date, class: 'form-control' %> +
    +
    + <%= form.label :expected_delivery_date, model_class.human_attribute_name(:expected_delivery_date), class: 'form-label' %> + <%= form.date_field :expected_delivery_date, class: 'form-control' %> +
    +
    - -
    -
    - <%= form.label :tailor_id, Production.human_attribute_name(:tailor), class: 'form-label' %> - <%= form.collection_select :tailor_id, @tailors, :id, :name, { include_blank: true }, { class: 'form-control', required: true } %> -
    -
    +
    +
    + <%= form.label :consider, model_class.human_attribute_name(:consider), class: 'form-check-label' %> + <%= form.check_box :consider, class: 'form-check-input' %> +
    +
    - -
    -
    - <%= form.label :cut_date, Production.human_attribute_name(:cut_date), class: 'form-label' %> - <%= form.date_field :cut_date, class: 'form-control', required: true %> -
    -
    - <%= form.label :delivery_date, Production.human_attribute_name(:delivery_date), class: 'form-label' %> - <%= form.date_field :delivery_date, class: 'form-control' %> -
    -
    +
    +
    + <%= form.label :observation, model_class.human_attribute_name(:observation), class: 'form-label' %> + <%= form.text_area :observation, class: 'form-control' %> +
    +
    + +

    <%= t('.products') %>

    +
    + <%= form.fields_for :production_products do |pp_form| %> + <%= render 'production_product_fields', f: pp_form %> + <% end %> + +
    - -
    -

    <%= t('productions.products') %>

    -
    - <%= form.fields_for :production_products do |pp_form| %> - <%= render 'production_product_fields', f: pp_form %> - <% end %> + <%= form.submit t('helpers.submit.create'), class: 'btn btn-primary mt-3' %> + <%= link_to t('helpers.links.cancel'), productions_path, class: 'btn btn-secondary mt-3' %> + <% end %> +
    - <%= link_to_add_association t('actions.add_product'), form, :production_products, - class: 'btn btn-primary', - data: { - association_insertion_node: '#production-products', - association_insertion_method: 'append' - } %>
    +
    -
    - <%= form.check_box :consider, class: 'form-check-input' %> - <%= form.label :consider, Production.human_attribute_name(:consider), class: 'form-check-label' %> -
    +<% content_for :page_scripts do %> + <% end %> \ No newline at end of file diff --git a/app/views/productions/show.html.erb b/app/views/productions/show.html.erb index 9bcbcf46..eeca65cb 100644 --- a/app/views/productions/show.html.erb +++ b/app/views/productions/show.html.erb @@ -30,7 +30,7 @@
      <% @production.production_products.each do |prod_product| %>
    • - Produto: <%= prod_product.product.name %>, Quantity: <%= prod_product.quantity %> + Produto: <%= prod_product.product&.name || 'No product assigned' %>, Quantity: <%= prod_product.quantity %>, Pieces Delivered: <%= prod_product.pieces_delivered %>, Pieces Missing: <%= prod_product.pieces_missing %>
    • <% end %>
    @@ -44,19 +44,60 @@
    <%= model_class.human_attribute_name(:cut_date) %>:
    <%= @production.cut_date %>
    -
    <%= model_class.human_attribute_name(:deliver_date)%>:
    -
    <%= @production.deliver_date %>
    +
    <%= model_class.human_attribute_name(:expected_delivery_date) %>:
    +
    <%= @production.expected_delivery_date %>
    <%= model_class.human_attribute_name(:consider)%>:
    <%= @production.consider ? 'Sim' : 'Não' %>
    +
    +
    +

    Detalhes dos Produtos

    +
    +
    +
    + + + + + + + + + + + <% @production.production_products.each do |pp| %> + + + + + + + <% end %> + + + + + + + + +
    ProdutoQuantidadePeças EntreguesPeças Faltantes
    <%= pp.product&.name || 'Nenhum produto atribuído' %><%= pp.quantity %><%= pp.pieces_delivered || 0 %><%= pp.quantity - (pp.pieces_delivered || 0) %>
    Totais<%= @production.total_pieces_delivered %><%= @production.total_pieces_missing %>
    +
    +
    +
    -<%= link_to t('.back', :default => t("helpers.links.back")), productions_path, :class => 'btn btn-secondary' %> -<%= link_to t('.edit', :default => t("helpers.links.edit")), edit_production_path(@production), :class => 'btn btn-warning' %> -<%= link_to t('.destroy', :default => t("helpers.links.destroy")), production_path(@production), :method => 'delete', - :data => { :confirm => t('.confirm', :default => t("helpers.links.confirm", :default => 'Are you sure?')) }, - :class => 'btn btn-danger' %> + +
    + <%= link_to t('.back', :default => t("helpers.links.back")), productions_path, :class => 'btn btn-secondary' %> + <%= link_to t('.edit', :default => t("helpers.links.edit")), edit_production_path(@production), :class => 'btn btn-warning' %> + <%= link_to t('.destroy', :default => t("helpers.links.destroy")), production_path(@production), :method => 'delete', + :data => { :confirm => t('.confirm', :default => t("helpers.links.confirm", :default => 'Are you sure?')) }, + :class => 'btn btn-danger' %> +
    <% content_for(:page_title, 'Show Production') %> + + diff --git a/app/views/shared/_navbar.html.erb b/app/views/shared/_navbar.html.erb index 7c3b40a6..9c515bf7 100644 --- a/app/views/shared/_navbar.html.erb +++ b/app/views/shared/_navbar.html.erb @@ -1,36 +1,37 @@ <% if user_signed_in? %> <% end %> diff --git a/config/locales/en.yml b/config/locales/en.yml index 00113493..333ccb37 100644 --- a/config/locales/en.yml +++ b/config/locales/en.yml @@ -45,3 +45,66 @@ en: formats: default: "%Y/%m/%d %H:%M" time: "%H:%M:%S" + + productions: + verify: + title: "Verify Production" + production_details: "Production Details" + tailor: "Tailor" + cut_date: "Cut Date" + delivery_date: "Delivery Date" + expected_delivery_date: "Expected Delivery Date" + products: "Products" + product_name: "Product Name" + quantity: "Quantity" + pieces_delivered: "Pieces Delivered" + pieces_missing: "Pieces Missing" + additional_info: "Additional Information" + observation: "Observation" + confirmed: "Confirmed" + paid: "Paid" + consider: "Consider" + finalize_production: "Finalize Production" + back: "Back to Edit" + update: + production_updated: "Production was successfully updated." + activerecord: + models: + production: "Production" + production_product: "Production Product" + attributes: + production: + number: "Number" + tailor: "Tailor" + cut_date: "Cut Date" + delivery_date: "Delivery Date" + expected_delivery_date: "Expected Delivery Date" + consider: "Consider" + confirmed: "Confirmed" + paid: "Paid" + observation: "Observation" + pieces_delivered: "Pieces Delivered" + pieces_missing: "Pieces Missing" + production_product: + product: "Product" + quantity: "Quantity" + pieces_delivered: "Pieces Delivered" + pieces_missing: "Pieces Missing" + expected_delivery_date: "Expected Delivery Date" + errors: + models: + production: + attributes: + tailor: + blank: "must be selected" + helpers: + submit: + update: "Update" + links: + back: "Back" + edit: "Edit" + destroy: "Destroy" + cancel: "Cancel" + confirm: "Are you sure?" + actions: + remove: "Remove" diff --git a/config/routes.rb b/config/routes.rb index ce976bcd..2210d9e4 100644 --- a/config/routes.rb +++ b/config/routes.rb @@ -1,13 +1,18 @@ # frozen_string_literal: true -#require 'sidekiq/web' - Rails.application.routes.draw do - resources :productions + # mount Sidekiq::Web => '/sidekiq' + mount GoodJob::Engine => 'good_job' + + resources :productions do + member do + get :verify + patch :verify, to: 'productions#update' + end + end + resources :tailors get 'dashboards/others_status' - #mount Sidekiq::Web => '/sidekiq' - mount GoodJob::Engine => 'good_job' resources :bling_order_items @@ -27,7 +32,7 @@ resources :shein_bling_order_items, only: :index resources :shein_dashboards - resources :shein_orders do + resources :shein_orders do collection do get :upload post :import @@ -70,11 +75,16 @@ delete :destroy_from_index end end - resources :bling_data, only: [:index, :show] + resources :bling_data, only: %i[index show] get 'products_defer', to: 'products#index_defer' get 'products_tags_defer', to: 'products#tags_index_defer' get '/products/:id/duplicate', to: 'products#duplicate', as: 'meeting_duplicate' get '/products/:id/update_active', to: 'products#update_active', as: 'update_product_active' + resources :items, only: [] do + member do + patch :update_status + end + end resources :customers do collection do @@ -121,4 +131,12 @@ end end root to: 'home#index' + + resources :accounts do + resources :productions do + member do + get :verify + end + end + end end diff --git a/db/migrate/20240901150326_add_pieces_delivered_and_pieces_missing_to_production_products.rb b/db/migrate/20240901150326_add_pieces_delivered_and_pieces_missing_to_production_products.rb new file mode 100644 index 00000000..155b0f3b --- /dev/null +++ b/db/migrate/20240901150326_add_pieces_delivered_and_pieces_missing_to_production_products.rb @@ -0,0 +1,6 @@ +class AddPiecesDeliveredAndPiecesMissingToProductionProducts < ActiveRecord::Migration[7.0] + def change + add_column :production_products, :pieces_delivered, :integer + add_column :production_products, :pieces_missing, :integer + end +end diff --git a/db/migrate/20240901200830_remove_number_from_productions.rb b/db/migrate/20240901200830_remove_number_from_productions.rb new file mode 100644 index 00000000..bddde8ae --- /dev/null +++ b/db/migrate/20240901200830_remove_number_from_productions.rb @@ -0,0 +1,5 @@ +class RemoveNumberFromProductions < ActiveRecord::Migration[7.0] + def change + remove_column :productions, :number, :integer + end +end From 789b227a3a1b061a89cd999420eb7910f57af6c9 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Mon, 2 Sep 2024 13:10:54 -0300 Subject: [PATCH 27/45] update the show view --- app/views/productions/show.html.erb | 17 ++--------------- 1 file changed, 2 insertions(+), 15 deletions(-) diff --git a/app/views/productions/show.html.erb b/app/views/productions/show.html.erb index eeca65cb..d74856d2 100644 --- a/app/views/productions/show.html.erb +++ b/app/views/productions/show.html.erb @@ -22,20 +22,6 @@ <% end %> -
    -
    -

    Produtos da Produção

    -
    -
    -
      - <% @production.production_products.each do |prod_product| %> -
    • - Produto: <%= prod_product.product&.name || 'No product assigned' %>, Quantity: <%= prod_product.quantity %>, Pieces Delivered: <%= prod_product.pieces_delivered %>, Pieces Missing: <%= prod_product.pieces_missing %> -
    • - <% end %> -
    -
    -

    Dados Produção

    @@ -78,7 +64,8 @@
    TotaisTotais<%= @production.production_products.sum(&:quantity) %> <%= @production.total_pieces_delivered %> <%= @production.total_pieces_missing %>
    <%= model_class.human_attribute_name(:tailor) %> <%= t 'productions.index.product_summary' %> <%= model_class.human_attribute_name(:cut_date) %><%= model_class.human_attribute_name(:deliver_date) %><%= model_class.human_attribute_name(:expected_delivery_date) %> <%= model_class.human_attribute_name(:consider) %> <%= model_class.human_attribute_name(:confirmed) %> <%= t 'helpers.actions' %> <%= I18n.l(production.cut_date, format: :long) if production.cut_date %><%= I18n.l(production.deliver_date, format: :long) if production.deliver_date %><%= I18n.l(production.expected_delivery_date, format: :long) if production.expected_delivery_date %> <%= production.consider ? 'Sim' : 'Não' %> <%= production.confirmed ? 'Verified' : 'Not Verified' %> diff --git a/app/views/productions/missing_pieces.html.erb b/app/views/productions/missing_pieces.html.erb index c21f709d..bb16360b 100644 --- a/app/views/productions/missing_pieces.html.erb +++ b/app/views/productions/missing_pieces.html.erb @@ -24,7 +24,7 @@

    <%= Production.human_attribute_name(:tailor) %>: <%= production.tailor.name %>

    -

    <%= Production.human_attribute_name(:cut_date) %>: <%= l(production.cut_date) if production.cut_date %>

    +

    <%= Production.human_attribute_name(:cut_date) %>: <%= pt_only_date_format(production.cut_date) if production.cut_date %>

    <%= Production.human_attribute_name(:expected_delivery_date) %>: <%= l(production.expected_delivery_date) if production.expected_delivery_date %>

    <%= t('.missing_pieces') %>:
      diff --git a/app/views/productions/show.html.erb b/app/views/productions/show.html.erb index 34e70bb0..b6cdf94c 100644 --- a/app/views/productions/show.html.erb +++ b/app/views/productions/show.html.erb @@ -58,6 +58,7 @@
    Quantidade Peças Entregues Peças FaltantesData de Entrega
    <%= pp.quantity %> <%= pp.pieces_delivered || 0 %> <%= pp.quantity - (pp.pieces_delivered || 0) %><%= pt_only_date_format(pp.delivery_date) || 'Não informado' %>
    <%= @production.production_products.sum(&:quantity) %> <%= @production.total_pieces_delivered %> <%= @production.total_pieces_missing %>
    @@ -88,7 +91,6 @@
    <%= link_to t('.back', :default => t("helpers.links.back")), productions_path, :class => 'btn btn-secondary' %> <%= link_to t('.edit', :default => t("helpers.links.edit")), edit_production_path(@production), :class => 'btn btn-warning' %> - <%= link_to t('productions.missing_pieces.title'), missing_pieces_productions_path, class: 'btn btn-info' %> <%= link_to t('.destroy', :default => t("helpers.links.destroy")), production_path(@production), :method => 'delete', :data => { :confirm => t('.confirm', :default => t("helpers.links.confirm", :default => 'Are you sure?')) }, :class => 'btn btn-danger' %> diff --git a/config/locales/pt-BR.models.productions.yml b/config/locales/pt-BR.models.productions.yml index f59c3173..549615ee 100644 --- a/config/locales/pt-BR.models.productions.yml +++ b/config/locales/pt-BR.models.productions.yml @@ -21,6 +21,7 @@ pt-BR: quantity: "Quantidade" pieces_delivered: "Peças Entregues" pieces_missing: "Peças Faltando" + delivery_date: "Data de Entrega" productions: index: title: "Produções" diff --git a/db/migrate/20240903193442_remove_columns_from_production.rb b/db/migrate/20240903193442_remove_columns_from_production.rb new file mode 100644 index 00000000..4e539964 --- /dev/null +++ b/db/migrate/20240903193442_remove_columns_from_production.rb @@ -0,0 +1,7 @@ +class RemoveColumnsFromProduction < ActiveRecord::Migration[7.0] + def change + remove_column :productions, :delivery_date, :datetime + remove_column :productions, :deliver_date, :datetime + remove_column :productions, :pieces_delivered, :integer + end +end diff --git a/db/migrate/20240903193443_add_delivery_date_to_production_product.rb b/db/migrate/20240903193443_add_delivery_date_to_production_product.rb new file mode 100644 index 00000000..e994515c --- /dev/null +++ b/db/migrate/20240903193443_add_delivery_date_to_production_product.rb @@ -0,0 +1,5 @@ +class AddDeliveryDateToProductionProduct < ActiveRecord::Migration[7.0] + def change + add_column :production_products, :delivery_date, :date + end +end diff --git a/db/migrate/20240903193444_remove_pieces_missing_from_production_product.rb b/db/migrate/20240903193444_remove_pieces_missing_from_production_product.rb new file mode 100644 index 00000000..dc329492 --- /dev/null +++ b/db/migrate/20240903193444_remove_pieces_missing_from_production_product.rb @@ -0,0 +1,5 @@ +class RemovePiecesMissingFromProductionProduct < ActiveRecord::Migration[7.0] + def change + remove_column :production_products, :pieces_missing, :integer + end +end diff --git a/spec/factories/productions.rb b/spec/factories/productions.rb index 32e5f320..ae404ce7 100644 --- a/spec/factories/productions.rb +++ b/spec/factories/productions.rb @@ -6,13 +6,11 @@ # confirmed :boolean # consider :boolean default(FALSE) # cut_date :datetime -# deliver_date :datetime -# delivery_date :date # expected_delivery_date :date # observation :text # paid :boolean -# pieces_delivered :integer # pieces_missing :integer +# service_order_number :string # created_at :datetime not null # updated_at :datetime not null # account_id :integer @@ -22,7 +20,6 @@ # # index_productions_on_account_id (account_id) # index_productions_on_cut_date (cut_date) -# index_productions_on_delivery_date (delivery_date) # index_productions_on_expected_delivery_date (expected_delivery_date) # index_productions_on_tailor_id (tailor_id) # diff --git a/spec/models/production_spec.rb b/spec/models/production_spec.rb index 85129a3e..91c90802 100644 --- a/spec/models/production_spec.rb +++ b/spec/models/production_spec.rb @@ -6,13 +6,11 @@ # confirmed :boolean # consider :boolean default(FALSE) # cut_date :datetime -# deliver_date :datetime -# delivery_date :date # expected_delivery_date :date # observation :text # paid :boolean -# pieces_delivered :integer # pieces_missing :integer +# service_order_number :string # created_at :datetime not null # updated_at :datetime not null # account_id :integer @@ -22,7 +20,6 @@ # # index_productions_on_account_id (account_id) # index_productions_on_cut_date (cut_date) -# index_productions_on_delivery_date (delivery_date) # index_productions_on_expected_delivery_date (expected_delivery_date) # index_productions_on_tailor_id (tailor_id) # From 8484f18ad2c2aa574217c88d7a9b1724d5a87c4d Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Tue, 3 Sep 2024 20:21:03 -0300 Subject: [PATCH 39/45] update schema --- db/schema.rb | 30 +++++++++++------------------- 1 file changed, 11 insertions(+), 19 deletions(-) diff --git a/db/schema.rb b/db/schema.rb index abe68994..ce18042f 100644 --- a/db/schema.rb +++ b/db/schema.rb @@ -10,7 +10,7 @@ # # It's strongly recommended that you check this file into your version control system. -ActiveRecord::Schema[7.0].define(version: 2024_09_01_200830) do +ActiveRecord::Schema[7.0].define(version: 2024_09_03_193444) do # These are extensions that must be enabled in order to support this database enable_extension "pgcrypto" enable_extension "plpgsql" @@ -36,7 +36,7 @@ t.string "record_type", null: false t.bigint "record_id", null: false t.bigint "blob_id", null: false - t.datetime "created_at", null: false + t.datetime "created_at", precision: nil, null: false t.index ["blob_id"], name: "index_active_storage_attachments_on_blob_id" t.index ["record_type", "record_id", "name", "blob_id"], name: "index_active_storage_attachments_uniqueness", unique: true end @@ -48,7 +48,7 @@ t.text "metadata" t.bigint "byte_size", null: false t.string "checksum" - t.datetime "created_at", null: false + t.datetime "created_at", precision: nil, null: false t.string "service_name", null: false t.index ["key"], name: "index_active_storage_blobs_on_key", unique: true end @@ -91,16 +91,12 @@ t.string "marketplace_code_id" t.integer "bling_id" t.bigint "account_id" - t.jsonb "items" t.decimal "value" + t.jsonb "items" t.date "collected_alteration_date" t.string "original_situation_id" - t.string "city", limit: 10485760 - t.string "state", limit: 10485760 t.index ["account_id"], name: "index_bling_order_items_on_account_id" - t.index ["bling_order_id"], name: "bling_order_id_index_on_bling_order_items" t.index ["bling_order_id"], name: "index_bling_order_items_on_bling_order_id", unique: true - t.index ["situation_id", "store_id"], name: "situation_id_index_on_bling_order_items" end create_table "categories", force: :cascade do |t| @@ -257,7 +253,6 @@ t.bigint "bling_order_item_id" t.datetime "created_at", null: false t.datetime "updated_at", null: false - t.boolean "pending", default: false end create_table "localizations", force: :cascade do |t| @@ -283,7 +278,7 @@ t.string "post_code" t.string "post_type" t.float "value" - t.datetime "send_date" + t.datetime "send_date", precision: nil t.datetime "created_at", null: false t.datetime "updated_at", null: false end @@ -295,29 +290,26 @@ t.datetime "created_at", null: false t.datetime "updated_at", null: false t.integer "pieces_delivered" - t.integer "pieces_missing" + t.date "delivery_date" t.index ["product_id"], name: "index_production_products_on_product_id" t.index ["production_id"], name: "index_production_products_on_production_id" end create_table "productions", force: :cascade do |t| t.datetime "cut_date" - t.datetime "deliver_date" t.datetime "created_at", null: false t.datetime "updated_at", null: false t.integer "account_id" t.bigint "tailor_id" t.boolean "consider", default: false - t.date "delivery_date" - t.integer "pieces_delivered" t.integer "pieces_missing" t.date "expected_delivery_date" t.boolean "confirmed" t.boolean "paid" t.text "observation" + t.string "service_order_number" t.index ["account_id"], name: "index_productions_on_account_id" t.index ["cut_date"], name: "index_productions_on_cut_date" - t.index ["delivery_date"], name: "index_productions_on_delivery_date" t.index ["expected_delivery_date"], name: "index_productions_on_expected_delivery_date" t.index ["tailor_id"], name: "index_productions_on_tailor_id" end @@ -415,7 +407,7 @@ create_table "simplo_clients", force: :cascade do |t| t.string "name" t.integer "age" - t.datetime "order_date" + t.datetime "order_date", precision: nil t.datetime "created_at", null: false t.datetime "updated_at", null: false end @@ -429,7 +421,7 @@ t.float "valor_total" t.float "peso" t.float "desconto" - t.datetime "data_pedido" + t.datetime "data_pedido", precision: nil t.datetime "created_at", null: false t.datetime "updated_at", null: false t.string "order_id" @@ -526,8 +518,8 @@ t.string "email", default: "", null: false t.string "encrypted_password", default: "", null: false t.string "reset_password_token" - t.datetime "reset_password_sent_at" - t.datetime "remember_created_at" + t.datetime "reset_password_sent_at", precision: nil + t.datetime "remember_created_at", precision: nil t.datetime "created_at", null: false t.datetime "updated_at", null: false t.string "first_name" From d8e58d5b92d8272c2add63495e640f7ae9ea59ab Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Tue, 3 Sep 2024 20:24:50 -0300 Subject: [PATCH 40/45] update annotate --- app/models/bling_order_item.rb | 4 ---- spec/factories/bling_order_items.rb | 4 ---- spec/models/bling_order_item_spec.rb | 4 ---- 3 files changed, 12 deletions(-) diff --git a/app/models/bling_order_item.rb b/app/models/bling_order_item.rb index ae83d1c8..b4635055 100644 --- a/app/models/bling_order_item.rb +++ b/app/models/bling_order_item.rb @@ -5,7 +5,6 @@ # id :bigint not null, primary key # aliquotaIPI :decimal(, ) # alteration_date :datetime -# city :string(10485760) # codigo :string # collected_alteration_date :date # date :datetime @@ -14,7 +13,6 @@ # descricaoDetalhada :text # items :jsonb # quantidade :integer -# state :string(10485760) # unidade :string # valor :decimal(, ) # value :decimal(, ) @@ -30,10 +28,8 @@ # # Indexes # -# bling_order_id_index_on_bling_order_items (bling_order_id) # index_bling_order_items_on_account_id (account_id) # index_bling_order_items_on_bling_order_id (bling_order_id) UNIQUE -# situation_id_index_on_bling_order_items (situation_id,store_id) # class BlingOrderItem < ApplicationRecord # TODO, refactor me separating the tables diff --git a/spec/factories/bling_order_items.rb b/spec/factories/bling_order_items.rb index bce90489..f98ae05a 100644 --- a/spec/factories/bling_order_items.rb +++ b/spec/factories/bling_order_items.rb @@ -5,7 +5,6 @@ # id :bigint not null, primary key # aliquotaIPI :decimal(, ) # alteration_date :datetime -# city :string(10485760) # codigo :string # collected_alteration_date :date # date :datetime @@ -14,7 +13,6 @@ # descricaoDetalhada :text # items :jsonb # quantidade :integer -# state :string(10485760) # unidade :string # valor :decimal(, ) # value :decimal(, ) @@ -30,10 +28,8 @@ # # Indexes # -# bling_order_id_index_on_bling_order_items (bling_order_id) # index_bling_order_items_on_account_id (account_id) # index_bling_order_items_on_bling_order_id (bling_order_id) UNIQUE -# situation_id_index_on_bling_order_items (situation_id,store_id) # FactoryBot.define do factory :bling_order_item do diff --git a/spec/models/bling_order_item_spec.rb b/spec/models/bling_order_item_spec.rb index da17301a..2c6247ac 100644 --- a/spec/models/bling_order_item_spec.rb +++ b/spec/models/bling_order_item_spec.rb @@ -5,7 +5,6 @@ # id :bigint not null, primary key # aliquotaIPI :decimal(, ) # alteration_date :datetime -# city :string(10485760) # codigo :string # collected_alteration_date :date # date :datetime @@ -14,7 +13,6 @@ # descricaoDetalhada :text # items :jsonb # quantidade :integer -# state :string(10485760) # unidade :string # valor :decimal(, ) # value :decimal(, ) @@ -30,10 +28,8 @@ # # Indexes # -# bling_order_id_index_on_bling_order_items (bling_order_id) # index_bling_order_items_on_account_id (account_id) # index_bling_order_items_on_bling_order_id (bling_order_id) UNIQUE -# situation_id_index_on_bling_order_items (situation_id,store_id) # require 'rails_helper' From 1ffee87af4722d786c5bb4aad5ad1a9e2e902d03 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Wed, 4 Sep 2024 17:24:59 -0300 Subject: [PATCH 41/45] fix the pending orders --- app/controllers/orders_control_controller.rb | 14 ++--- .../show_pending_orders.html.erb | 57 +++++++++++++------ 2 files changed, 47 insertions(+), 24 deletions(-) diff --git a/app/controllers/orders_control_controller.rb b/app/controllers/orders_control_controller.rb index bcc4723a..6339559a 100644 --- a/app/controllers/orders_control_controller.rb +++ b/app/controllers/orders_control_controller.rb @@ -24,24 +24,24 @@ def show_orders_products_stock def show_pending_orders situation_id = params[:situation_id] store_id = params[:store_id] - + if situation_id.present? cleaned_situation_ids = situation_id.split(',').map(&:to_i) else cleaned_situation_ids = BlingOrderItem::Status::PENDING end - + pending_items = Item.includes(:bling_order_item).where(bling_order_items: { situation_id: cleaned_situation_ids }) - + if store_id.present? - @pending_order_items = pending_items.where(bling_order_items: { store_id: store_id }) + @all_items = pending_items.where(bling_order_items: { store_id: store_id }) else - @pending_order_items = pending_items + @all_items = pending_items end - + respond_to do |format| format.html # show.html.erb - format.csv { send_data generate_csv(@pending_order_items), filename: "pending-orders-#{Date.today}.csv" } + format.csv { send_data generate_csv(@all_items), filename: "pending-orders-#{Date.today}.csv" } end end diff --git a/app/views/orders_control/show_pending_orders.html.erb b/app/views/orders_control/show_pending_orders.html.erb index d5b89802..d52028bd 100644 --- a/app/views/orders_control/show_pending_orders.html.erb +++ b/app/views/orders_control/show_pending_orders.html.erb @@ -24,27 +24,50 @@ <% @all_items.group_by { |item| item.bling_order_item.store_name }.each do |loja_name, items| %>
    +
    +
    <%= loja_name %>
    +
    -
    <%= loja_name %>
    <% items.group_by(&:sku).each do |codigo, sku_items| %> <% sorted_sku_items = sku_items.sort_by { |item| -item.quantity.to_i } %> -
    - - Código <%= codigo %> - <%= sorted_sku_items.sum { |item| item.quantity.to_i } %> unidades - - <% sorted_sku_items.each do |item| %> -
    -
    - Pedido: <%= item.bling_order_item.bling_order_id %>, Quantidade: <%= item.quantity %> unidades
    - Ver Pedido no Bling -

    Status: <%= item.pending? ? 'Pendente' : 'Não Pendente' %>

    - <% if item.bling_order_item.situation_id == BlingOrderItem::Status::PENDING %> - <%= link_to 'Marcar como Pendente', update_status_item_path(item, status: 'pendente'), method: :patch, class: 'btn btn-success' %> - <%= link_to 'Marcar como Não Pendente', update_status_item_path(item, status: 'nao_pendente'), method: :patch, class: 'btn btn-danger' %> - <% end %> -
    +
    + +
    +
    + + + + + + + + + + + <% sorted_sku_items.each do |item| %> + + + + + + + <% end %> + +
    PedidoQuantidadeStatusAções
    + <%= item.bling_order_item.bling_order_id %> + + Ver no Bling + + <%= item.quantity %> unidades<%= item.pending? ? 'Pendente' : 'Não Pendente' %> + <% if item.bling_order_item.situation_id == BlingOrderItem::Status::PENDING %> + <%= link_to 'Marcar Pendente', update_status_item_path(item, status: 'pendente'), method: :patch, class: 'btn btn-sm btn-success' %> + <%= link_to 'Marcar Não Pendente', update_status_item_path(item, status: 'nao_pendente'), method: :patch, class: 'btn btn-sm btn-danger' %> + <% end %> +
    - <% end %> +
    <% end %>
    From 3b2751a4c8b7c8c3e7ee4e392410c8e23f61c789 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Wed, 4 Sep 2024 17:31:10 -0300 Subject: [PATCH 42/45] fix the sort for quantity --- app/controllers/orders_control_controller.rb | 5 +++++ .../orders_control/show_pending_orders.html.erb | 13 ++++++------- 2 files changed, 11 insertions(+), 7 deletions(-) diff --git a/app/controllers/orders_control_controller.rb b/app/controllers/orders_control_controller.rb index 6339559a..0e9e229b 100644 --- a/app/controllers/orders_control_controller.rb +++ b/app/controllers/orders_control_controller.rb @@ -39,6 +39,11 @@ def show_pending_orders @all_items = pending_items end + # Group items by store and sort by total quantity + @sorted_stores = @all_items.group_by { |item| item.bling_order_item.store_name } + .sort_by { |_, items| -items.sum(&:quantity) } + .to_h + respond_to do |format| format.html # show.html.erb format.csv { send_data generate_csv(@all_items), filename: "pending-orders-#{Date.today}.csv" } diff --git a/app/views/orders_control/show_pending_orders.html.erb b/app/views/orders_control/show_pending_orders.html.erb index d52028bd..5edb8fa0 100644 --- a/app/views/orders_control/show_pending_orders.html.erb +++ b/app/views/orders_control/show_pending_orders.html.erb @@ -20,19 +20,18 @@ <% end %>
    - <% if @all_items.present? %> - <% @all_items.group_by { |item| item.bling_order_item.store_name }.each do |loja_name, items| %> + <% if @sorted_stores.present? %> + <% @sorted_stores.each do |loja_name, items| %>
    -
    <%= loja_name %>
    +
    <%= loja_name %> - Total: <%= items.sum(&:quantity) %> unidades
    - <% items.group_by(&:sku).each do |codigo, sku_items| %> - <% sorted_sku_items = sku_items.sort_by { |item| -item.quantity.to_i } %> + <% items.group_by(&:sku).sort_by { |_, sku_items| -sku_items.sum(&:quantity) }.each do |codigo, sku_items| %>
    @@ -46,7 +45,7 @@ - <% sorted_sku_items.each do |item| %> + <% sku_items.sort_by(&:quantity).reverse.each do |item| %> <%= item.bling_order_item.bling_order_id %> From 1bfe404103899634b41dabab3752d1346a34bcc2 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Thu, 5 Sep 2024 08:01:17 -0300 Subject: [PATCH 43/45] add new field to item and rules --- app/controllers/items_controller.rb | 12 +++++++++++ app/controllers/orders_control_controller.rb | 20 +++++++++++-------- app/models/item.rb | 17 ++++++++++++++++ .../show_pending_orders.html.erb | 20 +++++++++++++++---- .../20240905104750_add_resolved_to_items.rb | 6 ++++++ 5 files changed, 63 insertions(+), 12 deletions(-) create mode 100644 app/controllers/items_controller.rb create mode 100644 db/migrate/20240905104750_add_resolved_to_items.rb diff --git a/app/controllers/items_controller.rb b/app/controllers/items_controller.rb new file mode 100644 index 00000000..33adf96d --- /dev/null +++ b/app/controllers/items_controller.rb @@ -0,0 +1,12 @@ +class ItemsController < ApplicationController + def update_status + @item = Item.find(params[:id]) + case params[:status] + when 'resolved' + @item.resolve! + when 'unresolved' + @item.unresolve! + end + redirect_back(fallback_location: show_pending_orders_path, notice: 'Status atualizado com sucesso.') + end +end \ No newline at end of file diff --git a/app/controllers/orders_control_controller.rb b/app/controllers/orders_control_controller.rb index 0e9e229b..8ec7448b 100644 --- a/app/controllers/orders_control_controller.rb +++ b/app/controllers/orders_control_controller.rb @@ -20,10 +20,10 @@ def show_orders_products_stock .order(custom_id: :desc) end - def show_pending_orders situation_id = params[:situation_id] store_id = params[:store_id] + resolution_status = params[:resolution_status] if situation_id.present? cleaned_situation_ids = situation_id.split(',').map(&:to_i) @@ -31,14 +31,19 @@ def show_pending_orders cleaned_situation_ids = BlingOrderItem::Status::PENDING end - pending_items = Item.includes(:bling_order_item).where(bling_order_items: { situation_id: cleaned_situation_ids }) + items = Item.includes(:bling_order_item).where(bling_order_items: { situation_id: cleaned_situation_ids }) - if store_id.present? - @all_items = pending_items.where(bling_order_items: { store_id: store_id }) - else - @all_items = pending_items + items = items.where(bling_order_items: { store_id: store_id }) if store_id.present? + + case resolution_status + when 'unresolved' + items = items.unresolved + when 'resolved' + items = items.resolved end + @all_items = items + # Group items by store and sort by total quantity @sorted_stores = @all_items.group_by { |item| item.bling_order_item.store_name } .sort_by { |_, items| -items.sum(&:quantity) } @@ -46,11 +51,10 @@ def show_pending_orders respond_to do |format| format.html # show.html.erb - format.csv { send_data generate_csv(@all_items), filename: "pending-orders-#{Date.today}.csv" } + format.csv { send_data generate_csv(@all_items), filename: "orders-#{Date.today}.csv" } end end - def show_orders_business_day @simplo_orders = SimploOrder.where(order_status: %w[2 30 31]).order(order_id: :asc) @calendar = SimploOrder.calendar diff --git a/app/models/item.rb b/app/models/item.rb index 8488c2d0..4cb44085 100644 --- a/app/models/item.rb +++ b/app/models/item.rb @@ -7,7 +7,9 @@ # discount :decimal(, ) # ipi_tax :decimal(, ) # long_description :string +# pending :boolean default(FALSE) # quantity :integer +# resolved :boolean default(FALSE) # sku :string # unity :integer # value :decimal(, ) @@ -17,7 +19,22 @@ # bling_order_item_id :bigint # product_id :bigint # +# Indexes +# +# index_items_on_resolved (resolved) +# class Item < ApplicationRecord belongs_to :account belongs_to :bling_order_item + + scope :unresolved, -> { where(resolved: false) } + scope :resolved, -> { where(resolved: true) } + + def resolve! + update(resolved: true) + end + + def unresolve! + update(resolved: false) + end end diff --git a/app/views/orders_control/show_pending_orders.html.erb b/app/views/orders_control/show_pending_orders.html.erb index 5edb8fa0..ee675c92 100644 --- a/app/views/orders_control/show_pending_orders.html.erb +++ b/app/views/orders_control/show_pending_orders.html.erb @@ -16,7 +16,11 @@ <%= form.label :store_id, 'Filtro por Loja' %> <%= form.select :store_id, BlingOrderItem::STORE_ID_NAME_KEY_VALUE.invert, { include_blank: 'Todas', selected: params[:store_id] }, { class: 'form-control' } %>
    - <%= form.submit 'Filtro', class: 'btn btn-primary' %> +
    + <%= form.label :resolution_status, 'Status de Resolução' %> + <%= form.select :resolution_status, options_for_select([['Todos', ''], ['Não Resolvido', 'unresolved'], ['Resolvido', 'resolved']], params[:resolution_status]), {}, { class: 'form-control' } %> +
    + <%= form.submit 'Filtrar', class: 'btn btn-primary' %> <% end %>
    @@ -54,11 +58,19 @@ <%= item.quantity %> unidades - <%= item.pending? ? 'Pendente' : 'Não Pendente' %> + + <% if item.resolved %> + Resolvido + <%= button_to 'Marcar como Não Resolvido', update_status_item_path(item, status: 'unresolved'), method: :patch, class: 'btn btn-sm btn-warning' %> + <% else %> + Não Resolvido + <%= button_to 'Marcar como Resolvido', update_status_item_path(item, status: 'resolved'), method: :patch, class: 'btn btn-sm btn-success' %> + <% end %> + <% if item.bling_order_item.situation_id == BlingOrderItem::Status::PENDING %> - <%= link_to 'Marcar Pendente', update_status_item_path(item, status: 'pendente'), method: :patch, class: 'btn btn-sm btn-success' %> - <%= link_to 'Marcar Não Pendente', update_status_item_path(item, status: 'nao_pendente'), method: :patch, class: 'btn btn-sm btn-danger' %> + <%= button_to 'Marcar Pendente', update_status_item_path(item, status: 'pendente'), method: :patch, class: 'btn btn-sm btn-success' %> + <%= button_to 'Marcar Não Pendente', update_status_item_path(item, status: 'nao_pendente'), method: :patch, class: 'btn btn-sm btn-danger' %> <% end %> diff --git a/db/migrate/20240905104750_add_resolved_to_items.rb b/db/migrate/20240905104750_add_resolved_to_items.rb new file mode 100644 index 00000000..4d391ea7 --- /dev/null +++ b/db/migrate/20240905104750_add_resolved_to_items.rb @@ -0,0 +1,6 @@ +class AddResolvedToItems < ActiveRecord::Migration[7.0] + def change + add_column :items, :resolved, :boolean, default: false + add_index :items, :resolved + end +end From c3f4f5cbb0b278cae6a162aa97fa6d07ab4514c2 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Thu, 5 Sep 2024 08:07:36 -0300 Subject: [PATCH 44/45] update the view --- app/controllers/orders_control_controller.rb | 18 +-- .../show_pending_orders.html.erb | 151 ++++++++++-------- 2 files changed, 89 insertions(+), 80 deletions(-) diff --git a/app/controllers/orders_control_controller.rb b/app/controllers/orders_control_controller.rb index 8ec7448b..43a0b43e 100644 --- a/app/controllers/orders_control_controller.rb +++ b/app/controllers/orders_control_controller.rb @@ -23,7 +23,7 @@ def show_orders_products_stock def show_pending_orders situation_id = params[:situation_id] store_id = params[:store_id] - resolution_status = params[:resolution_status] + @resolution_status = params[:resolution_status] || 'unresolved' if situation_id.present? cleaned_situation_ids = situation_id.split(',').map(&:to_i) @@ -35,14 +35,14 @@ def show_pending_orders items = items.where(bling_order_items: { store_id: store_id }) if store_id.present? - case resolution_status - when 'unresolved' - items = items.unresolved - when 'resolved' - items = items.resolved - end - - @all_items = items + @all_items = case @resolution_status + when 'unresolved' + items.unresolved + when 'resolved' + items.resolved + else + items + end # Group items by store and sort by total quantity @sorted_stores = @all_items.group_by { |item| item.bling_order_item.store_name } diff --git a/app/views/orders_control/show_pending_orders.html.erb b/app/views/orders_control/show_pending_orders.html.erb index ee675c92..48baeb76 100644 --- a/app/views/orders_control/show_pending_orders.html.erb +++ b/app/views/orders_control/show_pending_orders.html.erb @@ -4,7 +4,7 @@
    -<%= link_to 'Exportar para CSV', show_pending_orders_path(format: :csv, situation_id: params[:situation_id], store_id: params[:store_id]), class: 'btn btn-info' %> +<%= link_to 'Exportar para CSV', show_pending_orders_path(format: :csv, situation_id: params[:situation_id], store_id: params[:store_id], resolution_status: @resolution_status), class: 'btn btn-info mb-3' %>
    <%= form_with(url: show_pending_orders_path, method: :get, local: true) do |form| %> @@ -16,83 +16,92 @@ <%= form.label :store_id, 'Filtro por Loja' %> <%= form.select :store_id, BlingOrderItem::STORE_ID_NAME_KEY_VALUE.invert, { include_blank: 'Todas', selected: params[:store_id] }, { class: 'form-control' } %>
    -
    - <%= form.label :resolution_status, 'Status de Resolução' %> - <%= form.select :resolution_status, options_for_select([['Todos', ''], ['Não Resolvido', 'unresolved'], ['Resolvido', 'resolved']], params[:resolution_status]), {}, { class: 'form-control' } %> -
    <%= form.submit 'Filtrar', class: 'btn btn-primary' %> <% end %> -
    - <% if @sorted_stores.present? %> - <% @sorted_stores.each do |loja_name, items| %> -
    -
    -
    -
    <%= loja_name %> - Total: <%= items.sum(&:quantity) %> unidades
    -
    -
    - <% items.group_by(&:sku).sort_by { |_, sku_items| -sku_items.sum(&:quantity) }.each do |codigo, sku_items| %> -
    - -
    -
    - - - - - - - - - - - <% sku_items.sort_by(&:quantity).reverse.each do |item| %> - - - - - - - <% end %> - -
    PedidoQuantidadeStatusAções
    - <%= item.bling_order_item.bling_order_id %> - - Ver no Bling - - <%= item.quantity %> unidades - <% if item.resolved %> - Resolvido - <%= button_to 'Marcar como Não Resolvido', update_status_item_path(item, status: 'unresolved'), method: :patch, class: 'btn btn-sm btn-warning' %> - <% else %> - Não Resolvido - <%= button_to 'Marcar como Resolvido', update_status_item_path(item, status: 'resolved'), method: :patch, class: 'btn btn-sm btn-success' %> - <% end %> - - <% if item.bling_order_item.situation_id == BlingOrderItem::Status::PENDING %> - <%= button_to 'Marcar Pendente', update_status_item_path(item, status: 'pendente'), method: :patch, class: 'btn btn-sm btn-success' %> - <%= button_to 'Marcar Não Pendente', update_status_item_path(item, status: 'nao_pendente'), method: :patch, class: 'btn btn-sm btn-danger' %> - <% end %> -
    + + +
    +
    +
    + <% if @sorted_stores.present? %> + <% @sorted_stores.each do |loja_name, items| %> +
    +
    +
    +
    <%= loja_name %> - Total: <%= items.sum(&:quantity) %> unidades
    +
    +
    + <% items.group_by(&:sku).sort_by { |_, sku_items| -sku_items.sum(&:quantity) }.each do |codigo, sku_items| %> +
    + +
    +
    + + + + + + + + + + + <% sku_items.sort_by(&:quantity).reverse.each do |item| %> + + + + + + + <% end %> + +
    PedidoQuantidadeStatusAções
    + <%= item.bling_order_item.bling_order_id %> + + Ver no Bling + + <%= item.quantity %> unidades + <% if item.resolved %> + Resolvido + <%= button_to 'Marcar como Não Resolvido', update_status_item_path(item, status: 'unresolved'), method: :patch, class: 'btn btn-sm btn-warning' %> + <% else %> + Não Resolvido + <%= button_to 'Marcar como Resolvido', update_status_item_path(item, status: 'resolved'), method: :patch, class: 'btn btn-sm btn-success' %> + <% end %> + + <% if item.bling_order_item.situation_id == BlingOrderItem::Status::PENDING %> + <%= button_to 'Marcar Pendente', update_status_item_path(item, status: 'pendente'), method: :patch, class: 'btn btn-sm btn-success' %> + <%= button_to 'Marcar Não Pendente', update_status_item_path(item, status: 'nao_pendente'), method: :patch, class: 'btn btn-sm btn-danger' %> + <% end %> +
    +
    +
    -
    + <% end %>
    - <% end %> +
    +
    + <% end %> + <% else %> +
    +
    +
    +

    Os pedidos aparecerão aqui

    +
    -
    - <% end %> - <% else %> -
    -
    -
    -

    Os pedidos aparecerão aqui

    -
    -
    + <% end %>
    - <% end %> +
    From fc0f8a75ea9e4b2045c6d030c4b0c6a370444282 Mon Sep 17 00:00:00 2001 From: puppe1990 Date: Thu, 5 Sep 2024 17:10:50 -0300 Subject: [PATCH 45/45] change layout --- app/views/orders_control/show_pending_orders.html.erb | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/app/views/orders_control/show_pending_orders.html.erb b/app/views/orders_control/show_pending_orders.html.erb index 48baeb76..4da88e86 100644 --- a/app/views/orders_control/show_pending_orders.html.erb +++ b/app/views/orders_control/show_pending_orders.html.erb @@ -68,16 +68,15 @@ <% if item.resolved %> Resolvido - <%= button_to 'Marcar como Não Resolvido', update_status_item_path(item, status: 'unresolved'), method: :patch, class: 'btn btn-sm btn-warning' %> <% else %> Não Resolvido - <%= button_to 'Marcar como Resolvido', update_status_item_path(item, status: 'resolved'), method: :patch, class: 'btn btn-sm btn-success' %> <% end %> - <% if item.bling_order_item.situation_id == BlingOrderItem::Status::PENDING %> - <%= button_to 'Marcar Pendente', update_status_item_path(item, status: 'pendente'), method: :patch, class: 'btn btn-sm btn-success' %> - <%= button_to 'Marcar Não Pendente', update_status_item_path(item, status: 'nao_pendente'), method: :patch, class: 'btn btn-sm btn-danger' %> + <% if item.resolved %> + <%= button_to 'Marcar como Não Resolvido', update_status_item_path(item, status: 'unresolved'), method: :patch, class: 'btn btn-sm btn-warning' %> + <% else %> + <%= button_to 'Marcar como Resolvido', update_status_item_path(item, status: 'resolved'), method: :patch, class: 'btn btn-sm btn-success' %> <% end %>