1
0
mirror of https://github.com/LaCasemate/fab-manager.git synced 2025-01-19 08:52:25 +01:00

Merge branch 'dev' for release 5.5.4

This commit is contained in:
Sylvain 2022-11-17 16:42:03 +01:00
commit 48d8b5dfab
10 changed files with 191 additions and 13 deletions

View File

@ -1,5 +1,10 @@
# Changelog Fab-manager
## v5.5.4 2022 November 17
- Fix a bug: unable to download an existing export of the statistics
- Fix a security issue: updated loader-utils to 2.0.4 to fix [CVE-2022-37601](https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2022-37601), [CVE-2022-37603](https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2022-37603) and [CVE-2022-37599](https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2022-37599)
## v5.5.3 2022 November 17
- By default, sort invoices by date in the admin list

View File

@ -30,7 +30,7 @@ class Statistics::QueryService
query: params[:body],
key: params[:type_key])
else
File.root.join(export.file)
Rails.root.join(export.file)
end
end
end

View File

@ -1,6 +1,6 @@
{
"name": "fab-manager",
"version": "5.5.3",
"version": "5.5.4",
"description": "Fab-manager is the FabLab management solution. It provides a comprehensive, web-based, open-source tool to simplify your administrative tasks and your marker's projects.",
"keywords": [
"fablab",

View File

@ -6,3 +6,17 @@ one:
field: "available_hours"
es_index: "fablab"
es_type: "availabilities"
two:
query: '{"size":0, "aggregations":{"%{aggs_name}":{"sum":{"field":"nb_total_places"}}}, "query":{"bool":{"must":[{"range":{"start_at":{"gte":"%{start_date}", "lte":"%{end_date}"}}}, {"match":{"available_type":"training"}}]}}}'
statistic_type_id: 3
field: "available_tickets"
es_index: "fablab"
es_type: "availabilities"
three:
query: '{"size":0, "aggregations":{"%{aggs_name}":{"avg":{"field":"ca", "script":"BigDecimal.valueOf(_value).setScale(1, RoundingMode.HALF_UP)", "missing": 0}}}, "query":{"bool":{"must":[{"range":{"date":{"gte":"%{start_date}", "lte":"%{end_date}"}}}]}}}'
statistic_type_id: 15
field: "average_cart"
es_index: "stats"
es_type: "order"

View File

@ -11,7 +11,7 @@ statistic_index_1:
statistic_index_2:
id: 2
es_type_key: machine
label: Créneaux machines
label: Heures machines
created_at: 2016-04-04 14:11:33.359367000 Z
updated_at: 2016-04-04 14:11:33.359367000 Z
table: true
@ -29,7 +29,7 @@ statistic_index_3:
statistic_index_4:
id: 4
es_type_key: event
label: Ateliers/Stages
label: Évènements
created_at: 2016-04-04 14:11:33.366381000 Z
updated_at: 2016-04-04 14:11:33.366381000 Z
table: true
@ -70,3 +70,12 @@ statistic_index_8:
updated_at: 2017-02-13 14:08:36.211740000 Z
table: true
ca: true
statistic_index_9:
id: 9
es_type_key: order
label: Commandes
created_at: 2022-10-11 13:31:22.962460
updated_at: 2022-10-11 13:31:22.962460 Z
table: true
ca: true

View File

@ -153,3 +153,17 @@ statistic_sub_type_22:
- month
created_at: 2016-04-04 15:18:28.864495000 Z
updated_at: 2016-04-04 15:18:28.864495000 Z
statistic_sub_type_23:
id: 23
key: paid-processed
label: Payée et/ou traitée
created_at: 2022-10-12 08:55:05.167910 Z
updated_at: 2022-10-12 08:55:05.167910 Z
statistic_sub_type_24:
id: 24
key: aborted
label: Interrompue
created_at: 2022-10-12 08:55:05.209986 Z
updated_at: 2022-10-12 08:55:05.209986 Z

View File

@ -243,3 +243,18 @@ statistic_type_sub_type_35:
statistic_sub_type_id: 22
created_at: 2016-04-04 15:18:28.867317000 Z
updated_at: 2016-04-04 15:18:28.867317000 Z
statistic_type_sub_type_36:
id: 36
statistic_type_id: 15
statistic_sub_type_id: 23
created_at: 2022-10-12 08:55:05.187077
updated_at: 2022-10-12 08:55:05.187077
statistic_type_sub_type_37:
id: 37
statistic_type_id: 15
statistic_sub_type_id: 24
created_at: 2022-10-12 08:55:05.211284
updated_at: 2022-10-12 08:55:05.211284

View File

@ -92,8 +92,8 @@ statistic_type_9:
statistic_type_10:
id: 10
statistic_index_id: 1
key: '2592000'
label: 'Durée : one month'
key: '2629746'
label: 'Durée : un mois'
graph: true
created_at: 2016-04-04 15:15:21.110438000 Z
updated_at: 2016-04-04 15:15:21.110438000 Z
@ -102,8 +102,8 @@ statistic_type_10:
statistic_type_11:
id: 11
statistic_index_id: 1
key: '5184000'
label: 'Durée : 2 months'
key: '5259492'
label: 'Durée : 2 mois'
graph: true
created_at: 2016-04-04 15:17:24.950033000 Z
updated_at: 2016-04-04 15:17:24.950033000 Z
@ -133,8 +133,18 @@ statistic_type_14:
id: 14
statistic_index_id: 1
key: '31556952'
label: 'Durée : 1 year'
label: 'Durée : 1 an'
graph: true
created_at: 2016-04-04 15:17:24.950033000 Z
updated_at: 2016-04-04 15:17:24.950033000 Z
simple: true
simple: true
statistic_type_15:
id: 15
statistic_index_id: 9
key: store
label: Boutique
graph: true
created_at: 2022-10-11 13:31:23.004224 Z
updated_at: 2022-10-11 13:31:23.004224 Z
simple: true

View File

@ -0,0 +1,111 @@
# frozen_string_literal: true
require 'test_helper'
require 'rubyXL'
module Exports; end
class Exports::StatisticsExportTest < ActionDispatch::IntegrationTest
setup do
admin = User.with_role(:admin).first
login_as(admin, scope: :user)
end
test 'export machine reservations statistics to Excel' do
# Build the stats for the June 2015, a machine reservation should have happened at the time
::Statistics::BuilderService.generate_statistic({ start_date: '2015-06-01'.to_date.beginning_of_day,
end_date: '2015-06-30'.to_date.end_of_day })
# Create a new export
post '/stats/machine/export', {
params: {
type_key: 'booking',
body: '{"query":{"bool":{"must":[{"term":{"type":"booking"}},{"range":{"date":{"gte":"2015-06-01T02:00:00+02:00",' \
'"lte":"2015-06-30T23:59:59+02:00"}}}]}},"sort":[{"date":{"order":"desc"}}],"aggs":{"total_ca":{"sum":{"field":"ca"}}, ' \
'"average_age":{"avg":{"field":"age"}},"total_stat":{"sum":{"field":"stat"}}}}'
}
}
# Check response format & status
assert_equal 200, response.status, response.body
assert_equal Mime[:json], response.content_type
# Check the export was created correctly
res = json_response(response.body)
e = Export.where(id: res[:export_id]).first
assert_not_nil e, 'Export was not created in database'
# Run the worker
worker = StatisticsExportWorker.new
worker.perform(e.id)
# notification
assert_not_empty Notification.where(attached_object: e)
# resulting XLSX file
assert FileTest.exist?(e.file), 'XLSX file was not generated'
workbook = RubyXL::Parser.parse(e.file)
# test worksheet
assert_not_nil workbook[StatisticIndex.find_by(es_type_key: 'machine').label]
# test data
reservation = Reservation.find(2)
wb = workbook[StatisticIndex.find_by(es_type_key: 'machine').label]
assert_equal 1, wb.sheet_data[0][1].value
assert_equal 15.0, wb.sheet_data[1][1].value
assert_equal reservation.user.statistic_profile.age.to_i, wb.sheet_data[2][1].value
assert_equal reservation.created_at.to_date, wb.sheet_data[5][0].value.to_date
assert_equal reservation.user.profile.full_name, wb.sheet_data[5][1].value
assert_equal reservation.user.email, wb.sheet_data[5][2].value
assert_equal reservation.user.profile.phone, wb.sheet_data[5][3].value
assert_equal I18n.t("export.#{reservation.user.statistic_profile.str_gender}"), wb.sheet_data[5][4].value
assert_equal reservation.user.statistic_profile.age.to_i, wb.sheet_data[5][5].value
assert_equal reservation.reservable.name, wb.sheet_data[5][6].value
assert_equal reservation.invoice_items.first.invoice.total / 100.0, wb.sheet_data[5][7].value
# Clean XLSX file
require 'fileutils'
FileUtils.rm(e.file)
end
test 'export global statistics to Excel' do
# Build the stats for the June 2015
::Statistics::BuilderService.generate_statistic({ start_date: '2015-06-01'.to_date.beginning_of_day,
end_date: '2015-06-30'.to_date.end_of_day })
# Create a new export
post '/stats/global/export', {
params: {
type_key: 'booking',
body: '{"query":{"bool":{"must":[{"range":{"date":{"gte":"2015-06-01T02:00:00+02:00","lte":"2015-06-30T23:59:59+02:00"}}}]}}}'
}
}
# Check response format & status
assert_equal 200, response.status, response.body
assert_equal Mime[:json], response.content_type
# Check the export was created correctly
res = json_response(response.body)
e = Export.where(id: res[:export_id]).first
assert_not_nil e, 'Export was not created in database'
# Run the worker
worker = StatisticsExportWorker.new
worker.perform(e.id)
# notification
assert_not_empty Notification.where(attached_object: e)
# resulting XLSX file
assert FileTest.exist?(e.file), 'XLSX file was not generated'
workbook = RubyXL::Parser.parse(e.file)
# test worksheets
StatisticIndex.where(table: true).includes(:statistic_fields, statistic_types: [:statistic_sub_types]).each do |index|
index.statistic_types.each do |type|
sheet_name = "#{index.label} - #{type.label}".gsub(%r{[*|\\:"<>?/]}, '').truncate(31)
assert_not_nil workbook[sheet_name], "#{sheet_name} not found"
end
end
end
end

View File

@ -5382,9 +5382,9 @@ loader-utils@^1.0.2, loader-utils@^1.1.0, loader-utils@^1.4.0:
json5 "^1.0.1"
loader-utils@^2.0.0:
version "2.0.2"
resolved "https://registry.yarnpkg.com/loader-utils/-/loader-utils-2.0.2.tgz#d6e3b4fb81870721ae4e0868ab11dd638368c129"
integrity sha512-TM57VeHptv569d/GKh6TAYdzKblwDNiumOdkFnejjD0XwTH87K90w3O7AiJRqdQoXygvi1VQTJTLGhJl7WqA7A==
version "2.0.4"
resolved "https://registry.yarnpkg.com/loader-utils/-/loader-utils-2.0.4.tgz#8b5cb38b5c34a9a018ee1fc0e6a066d1dfcc528c"
integrity sha512-xXqpXoINfFhgua9xiqD8fPFHgkoq1mmmpE92WlDbm9rNRd/EbRb+Gqf908T2DMfuHjjJlksiK2RbHVOdD/MqSw==
dependencies:
big.js "^5.2.2"
emojis-list "^3.0.0"