lesli_audit 1.0.1 → 1.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (92) hide show
  1. checksums.yaml +4 -4
  2. data/app/assets/images/lesli_audit/audit-logo.svg +1 -72
  3. data/app/controllers/lesli_audit/analytics_controller.rb +4 -7
  4. data/app/controllers/lesli_audit/dashboards_controller.rb +0 -2
  5. data/app/controllers/lesli_audit/logs_controller.rb +25 -0
  6. data/app/controllers/lesli_audit/requests_controller.rb +1 -1
  7. data/app/controllers/lesli_audit/user_journals_controller.rb +60 -0
  8. data/app/controllers/lesli_audit/users_controller.rb +3 -1
  9. data/app/helpers/lesli_audit/logs_helper.rb +4 -0
  10. data/app/helpers/lesli_audit/user_journals_helper.rb +4 -0
  11. data/app/interfaces/lesli_audit/logger_interface.rb +43 -8
  12. data/app/models/lesli_audit/account.rb +7 -1
  13. data/app/models/lesli_audit/account_device.rb +5 -0
  14. data/app/models/lesli_audit/account_log.rb +11 -0
  15. data/app/models/lesli_audit/dashboard.rb +1 -2
  16. data/app/models/lesli_audit/user_journal.rb +7 -0
  17. data/app/models/lesli_audit/user_log.rb +7 -0
  18. data/app/models/lesli_audit/user_request.rb +1 -1
  19. data/app/services/lesli_audit/analytic_service.rb +53 -41
  20. data/{db/migrate/v1.0/0503050110_create_lesli_audit_dashboards.rb → app/services/lesli_audit/log_service.rb} +10 -4
  21. data/app/services/lesli_audit/request_service.rb +1 -2
  22. data/app/services/lesli_audit/user_service.rb +53 -2
  23. data/app/views/lesli_audit/analytics/index.html.erb +20 -18
  24. data/app/views/lesli_audit/dashboards/_component-calendar.html.erb +0 -0
  25. data/app/views/lesli_audit/dashboards/show.html.erb +1 -1
  26. data/app/views/lesli_audit/logs/index.html.erb +23 -0
  27. data/app/views/lesli_audit/logs/show.html.erb +10 -0
  28. data/app/views/lesli_audit/partials/_navigation.html.erb +4 -5
  29. data/app/views/lesli_audit/user_journals/_form.html.erb +17 -0
  30. data/app/views/lesli_audit/user_journals/_user_journal.html.erb +2 -0
  31. data/app/views/lesli_audit/user_journals/edit.html.erb +12 -0
  32. data/app/views/lesli_audit/user_journals/index.html.erb +16 -0
  33. data/app/views/lesli_audit/user_journals/new.html.erb +11 -0
  34. data/app/views/lesli_audit/user_journals/show.html.erb +10 -0
  35. data/app/views/lesli_audit/users/index.html.erb +31 -2
  36. data/config/routes.rb +8 -27
  37. data/db/migrate/v1.0/0501110110_create_lesli_audit_account_logs.rb +53 -0
  38. data/db/migrate/v1.0/0501110210_create_lesli_audit_account_devices.rb +45 -0
  39. data/db/migrate/v1.0/0501120110_create_lesli_audit_user_logs.rb +54 -0
  40. data/db/migrate/v1.0/0501120210_create_lesli_audit_user_journals.rb +45 -0
  41. data/db/migrate/v1.0/{0503110010_create_lesli_audit_user_requests.rb → 0501120310_create_lesli_audit_user_requests.rb} +4 -3
  42. data/db/seed/devices.rb +68 -0
  43. data/db/seeds.rb +1 -0
  44. data/db/version_structure.rb +53 -0
  45. data/lib/lesli_audit/engine.rb +1 -0
  46. data/lib/lesli_audit/version.rb +2 -2
  47. data/readme.md +78 -25
  48. metadata +46 -54
  49. data/app/helpers/lesli_audit/dashboard/components_helper.rb +0 -4
  50. data/app/models/lesli_audit/account/request.rb +0 -4
  51. data/app/models/lesli_audit/analytic.rb +0 -4
  52. data/app/models/lesli_audit/dashboard/component.rb +0 -18
  53. data/app/models/lesli_audit/request.rb +0 -4
  54. data/app/models/lesli_audit/user.rb +0 -4
  55. data/app/services/lesli_audit/account/activity_services.rb +0 -69
  56. data/app/services/lesli_audit/analytics/trend_services.rb +0 -84
  57. data/app/services/lesli_audit/analytics/visitor_service.rb +0 -172
  58. data/app/services/lesli_audit/users/activity_services.rb +0 -61
  59. data/app/services/lesli_audit/users/log_services.rb +0 -62
  60. data/app/services/lesli_audit/users/registration_services.rb +0 -62
  61. data/app/services/lesli_audit/users/role_services.rb +0 -61
  62. data/app/services/lesli_audit/users/working_hour_services.rb +0 -78
  63. data/app/views/lesli_audit/accounts/_account.html.erb +0 -2
  64. data/app/views/lesli_audit/accounts/_form.html.erb +0 -17
  65. data/app/views/lesli_audit/accounts/edit.html.erb +0 -10
  66. data/app/views/lesli_audit/accounts/index.html.erb +0 -14
  67. data/app/views/lesli_audit/accounts/new.html.erb +0 -9
  68. data/app/views/lesli_audit/accounts/show.html.erb +0 -10
  69. data/app/views/lesli_audit/analytics/_analytic.html.erb +0 -2
  70. data/app/views/lesli_audit/analytics/_form.html.erb +0 -17
  71. data/app/views/lesli_audit/analytics/edit.html.erb +0 -10
  72. data/app/views/lesli_audit/analytics/new.html.erb +0 -9
  73. data/app/views/lesli_audit/analytics/show.html.erb +0 -10
  74. data/app/views/lesli_audit/dashboard/components/_component.html.erb +0 -2
  75. data/app/views/lesli_audit/dashboard/components/_form.html.erb +0 -17
  76. data/app/views/lesli_audit/dashboard/components/edit.html.erb +0 -1
  77. data/app/views/lesli_audit/dashboard/components/index.html.erb +0 -14
  78. data/app/views/lesli_audit/dashboard/components/new.html.erb +0 -9
  79. data/app/views/lesli_audit/dashboard/components/show.html.erb +0 -1
  80. data/app/views/lesli_audit/dashboards/_dashboard.html.erb +0 -2
  81. data/app/views/lesli_audit/dashboards/_form.html.erb +0 -17
  82. data/app/views/lesli_audit/requests/_form.html.erb +0 -17
  83. data/app/views/lesli_audit/requests/_request.html.erb +0 -2
  84. data/app/views/lesli_audit/requests/edit.html.erb +0 -10
  85. data/app/views/lesli_audit/requests/new.html.erb +0 -9
  86. data/app/views/lesli_audit/requests/show.html.erb +0 -10
  87. data/app/views/lesli_audit/users/_form.html.erb +0 -17
  88. data/app/views/lesli_audit/users/_user.html.erb +0 -2
  89. data/app/views/lesli_audit/users/edit.html.erb +0 -10
  90. data/app/views/lesli_audit/users/new.html.erb +0 -9
  91. /data/db/migrate/v1.0/{0503000110_create_lesli_audit_accounts.rb → 0501000110_create_lesli_audit_accounts.rb} +0 -0
  92. /data/db/migrate/v1.0/{0503100010_create_lesli_audit_account_requests.rb → 0501110310_create_lesli_audit_account_requests.rb} +0 -0
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 243d721faa43b0cdba37a620455872fd0f515bbae81e18fc6bf49c4490c3e5aa
4
- data.tar.gz: 983e1c3c7f1c44d2cea04996ca5f1060d797092c24c3e45c396fc1159ee8fda5
3
+ metadata.gz: ff9465d4d130455ae1ef9804d86e17e54754708857234684a0d99237f8545770
4
+ data.tar.gz: 3455cb58ed202920a07a0faacf21ced66b421201a2832206e22c0495bff8d05c
5
5
  SHA512:
6
- metadata.gz: 24214a6c519ed8554cc81df0fdd045eae85a7195e7057fa20a87620d1af56c43eaf43d9dd7f638ef85c3edc14fa0c7232e1efbaf2a8120516ea6b6a24f69642b
7
- data.tar.gz: f16f44e3ac62f688ce7aea3db2290ba5546175ce33cf511307382f22095af22d74cd0eafd93a253e9c63a22406fd77689de1fc0de38c1f061a0d33ec2bdf8c7c
6
+ metadata.gz: 32ea636b6528c49201ba30eb2e972deaeca0ea47bf625f5e8815a81fec5dbb83bdb3c4f450c014cb33f3eef2b9e5b040acaf8a887410d3117880e89a3736dfc6
7
+ data.tar.gz: 21ee15b705797e0f6871a7432b7044b85bdaee377b376b55f568d77a329e9be51bcfc6426c80290c4ec0c08dab47fa2b8da11024c59751d3af23e7ce0e8c9256
@@ -1,72 +1 @@
1
- <?xml version="1.0" encoding="UTF-8" standalone="no"?>
2
- <svg
3
- xmlns:dc="http://purl.org/dc/elements/1.1/"
4
- xmlns:cc="http://creativecommons.org/ns#"
5
- xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
6
- xmlns:svg="http://www.w3.org/2000/svg"
7
- xmlns="http://www.w3.org/2000/svg"
8
- xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
9
- xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
10
- inkscape:version="1.0 (4035a4f, 2020-05-01)"
11
- height="48.025002"
12
- width="43.825001"
13
- sodipodi:docname="iconfinder_186_2508414.svg"
14
- xml:space="preserve"
15
- viewBox="0 0 43.825001 48.025002"
16
- version="1.1"
17
- id="Layer_1"
18
- enable-background="new 0 0 48 48"><metadata
19
- id="metadata860"><rdf:RDF><cc:Work
20
- rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
21
- rdf:resource="http://purl.org/dc/dcmitype/StillImage" /></cc:Work></rdf:RDF></metadata><defs
22
- id="defs858" /><sodipodi:namedview
23
- inkscape:current-layer="Layer_1"
24
- inkscape:window-maximized="1"
25
- inkscape:window-y="23"
26
- inkscape:window-x="0"
27
- inkscape:cy="24"
28
- inkscape:cx="18.731461"
29
- inkscape:zoom="9.7781858"
30
- showgrid="false"
31
- id="namedview856"
32
- inkscape:window-height="953"
33
- inkscape:window-width="1680"
34
- inkscape:pageshadow="2"
35
- inkscape:pageopacity="0"
36
- guidetolerance="10"
37
- gridtolerance="10"
38
- objecttolerance="10"
39
- borderopacity="1"
40
- bordercolor="#666666"
41
- pagecolor="#ffffff" /><g
42
- transform="translate(-2.1)"
43
- id="g853"><g
44
- id="g837"><path
45
- id="path833"
46
- fill="#e6e6e5"
47
- d="M 26.4,0 H 6.5 C 4.1,0 2.1,2 2.1,4.4 v 39 c 0,2.4 2,4.4 4.4,4.4 h 30.7 c 2.4,0 4.4,-2 4.4,-4.4 V 15.3 C 36.7,10.3 30.3,3.9 26.4,0 Z" /><path
48
- id="path835"
49
- fill="#98d0f1"
50
- d="m 26.4,0 v 10.8 c 0,2.4 2,4.4 4.4,4.4 H 41.6 C 37.6,11.3 31.2,4.9 26.4,0 Z" /></g><g
51
- id="g841"><path
52
- id="path839"
53
- fill="#ec7b72"
54
- d="m 21.2,40.7 c -0.2,0 -0.4,-0.2 -0.5,-0.4 l -5.1,-21.4 -4.1,8.4 c -0.1,0.2 -0.3,0.3 -0.4,0.3 h -8 c -0.3,0 -0.5,-0.2 -0.5,-0.5 0,-0.3 0.2,-0.5 0.5,-0.5 h 7.7 l 4.6,-9.4 c 0.1,-0.2 0.3,-0.3 0.5,-0.3 0.2,0 0.4,0.2 0.4,0.4 l 5,20.7 2.6,-11.1 c 0.1,-0.2 0.3,-0.4 0.5,-0.4 h 4.1 l 1.7,-4.4 c 0.1,-0.2 0.3,-0.3 0.5,-0.3 0.2,0 0.4,0.2 0.5,0.4 l 3.5,12 L 36,27 c 0,-0.2 0.2,-0.4 0.5,-0.4 h 4.3 c 0.3,0 0.5,0.2 0.5,0.5 0,0.3 -0.2,0.5 -0.5,0.5 h -3.9 l -1.6,8.9 c 0,0.2 -0.2,0.4 -0.5,0.4 -0.2,0 -0.4,-0.1 -0.5,-0.4 l -3.7,-12.6 -1.3,3.4 c -0.1,0.2 -0.3,0.3 -0.5,0.3 h -4 l -3,12.8 c -0.1,0.1 -0.3,0.3 -0.6,0.3 z" /></g><g
55
- id="g851"><rect
56
- id="rect843"
57
- y="33.900002"
58
- x="33.700001"
59
- width="2.5"
60
- transform="matrix(0.7071,-0.7071,0.7071,0.7071,-15.9478,35.568)"
61
- height="6.3000002"
62
- fill="#333333" /><path
63
- id="path845"
64
- fill="#525252"
65
- d="m 18.5,20.6 c -4.2,4.2 -4.2,11 0,15.1 4.2,4.1 11,4.2 15.1,0 4.2,-4.2 4.2,-10.9 0,-15.1 -4.2,-4.2 -10.9,-4.2 -15.1,0 z m 13.2,13.2 c -3.1,3.1 -8.2,3.1 -11.3,0 -3.1,-3.1 -3.1,-8.2 0,-11.4 3.1,-3.1 8.2,-3.1 11.3,0 3.2,3.2 3.2,8.3 0,11.4 z" /><path
66
- id="path847"
67
- opacity="0.25"
68
- fill="#ffffff"
69
- d="m 30.6,23.9 c -2.4,-2.4 -6.3,-2.4 -8.7,0 0,0 0,0 0,0 l 1.7,1.7 c 0,0 0,0 0,0 2.1,-2.1 5.6,-2.1 7.7,0 0.4,0.4 0.8,0.9 1,1.4 -0.3,-1.1 -0.9,-2.2 -1.7,-3.1 z" /><path
70
- id="path849"
71
- fill="#ffcc67"
72
- d="m 37.5,34.5 c -0.3,-0.3 -0.8,-0.3 -1.1,0 v 0 l -4,4 v 0 c -0.3,0.3 -0.3,0.8 0,1.1 0.3,0.3 0.8,0.3 1.1,0 l 7.6,7.6 c 1.1,1.1 2.9,1.1 4,0 1.1,-1.1 1.1,-2.9 0,-4 l -7.6,-7.6 c 0.3,-0.3 0.3,-0.8 0,-1.1 z" /></g></g></svg>
1
+ <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 43.8 48.09" fill="#0d52bf"><path stroke="#000" stroke-miterlimit="10" stroke-width=".25" d="M36.5 12.29c-4.3-4.3-9-9.1-12.2-12.2 3.7 3.8 8.4 8.5 12.2 12.2Z"/><path d="m19.2 38.09.1-.3q-.1 0-.2-.1z"/><path stroke="#000" stroke-miterlimit="10" stroke-width=".25" d="m39.5 15.29-3-3z"/><path d="m33.3 35.89.1-.4-.2.2z"/><path d="M31.26 40.61c-.13.04-.27.05-.41.05-.41 0-.79-.16-1.08-.45s-.44-.67-.44-1.08c0-.39.15-.75.4-1.03a11.2 11.2 0 0 1-5.7 1.55c-1.31 0-2.62-.24-3.88-.68l-.35 1.61c-.1.1-.3.3-.6.3-.2 0-.4-.2-.5-.4l-.56-2.45c-.8-.47-1.57-1.04-2.26-1.72a11.17 11.17 0 0 1-3.38-7.98c-.01-2.25.62-4.4 1.82-6.25l-.72-3.01-4.1 8.4c-.1.2-.3.3-.4.3H1c-.3 0-.5-.2-.5-.5s.2-.5.5-.5h7.7l4.6-9.4c.1-.2.3-.3.5-.3s.4.2.4.4l.86 3.58c.25-.31.52-.62.81-.91 4.45-4.46 11.7-4.46 16.16 0 1.82 1.82 2.95 4.14 3.27 6.63h3.4c.3 0 .5.2.5.5s-.2.5-.5.5h-3.32c0 .15.02.3.02.45 0 2.07-.57 4.06-1.61 5.81.6-.58 1.55-.58 2.14.01.29.29.44.67.44 1.08 0 .14-.02.28-.05.41l3.18 3.18V15.39l-.1-.1H28.7c-2.4 0-4.4-2-4.4-4.4V.09H4.4C2 .09 0 2.09 0 4.49v39c0 2.4 2 4.4 4.4 4.4h30.7c.95 0 1.82-.32 2.55-.89z"/><path d="m29.718 35.787 1.768-1.768 4.454 4.455-1.767 1.768z"/><path d="M16.37 20.66c-4.2 4.2-4.2 11 0 15.1s11 4.2 15.1 0c4.2-4.2 4.2-10.9 0-15.1s-10.9-4.2-15.1 0m13.2 13.2c-3.1 3.1-8.2 3.1-11.3 0s-3.1-8.2 0-11.4c3.1-3.1 8.2-3.1 11.3 0 3.2 3.2 3.2 8.3 0 11.4"/><path d="M28.47 23.96c-2.4-2.4-6.3-2.4-8.7 0l1.7 1.7c2.1-2.1 5.6-2.1 7.7 0 .4.4.8.9 1 1.4-.3-1.1-.9-2.2-1.7-3.1" style="isolation:isolate"/><path d="M35.37 34.56c-.3-.3-.8-.3-1.1 0l-4 4c-.3.3-.3.8 0 1.1s.8.3 1.1 0l7.6 7.6c1.1 1.1 2.9 1.1 4 0s1.1-2.9 0-4l-7.6-7.6c.3-.3.3-.8 0-1.1"/></svg>
@@ -3,13 +3,10 @@ module LesliAudit
3
3
 
4
4
  # GET /analytics
5
5
  def index
6
- @visitors = respond_as_successful(AnalyticService.new(current_user, query).visitors)
7
- @controllers = respond_as_successful(AnalyticService.new(current_user, query).controllers)
8
- @users = respond_as_successful(AnalyticService.new(current_user, query).users)
9
- end
10
-
11
- def devices
12
- respond_with_successful(AnalyticService.new(current_user, query).devices)
6
+ @visitors = AnalyticService.new(current_user, query).visitors
7
+ @requests = AnalyticService.new(current_user, query).requests
8
+ @browsers = AnalyticService.new(current_user, query).browsers
9
+ @platforms = AnalyticService.new(current_user, query).devices
13
10
  end
14
11
 
15
12
  private
@@ -32,7 +32,5 @@ Building a better future, one line of code at a time.
32
32
 
33
33
  module LesliAudit
34
34
  class DashboardsController < Lesli::Shared::DashboardsController
35
- def show
36
- end
37
35
  end
38
36
  end
@@ -0,0 +1,25 @@
1
+ module LesliAudit
2
+ class LogsController < ApplicationController
3
+ before_action :set_log, only: %i[ show ]
4
+
5
+ # GET /logs
6
+ def index
7
+ @logs = respond_with_pagination(LesliAudit::LogService.new(current_user, query).index)
8
+ end
9
+
10
+ # GET /logs/1
11
+ def show
12
+ end
13
+
14
+ private
15
+
16
+ def set_log
17
+ @log = Log.find(params.expect(:id))
18
+ end
19
+
20
+ # Only allow a list of trusted parameters through.
21
+ def log_params
22
+ params.fetch(:log, {})
23
+ end
24
+ end
25
+ end
@@ -35,7 +35,7 @@ module LesliAudit
35
35
 
36
36
  # GET /requests
37
37
  def index
38
- @requests = respond_as_pagination(LesliAudit::RequestService.new(current_user, query).index)
38
+ @requests = respond_with_pagination(LesliAudit::RequestService.new(current_user, query).index)
39
39
  end
40
40
  end
41
41
  end
@@ -0,0 +1,60 @@
1
+ module LesliAudit
2
+ class UserJournalsController < ApplicationController
3
+ before_action :set_user_journal, only: %i[ show edit update destroy ]
4
+
5
+ # GET /user_journals
6
+ def index
7
+ @user_journals = UserJournal.all
8
+ end
9
+
10
+ # GET /user_journals/1
11
+ def show
12
+ end
13
+
14
+ # GET /user_journals/new
15
+ def new
16
+ @user_journal = UserJournal.new
17
+ end
18
+
19
+ # GET /user_journals/1/edit
20
+ def edit
21
+ end
22
+
23
+ # POST /user_journals
24
+ def create
25
+ @user_journal = UserJournal.new(user_journal_params)
26
+
27
+ if @user_journal.save
28
+ redirect_to @user_journal, notice: "User journal was successfully created."
29
+ else
30
+ render :new, status: :unprocessable_content
31
+ end
32
+ end
33
+
34
+ # PATCH/PUT /user_journals/1
35
+ def update
36
+ if @user_journal.update(user_journal_params)
37
+ redirect_to @user_journal, notice: "User journal was successfully updated.", status: :see_other
38
+ else
39
+ render :edit, status: :unprocessable_content
40
+ end
41
+ end
42
+
43
+ # DELETE /user_journals/1
44
+ def destroy
45
+ @user_journal.destroy!
46
+ redirect_to user_journals_path, notice: "User journal was successfully destroyed.", status: :see_other
47
+ end
48
+
49
+ private
50
+ # Use callbacks to share common setup or constraints between actions.
51
+ def set_user_journal
52
+ @user_journal = UserJournal.find(params.expect(:id))
53
+ end
54
+
55
+ # Only allow a list of trusted parameters through.
56
+ def user_journal_params
57
+ params.fetch(:user_journal, {})
58
+ end
59
+ end
60
+ end
@@ -34,7 +34,9 @@ module LesliAudit
34
34
 
35
35
  # GET /users
36
36
  def index
37
- @users = respond_as_successful(UserService.new(current_user, query).registrations)
37
+ @requests = UserService.new(current_user, query).requests
38
+ @registrations = UserService.new(current_user, query).registrations
39
+ @working_hours = UserService.new(current_user, query).working_hours
38
40
  end
39
41
  end
40
42
  end
@@ -0,0 +1,4 @@
1
+ module LesliAudit
2
+ module LogsHelper
3
+ end
4
+ end
@@ -0,0 +1,4 @@
1
+ module LesliAudit
2
+ module UserJournalsHelper
3
+ end
4
+ end
@@ -61,8 +61,7 @@ module LesliAudit
61
61
  end
62
62
 
63
63
  def log_account_requests
64
- return unless Lesli.config.security.dig(:enable_analytics)
65
- return unless defined?(LesliAudit)
64
+ return unless Lesli.config.audit.dig(:enable_analytics)
66
65
  return unless current_user
67
66
 
68
67
  # Try to save a unique record for this request configuration
@@ -85,11 +84,20 @@ module LesliAudit
85
84
  # Track all user activity
86
85
  # this is disabled by default in the settings file
87
86
  def log_user_requests
88
- return unless Lesli.config.security.dig(:enable_analytics)
89
- return unless defined?(LesliAudit)
90
87
  return unless current_user
91
88
  return unless session[:user_session_id]
89
+
90
+ current_user.account.audit.user_journals.create({
91
+ request_controller: controller_path,
92
+ request_action: action_name,
93
+ session_id: session[:user_session_id],
94
+ user_id: current_user.id,
95
+ date: Date2.new.date.to_s
96
+ }) if Lesli.config.audit.dig(:enable_journals)
92
97
 
98
+ # Determine the correct SQL "now" keyword based on the database connection
99
+ now_func = ActiveRecord::Base.connection.adapter_name =~ /sqlite/i ? 'CURRENT_TIMESTAMP' : 'NOW()'
100
+
93
101
  # Try to save a unique record for this request configuration
94
102
  current_user.account.audit.user_requests.upsert(
95
103
  {
@@ -97,18 +105,45 @@ module LesliAudit
97
105
  request_action: action_name,
98
106
  session_id: session[:user_session_id],
99
107
  user_id: current_user.id,
100
- request_count: 1,
101
- created_at: Date2.new.date.to_s
108
+ date: Date2.new.date.to_s,
109
+ request_count: 1
102
110
  },
103
111
 
104
112
  # group of columns to consider a request as unique
105
- unique_by: %i[request_controller request_action created_at user_id session_id],
113
+ unique_by: %i[request_controller request_action date user_id session_id],
114
+
115
+ # if request id is not unique
116
+ # - increase the counter for this configuration
117
+ # - update the datetime of the last request
118
+ on_duplicate: Arel.sql(
119
+ "request_count = lesli_audit_user_requests.request_count + 1,updated_at = #{LesliDate::Compatibility.db_now}"
120
+ )
121
+ ) if Lesli.config.audit.dig(:enable_analytics)
122
+ end
123
+
124
+ def log_devices
125
+ return unless Lesli.config.audit.dig(:enable_analytics)
126
+ return unless current_user
127
+
128
+ user_agent = get_user_agent(false)
129
+
130
+ # Try to save a unique record for this request configuration
131
+ current_user.account.audit.account_devices.upsert(
132
+ {
133
+ :created_at => Date2.new.date.to_s,
134
+ :agent_platform => user_agent&.dig(:platform) || "unknown",
135
+ :agent_browser => user_agent&.dig(:browser) || "unknown",
136
+ :agent_count => 1
137
+ },
138
+
139
+ # group of columns to consider a request as unique
140
+ unique_by: %i[agent_platform agent_browser created_at account_id],
106
141
 
107
142
  # if request id is not unique
108
143
  # - increase the counter for this configuration
109
144
  # - update the datetime of the last request
110
145
  on_duplicate: Arel.sql(
111
- 'request_count = lesli_audit_user_requests.request_count + 1'
146
+ 'agent_count = lesli_audit_account_devices.agent_count + 1'
112
147
  )
113
148
  )
114
149
  end
@@ -1,9 +1,15 @@
1
1
  module LesliAudit
2
2
  class Account < ApplicationRecord
3
3
  belongs_to :account, class_name: "Lesli::Account"
4
+ has_many :dashboards
5
+
6
+ has_many :account_logs
7
+ has_many :account_devices
4
8
  has_many :account_requests
9
+
10
+ has_many :user_logs
11
+ has_many :user_journals
5
12
  has_many :user_requests
6
- has_many :dashboards
7
13
 
8
14
  after_create :initialize_account
9
15
 
@@ -0,0 +1,5 @@
1
+ module LesliAudit
2
+ class AccountDevice < ApplicationRecord
3
+ belongs_to :account, class_name: 'Lesli::Account'
4
+ end
5
+ end
@@ -0,0 +1,11 @@
1
+ module LesliAudit
2
+ class AccountLog < ApplicationRecord
3
+ belongs_to :account, optional: true
4
+ belongs_to :user, class_name: "Lesli::User", optional: true
5
+
6
+ enum :operation, {
7
+ :account_creation => 'account_creation',
8
+ :account_initialization => 'account_initialization'
9
+ }
10
+ end
11
+ end
@@ -1,6 +1,5 @@
1
1
  module LesliAudit
2
2
  class Dashboard < Lesli::Shared::Dashboard
3
- self.table_name = "lesli_audit_dashboards"
4
- belongs_to :account
3
+ COMPONENTS = %i[calendar]
5
4
  end
6
5
  end
@@ -0,0 +1,7 @@
1
+ module LesliAudit
2
+ class UserJournal < ApplicationRecord
3
+ belongs_to :account
4
+ belongs_to :user, class_name: "Lesli::User"
5
+ belongs_to :session, class_name: "LesliShield::User::Session"
6
+ end
7
+ end
@@ -0,0 +1,7 @@
1
+ module LesliAudit
2
+ class UserLog < ApplicationRecord
3
+ belongs_to :account, optional: true
4
+ belongs_to :user, class_name: "Lesli::User"
5
+ belongs_to :session, class_name: "LesliShield::User::Session", optional: true
6
+ end
7
+ end
@@ -2,6 +2,6 @@ module LesliAudit
2
2
  class UserRequest < ApplicationRecord
3
3
  belongs_to :account
4
4
  belongs_to :user, class_name: "Lesli::User"
5
- belongs_to :session, class_name: "Lesli::User::Session"
5
+ belongs_to :session, class_name: "LesliShield::User::Session"
6
6
  end
7
7
  end
@@ -41,46 +41,34 @@ module LesliAudit
41
41
  # @description
42
42
  # @example
43
43
  def visitors
44
-
45
- group = 'day'
46
- #group = params[:bygroup] if ['month','week','day'].include?(params[:bygroup])
47
-
48
- # only the users of the account
49
- usrs = current_user.account.users
50
-
51
- group_by = "DATE_TRUNC('month', created_at)" if group == 'month'
52
- group_by = "DATE_TRUNC('week', created_at)" if group == 'week'
53
- group_by = "DATE_TRUNC('day', created_at)" if group == 'day'
54
-
55
- # compatibility for SQLite
56
- if ActiveRecord::Base.connection.adapter_name == "SQLite"
57
- group_by = "strftime('%Y-%m-%d', created_at)"
58
- end
59
-
60
- requests = current_user.account.audit.account_requests.group(group_by)
61
-
62
- requests = apply_filters(requests, query)
63
-
64
- requests.limit(10).order("date desc").select(
65
- "count(id) resources",
66
- "sum(request_count) requests",
67
- "#{group_by} date"
68
- ).as_json
69
- end
70
-
71
- def users
72
-
73
- current_user.account.audit.user_requests
74
- .joins(:user)
75
- .group(:email)
76
- .limit(LIMIT).order("requests DESC").select(
77
- :email,
78
- "count(lesli_audit_user_requests.id) resources",
79
- "sum(lesli_audit_user_requests.request_count) requests"
80
- )
81
- end
82
-
83
- def controllers
44
+ #Rails.cache.fetch(cache_key_for_account(__method__), expires_in: 1.hour) do
45
+ group = 'day'
46
+ #group = params[:bygroup] if ['month','week','day'].include?(params[:bygroup])
47
+
48
+ # only the users of the account
49
+ usrs = current_user.account.users
50
+
51
+ group_by = "DATE_TRUNC('month', created_at)" if group == 'month'
52
+ group_by = "DATE_TRUNC('week', created_at)" if group == 'week'
53
+ group_by = "DATE_TRUNC('day', created_at)" if group == 'day'
54
+
55
+ # compatibility for SQLite
56
+ if ActiveRecord::Base.connection.adapter_name == "SQLite"
57
+ group_by = "strftime('%Y-%m-%d', created_at)"
58
+ end
59
+
60
+ requests = current_user.account.audit.account_requests.group(group_by)
61
+
62
+ requests = apply_filters(requests, query)
63
+
64
+ requests.limit(10).order("xaxiskey desc").select(
65
+ "sum(request_count) yaxiskey",
66
+ "#{group_by} xaxiskey"
67
+ ).as_json
68
+ #end
69
+ end
70
+
71
+ def requests
84
72
  requests = current_user.account.audit.account_requests
85
73
  .group("request_controller").limit(30)
86
74
 
@@ -89,7 +77,31 @@ module LesliAudit
89
77
  requests = requests.limit(LIMIT).order("requests DESC").select(
90
78
  :request_controller,
91
79
  "sum(request_count) requests"
92
- )
80
+ ).as_json
81
+ end
82
+
83
+ def devices
84
+ #Rails.cache.fetch(cache_key_for_account(__method__), expires_in: 4.hour) do
85
+ current_user.account.audit.account_devices
86
+ .group(:agent_platform, :created_at)
87
+ .select(
88
+ 'created_at as xaxiskey',
89
+ 'agent_platform as dataname',
90
+ 'sum(agent_count) as yaxiskey'
91
+ ).as_json
92
+ #end
93
+ end
94
+
95
+ def browsers
96
+ #Rails.cache.fetch(cache_key_for_account(__method__), expires_in: 4.hour) do
97
+ current_user.account.audit.account_devices
98
+ .group(:agent_browser, :created_at)
99
+ .select(
100
+ 'created_at as xaxiskey',
101
+ 'agent_browser as dataname',
102
+ 'sum(agent_count) as yaxiskey'
103
+ ).as_json
104
+ #end
93
105
  end
94
106
 
95
107
  private
@@ -17,7 +17,7 @@ GNU General Public License for more details.
17
17
  You should have received a copy of the GNU General Public License
18
18
  along with this program. If not, see http://www.gnu.org/licenses/.
19
19
 
20
- Lesli · Ruby on Rails SaaS Development Framework.
20
+ Lesli · Ruby on Rails SaaS development platform.
21
21
 
22
22
  Made with ♥ by https://www.lesli.tech
23
23
  Building a better future, one line of code at a time.
@@ -30,8 +30,14 @@ Building a better future, one line of code at a time.
30
30
  // ·
31
31
  =end
32
32
 
33
- class CreateLesliAuditDashboards < ActiveRecord::Migration[6.1]
34
- def change
35
- create_table_lesli_shared_dashboards_10(:lesli_audit)
33
+ module LesliAudit
34
+ class LogService < Lesli::ApplicationLesliService
35
+
36
+ def index
37
+ current_user.logs.all
38
+ .order(created_at: :desc)
39
+ .page(query[:pagination][:page])
40
+ .per(query[:pagination][:perPage])
41
+ end
36
42
  end
37
43
  end
@@ -41,9 +41,8 @@ module LesliAudit
41
41
  def index
42
42
 
43
43
 
44
- requests = Account::Request.all
44
+ requests = current_user.requests
45
45
  .order(created_at: :desc)
46
- .order(request_count: :desc)
47
46
  .page(query[:pagination][:page])
48
47
  .per(query[:pagination][:perPage])
49
48
 
@@ -33,6 +33,57 @@ Building a better future, one line of code at a time.
33
33
  module LesliAudit
34
34
  class UserService < Lesli::ApplicationLesliService
35
35
 
36
+ def requests
37
+ current_user.account.audit.user_requests
38
+ .joins(:user)
39
+ .group(:email)
40
+ .limit(5)
41
+ .order("requests DESC")
42
+ .select(
43
+ :email,
44
+ "count(lesli_audit_user_requests.id) resources",
45
+ "sum(lesli_audit_user_requests.request_count) requests"
46
+ )
47
+ end
48
+
49
+ def working_hours
50
+
51
+ group = 'day'
52
+
53
+ group_by = "DATE_TRUNC('month', lesli_audit_user_requests.date)" if group == 'month'
54
+ group_by = "DATE_TRUNC('week', lesli_audit_user_requests.date)" if group == 'week'
55
+ group_by = "DATE_TRUNC('day', lesli_audit_user_requests.date)" if group == 'day'
56
+
57
+ # compatibility for SQLite
58
+ if ActiveRecord::Base.connection.adapter_name == "SQLite"
59
+ group_by = "strftime('%Y-%m-%d', lesli_audit_user_requests.date)"
60
+ end
61
+
62
+ user_requests = current_user.account.users.joins(:requests)
63
+
64
+ user_requests = user_requests.select(
65
+ :id,
66
+ "lesli_users.id as user_id",
67
+ "lesli_users.email as user_email",
68
+ "#{group_by} date",
69
+ "min(lesli_audit_user_requests.created_at) as first_activity",
70
+ "max(lesli_audit_user_requests.updated_at) as last_activity",
71
+ "count(lesli_audit_user_requests.id) resources",
72
+ "sum(lesli_audit_user_requests.request_count) requests"
73
+ )
74
+
75
+ user_requests = user_requests
76
+ .group(:user_id, group_by)
77
+
78
+ user_requests.map do |request|
79
+ request[:first_activity] = Date2.new(request[:first_activity]).time
80
+ request[:last_activity] = Date2.new(request[:last_activity]).time
81
+ request
82
+ end
83
+
84
+ user_requests.reverse
85
+ end
86
+
36
87
  def registrations
37
88
 
38
89
  #Get filters from the request
@@ -59,8 +110,8 @@ module LesliAudit
59
110
  .group(group_by)
60
111
  .count.map do |request|
61
112
  {
62
- :date => request[0],
63
- :count => request[1]
113
+ :xaxiskey => request[0],
114
+ :yaxiskey => request[1]
64
115
  }
65
116
  end
66
117
  end