Code Coverage |
||||||||||
Lines |
Functions and Methods |
Classes and Traits |
||||||||
Total | |
100.00% |
94 / 94 |
|
100.00% |
7 / 7 |
CRAP | |
100.00% |
1 / 1 |
UserWorklogController | |
100.00% |
94 / 94 |
|
100.00% |
7 / 7 |
19 | |
100.00% |
1 / 1 |
__construct | |
100.00% |
1 / 1 |
|
100.00% |
1 / 1 |
1 | |||
editWorklog | |
100.00% |
15 / 15 |
|
100.00% |
1 / 1 |
3 | |||
saveWorklog | |
100.00% |
34 / 34 |
|
100.00% |
1 / 1 |
6 | |||
showDeleteWorklog | |
100.00% |
9 / 9 |
|
100.00% |
1 / 1 |
2 | |||
deleteWorklog | |
100.00% |
20 / 20 |
|
100.00% |
1 / 1 |
3 | |||
showEditWorklog | |
100.00% |
11 / 11 |
|
100.00% |
1 / 1 |
1 | |||
needsUser | |
100.00% |
4 / 4 |
|
100.00% |
1 / 1 |
3 |
1 | <?php |
2 | |
3 | declare(strict_types=1); |
4 | |
5 | namespace Engelsystem\Controllers\Admin; |
6 | |
7 | use Carbon\Carbon; |
8 | use Engelsystem\Config\Config; |
9 | use Engelsystem\Controllers\BaseController; |
10 | use Engelsystem\Controllers\HasUserNotifications; |
11 | use Engelsystem\Helpers\Authenticator; |
12 | use Engelsystem\Http\Exceptions\HttpForbidden; |
13 | use Engelsystem\Http\Exceptions\HttpNotFound; |
14 | use Engelsystem\Http\Redirector; |
15 | use Engelsystem\Http\Request; |
16 | use Engelsystem\Http\Response; |
17 | use Engelsystem\Models\User\User; |
18 | use Engelsystem\Models\Worklog; |
19 | use Psr\Log\LoggerInterface; |
20 | |
21 | class UserWorklogController extends BaseController |
22 | { |
23 | use HasUserNotifications; |
24 | |
25 | /** @var array<string> */ |
26 | protected array $permissions = [ |
27 | 'admin_user_worklog', |
28 | ]; |
29 | |
30 | public function __construct( |
31 | protected Authenticator $auth, |
32 | protected Config $config, |
33 | protected LoggerInterface $log, |
34 | protected Worklog $worklog, |
35 | protected Redirector $redirect, |
36 | protected Response $response, |
37 | protected User $user |
38 | ) { |
39 | } |
40 | |
41 | public function editWorklog(Request $request): Response |
42 | { |
43 | $user = $this->needsUser($request); |
44 | $worklogId = $request->getAttribute('worklog_id'); // optional |
45 | |
46 | if (isset($worklogId)) { |
47 | $worklog = $this->worklog->findOrFail((int) $worklogId); |
48 | |
49 | if ($worklog->user->id != $user->id) { |
50 | throw new HttpNotFound(); |
51 | } |
52 | return $this->showEditWorklog( |
53 | $user, |
54 | $worklog->worked_at, |
55 | $worklog->hours, |
56 | $worklog->description, |
57 | $worklog->night_shift, |
58 | true |
59 | ); |
60 | } else { |
61 | return $this->showEditWorklog($user, Carbon::today()); |
62 | } |
63 | } |
64 | |
65 | public function saveWorklog(Request $request): Response |
66 | { |
67 | $user = $this->needsUser($request); |
68 | $worklogId = $request->getAttribute('worklog_id'); // optional |
69 | |
70 | $data = $this->validate($request, [ |
71 | 'work_date' => 'required|date:Y-m-d', |
72 | 'work_hours' => 'float|min:0', |
73 | 'description' => 'required|max:200', |
74 | 'night_shift' => 'optional|checked', |
75 | ]); |
76 | |
77 | // Search / create worklog |
78 | if (isset($worklogId)) { |
79 | $worklog = $this->worklog->findOrFail((int) $worklogId); |
80 | |
81 | if ($worklog->user->id != $user->id) { |
82 | throw new HttpNotFound(); |
83 | } |
84 | } else { |
85 | $worklog = new Worklog(); |
86 | $worklog->user()->associate($user); |
87 | $worklog->creator()->associate($this->auth->user()); |
88 | } |
89 | $worklog->worked_at = $data['work_date']; |
90 | $worklog->hours = $data['work_hours']; |
91 | $worklog->description = $data['description']; |
92 | $worklog->night_shift = $data['night_shift'] ?: false; |
93 | $worklog->save(); |
94 | |
95 | $this->log->info( |
96 | 'Saved worklog ({wl_id}) for {name} ({id}) at {time} spanning {hours}h{night_shift}: {text}', |
97 | [ |
98 | 'wl_id' => $worklog->id, |
99 | 'name' => $user->name, |
100 | 'id' => $user->id, |
101 | 'time' => $worklog->worked_at, |
102 | 'hours' => $worklog->hours, |
103 | 'text' => $worklog->description, |
104 | 'night_shift' => $worklog->night_shift ? ' at night' : '', |
105 | ] |
106 | ); |
107 | $this->addNotification(isset($worklogId) ? 'worklog.edit.success' : 'worklog.add.success'); |
108 | |
109 | return $this->redirect->to('/users?action=view&user_id=' . $user->id); |
110 | // TODO Once User_view.php gets removed, change this to withView + getNotifications |
111 | } |
112 | |
113 | public function showDeleteWorklog(Request $request): Response |
114 | { |
115 | $user = $this->needsUser($request); |
116 | $worklogId = $request->getAttribute('worklog_id'); |
117 | $worklog = $this->worklog->findOrFail($worklogId); |
118 | |
119 | if ($worklog->user->id != $user->id) { |
120 | throw new HttpNotFound(); |
121 | } |
122 | |
123 | return $this->response->withView( |
124 | 'admin/user/delete-worklog.twig', |
125 | ['userdata' => $user] |
126 | ); |
127 | } |
128 | |
129 | public function deleteWorklog(Request $request): Response |
130 | { |
131 | $user = $this->needsUser($request); |
132 | $worklogId = $request->getAttribute('worklog_id'); |
133 | $worklog = $this->worklog->findOrFail($worklogId); |
134 | |
135 | if ($worklog->user->id != $user->id) { |
136 | throw new HttpNotFound(); |
137 | } |
138 | $worklog->delete(); |
139 | |
140 | $this->log->info( |
141 | 'Deleted worklog ({wl_id}) for {name} ({id}) at {time} spanning {hours}h{night_shift}: {text}', |
142 | [ |
143 | 'wl_id' => $worklog->id, |
144 | 'name' => $worklog->user->name, |
145 | 'id' => $worklog->user->id, |
146 | 'time' => $worklog->worked_at, |
147 | 'hours' => $worklog->hours, |
148 | 'text' => $worklog->description, |
149 | 'night_shift' => $worklog->night_shift ? ' at night' : '', |
150 | ] |
151 | ); |
152 | $this->addNotification('worklog.delete.success'); |
153 | |
154 | return $this->redirect->to('/users?action=view&user_id=' . $user->id); |
155 | // TODO Once User_view.php gets removed, change this to withView + getNotifications |
156 | } |
157 | |
158 | private function showEditWorklog( |
159 | User $user, |
160 | Carbon $work_date, |
161 | float $work_hours = 0, |
162 | string $description = '', |
163 | bool $night_shift = false, |
164 | bool $is_edit = false |
165 | ): Response { |
166 | return $this->response->withView( |
167 | 'admin/user/edit-worklog.twig', |
168 | [ |
169 | 'userdata' => $user, |
170 | 'work_date' => $work_date, |
171 | 'work_hours' => $work_hours, |
172 | 'description' => $description, |
173 | 'night_shift' => $night_shift, |
174 | 'is_edit' => $is_edit, |
175 | ] |
176 | ); |
177 | } |
178 | |
179 | private function needsUser(Request $request): User |
180 | { |
181 | $userId = (int) $request->getAttribute('user_id'); |
182 | if (!config('enable_self_worklog') && ($userId === $this->auth->user()->id)) { |
183 | throw new HttpForbidden(); |
184 | } |
185 | return $this->user->findOrFail($userId); |
186 | } |
187 | } |