dbxapp 4.1.3
CMS, Shop, Workflows und modulare Geschäftsanwendungen
Loading...
Searching...
No Matches
user_list.class.php
Go to the documentation of this file.
1<?php
2namespace dbx\dbxUser_admin;
3dbx()->use_system_class('dbxReport');
4
6 public function run_body($content) {
7 $this->_record = is_array($this->_record) ? $this->_record : array();
8 return $content;
9 }
10}
11
12Class user_list {
13
14 private $dd = 'dbxUser';
15 private $texts;
16
17 private function texts() {
18 if ($this->texts) {
19 return $this->texts;
20 }
21 $texts = new \dbxForm();
22 $texts->init('dbxUser_admin_texts');
23 $texts->_fd = 'dbxUser_admin|user-admin';
24 $texts->load_fd_messages();
25 $texts->set_form_help_enabled(false);
26 $this->texts = $texts;
27 return $this->texts;
28 }
29
30 private function base_url($run2, $params = array()) {
31 $url = '?dbx_modul=dbxUser_admin&dbx_run1=user&dbx_run2=' . rawurlencode((string) $run2);
32 foreach ($params as $key => $value) {
33 $url .= '&' . rawurlencode((string) $key) . '=' . rawurlencode((string) $value);
34 }
35 return $url;
36 }
37
38 private function request_json() {
39 $raw = file_get_contents('php://input');
40 $data = $raw ? json_decode($raw, true) : array();
41 return is_array($data) ? $data : array();
42 }
43
44 private function avatar_file($file) {
45 $file = trim((string) $file);
46 if ($file === '' || !preg_match('/^[A-Za-z0-9_.-]+\.(png|jpg|jpeg|webp|gif)$/i', $file)) {
47 return 'avatar-0.png';
48 }
49
50 $path = dbx()->get_base_dir() . 'dbx/modules/dbxUser/img/avatar/' . $file;
51 return is_file($path) ? $file : 'avatar-0.png';
52 }
53
54 private function status_label($status) {
55 $status = (string) $status;
56 if ($status === '1') return $this->texts()->get_fd_message('status_active');
57 if ($status === '2') return $this->texts()->get_fd_message('status_locked');
58 if ($status === '3') return $this->texts()->get_fd_message('status_archive');
59 return $this->texts()->get_fd_message('status_new');
60 }
61
62 private function user_row($row) {
63 $row = is_array($row) ? $row : array();
64 $avatar = $this->avatar_file($row['avatar'] ?? '');
65 $name = trim((string)($row['name'] ?? '') . ' ' . (string)($row['name2'] ?? ''));
66
67 $row['avatar'] = $avatar;
68 $row['avatar_img'] = dbx()->get_base_url() . 'dbx/modules/dbxUser/img/avatar/' . $avatar;
69 $row['display_name'] = $name !== '' ? $name : (string)($row['uname'] ?? '');
70 $row['status_label'] = $this->status_label($row['status'] ?? 0);
71 $row['profile_link'] = $this->base_url('edit_profil', array('rid' => (int)($row['id'] ?? 0)));
72
73 return $row;
74 }
75
76 private function allowed_grid_fields() {
77 return array(
78 'uname', 'name', 'name2', 'email', 'roles', 'status', 'language',
79 'telefon', 'handy', 'strasse', 'plz', 'ort', 'land', 'BSNR', 'LANR',
80 'emailbill', 'is_confirm', 'login_pid', 'logout_pid', 'design', 'color'
81 );
82 }
83
84 private function normalize_grid_row($row, $is_new = false) {
85 $allowed = array_flip($this->allowed_grid_fields());
86 $out = array();
87
88 foreach ((array) $row as $key => $value) {
89 if (!isset($allowed[$key])) {
90 continue;
91 }
92 if (is_array($value)) {
93 $value = implode(',', $value);
94 }
95 $out[$key] = trim((string) $value);
96 }
97
98 foreach (array('status', 'is_confirm') as $intField) {
99 if (isset($out[$intField])) {
100 $out[$intField] = (int) $out[$intField];
101 }
102 }
103
104 if ($is_new) {
105 if (empty($out['uname'])) {
106 $out['uname'] = 'neuer.benutzer.' . date('YmdHis');
107 }
108 if (empty($out['status'])) {
109 $out['status'] = 1;
110 }
111 if (empty($out['language'])) {
112 $out['language'] = 'de';
113 }
114 if (empty($out['name'])) {
115 $out['name'] = 'Neuer';
116 }
117 if (empty($out['name2'])) {
118 $out['name2'] = 'Benutzer';
119 }
120 $out['pass'] = md5(bin2hex(random_bytes(8)));
121 }
122
123 return $out;
124 }
125
126 private function grid_cols() {
127 $texts = $this->texts();
128 $statusValues = '0=' . $texts->get_fd_message('status_new')
129 . '~1=' . $texts->get_fd_message('status_active')
130 . '~2=' . $texts->get_fd_message('status_locked')
131 . '~3=' . $texts->get_fd_message('status_archive');
132 $languageValues = 'de=' . $texts->get_fd_message('language_de')
133 . '~en=' . $texts->get_fd_message('language_en')
134 . '~es=' . $texts->get_fd_message('language_es');
135 $confirmValues = '0=' . $texts->get_fd_message('no')
136 . '~1=' . $texts->get_fd_message('yes');
137 return implode(',', array(
138 'id[' . $texts->get_fd_message('label_id') . ']:number:p:width=72;hozAlign=center;headerHozAlign=center',
139 'avatar_img[' . $texts->get_fd_message('label_avatar') . ']:image:p:width=78;imgWidth=38px;imgHeight=38px',
140 'uname[' . $texts->get_fd_message('label_login') . ']:text::width=160',
141 'display_name[' . $texts->get_fd_message('label_name') . ']:text:p:width=210',
142 'name[' . $texts->get_fd_message('label_first_name') . ']:text::width=150',
143 'name2[' . $texts->get_fd_message('label_last_name') . ']:text::width=150',
144 'email[' . $texts->get_fd_message('label_email') . ']:text::width=230',
145 'roles[' . $texts->get_fd_message('label_groups') . ']:text::width=180',
146 'status[' . $texts->get_fd_message('label_status') . ']:text::editor=list;values=' . $statusValues . ';width=110',
147 'language[' . $texts->get_fd_message('label_language') . ']:text::editor=list;values=' . $languageValues . ';width=105',
148 'telefon[' . $texts->get_fd_message('label_phone') . ']:text::width=140',
149 'handy[' . $texts->get_fd_message('label_mobile') . ']:text::width=140',
150 'plz[' . $texts->get_fd_message('label_zip') . ']:text::width=90',
151 'ort[' . $texts->get_fd_message('label_city') . ']:text::width=150',
152 'lastvisit[' . $texts->get_fd_message('label_last_login') . ']:text:p:width=170',
153 'is_confirm[' . $texts->get_fd_message('label_confirmed_short') . ']:text::editor=list;values=' . $confirmValues . ';width=90'
154 ));
155 }
156
157 private function grid_read() {
158 $oDB = dbx()->get_system_obj('dbxDB');
159 $search = dbx()->get_request_var('dbx_search', '', 'sqlsearch|max=128');
160 $where = $oDB->build_search_where($this->dd, $search, array('uname', 'name', 'name2', 'email', 'roles', 'ort'), array('id'), 'contains');
161 $sort = dbx()->get_request_var('dbx_sorters', '', '*');
162 $rsort = 'id';
163 $rdesc = 'ASC';
164
165 if ($sort) {
166 $sorters = json_decode($sort, true);
167 if (is_array($sorters) && isset($sorters[0]['field'])) {
168 $field = (string) $sorters[0]['field'];
169 if (in_array($field, array('id', 'uname', 'name', 'name2', 'email', 'status', 'lastvisit'), true)) {
170 $rsort = $field;
171 $rdesc = strtolower((string)($sorters[0]['dir'] ?? 'asc')) === 'desc' ? 'DESC' : 'ASC';
172 }
173 }
174 }
175
176 $flds = array('id', 'uname', 'name', 'name2', 'email', 'roles', 'status', 'language', 'telefon', 'handy', 'plz', 'ort', 'lastvisit', 'is_confirm', 'avatar');
177 $rows = $oDB->select($this->dd, $where, $flds, $rsort, $rdesc, '', 1000, 0);
178 if (!is_array($rows)) {
179 $rows = array();
180 }
181
182 $out = array();
183 foreach ($rows as $row) {
184 $out[] = $this->user_row($row);
185 }
186
187 dbx()->json_response(array(
188 'ok' => 1,
189 'count' => count($out),
190 'rows' => $out,
191 'server_time' => date('Y-m-d H:i:s')
192 ));
193 }
194
195 private function grid_save() {
196 $oDB = dbx()->get_system_obj('dbxDB');
197 $payload = $this->request_json();
198 $rows = is_array($payload['rows'] ?? null) ? $payload['rows'] : array();
199 $saved = array();
200
201 foreach ($rows as $row) {
202 $id = (int)($row['id'] ?? 0);
203 if ($id <= 0) {
204 continue;
205 }
206 $data = $this->normalize_grid_row($row);
207 if (!$data) {
208 continue;
209 }
210 $ok = $oDB->update($this->dd, $data, $id);
211 if ($ok >= 0) {
212 $saved[] = $this->user_row($oDB->select1($this->dd, $id));
213 }
214 }
215
216 dbx()->json_response(array('ok' => 1, 'success' => true, 'rows' => $saved));
217 }
218
219 private function grid_insert() {
220 $oDB = dbx()->get_system_obj('dbxDB');
221 $data = $this->normalize_grid_row(array(), true);
222 $id = ($oDB->insert($this->dd, $data) === 1) ? $oDB->get_insert_id() : 0;
223
224 if ($id > 0) {
225 $row = $oDB->select1($this->dd, $id);
226 dbx()->json_response(array('ok' => 1, 'success' => true, 'row' => $this->user_row($row)));
227 }
228
229 dbx()->json_response(array('ok' => 0, 'success' => false, 'msg' => $this->texts()->get_fd_message('user_create_error')));
230 }
231
232 private function grid_delete() {
233 $payload = $this->request_json();
234 $id = (int)($payload['id'] ?? 0);
235 if ($id <= 0) {
236 dbx()->json_response(array('ok' => 0, 'success' => false, 'msg' => $this->texts()->get_fd_message('id_missing')));
237 }
238
239 $oDB = dbx()->get_system_obj('dbxDB');
240 $ok = $oDB->delete($this->dd, $id);
241 dbx()->json_response(array('ok' => $ok ? 1 : 0, 'success' => $ok ? true : false));
242 }
243
244 public function edit($rid=0) {
245 $obj=dbx()->get_include_obj('dbxUser_view');
246 $content=$obj->run();
247 return $content;
248 }
249
250 public function list() {
251 $texts = $this->texts();
252 $oReport = dbx()->get_system_obj('dbxReport');
253 $oDB = dbx()->get_system_obj('dbxDB');
254 $all = $oDB->count($this->dd);
255 $active = $oDB->count($this->dd, 'status = 1');
256 $locked = $oDB->count($this->dd, 'status = 2');
257
258 $oReport->init('report-user-grid', 'user-admin-grid');
259 $oReport->_fd = 'dbxUser_admin|user-admin';
260 $oReport->load_fd_messages();
261 $oReport->set_form_help_enabled(false);
262 $oReport->add_rep('shell_panel_class', 'dbx-grid dbx-user-admin dbx-ajax-root');
263 $oReport->add_rep('bar_title', $texts->get_fd_message('users_title'));
264 $oReport->add_rep('bar_subtitle', $texts->get_fd_message('users_subtitle'));
265 $oReport->_mode = 'tabulurator';
266 $oReport->_rrows = 620;
267 $oReport->_grid_id = 'dbx_user_admin_grid';
268 $oReport->_grid_cols = $this->grid_cols();
269 $oReport->_grid_layout = 'fitDataStretch';
270 $oReport->_grid_read_url = $this->base_url('user_grid_read');
271 $oReport->_grid_save_url = $this->base_url('user_grid_save');
272 $oReport->_grid_insert_url = $this->base_url('user_grid_insert');
273 $oReport->_grid_delete_url = $this->base_url('user_grid_delete');
274 $oReport->add_grid_stats(array(
275 array('label' => $texts->get_fd_message('stats_total'), 'value' => (string)$all),
276 array('label' => $texts->get_fd_message('status_active'), 'value' => (string)$active, 'tone' => 'ok'),
277 array('label' => $texts->get_fd_message('status_locked'), 'value' => (string)$locked, 'tone' => 'lock'),
278 ), $texts->get_fd_message('users_stats'));
279 $oReport->add_obj('new_user_url', 'obj-value', $this->base_url('new_user'));
280 $oReport->add_obj('groups_url', 'obj-value', $this->base_url('list_groups'));
281 $oReport->add_obj('bar_actions', 'obj-value',
282 '<a class="btn btn-primary btn-sm dbx-win" href="' . dbx()->esc($this->base_url('new_user')) . '" data-url="' . dbx()->esc($this->base_url('new_user')) . '" data-title="' . dbx()->esc($texts->get_fd_message('profile_title')) . '" title="' . dbx()->esc($texts->get_fd_message('action_new_user')) . '"><i class="bi bi-person-plus"></i></a>'
283 . '<a class="btn btn-outline-secondary btn-sm" href="' . dbx()->esc($this->base_url('list_groups')) . '" title="' . dbx()->esc($texts->get_fd_message('action_manage_groups')) . '"><i class="bi bi-people"></i></a>'
284 );
285
286 return $oReport->run();
287 }
288
289 public function run() {
290 $work = dbx()->get_modul_var('dbx_run2', 'list_user', 'parameter');
291 $content = '';
292
293 switch ($work) {
294 case 'user_grid_read':
295 $this->grid_read();
296 break;
297 case 'user_grid_save':
298 $this->grid_save();
299 break;
300 case 'user_grid_insert':
301 $this->grid_insert();
302 break;
303 case 'user_grid_delete':
304 $this->grid_delete();
305 break;
306 default:
307 $content=$this->list();
308 break;
309 }
310
311 return $content;
312 }
313}
314
315?>
dbx()
Liefert die zentrale dbXapp-API als Singleton.
Definition dbxApi.php:2805
esc($value)
Escaped einen Wert fuer HTML-Text und HTML-Attribute.
Definition dbxApi.php:2310
DBX schema administration.