itsm-widget 1.0.4 → 1.0.6
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.
- package/ANGULAR-INSTALLATION.md +303 -115
- package/API-SERVICE.md +130 -6
- package/README.md +104 -14
- package/dist/itsm-widget-config.json +1 -1
- package/dist/itsm-widget.min.css +1 -1
- package/dist/itsm-widget.min.js +1 -1
- package/package.json +1 -1
package/API-SERVICE.md
CHANGED
|
@@ -31,16 +31,18 @@ const ITSMAPIService = window.ITSMAPIService;
|
|
|
31
31
|
|
|
32
32
|
```javascript
|
|
33
33
|
const apiService = new ITSMAPIService({
|
|
34
|
-
baseUrl
|
|
34
|
+
// baseUrl sẽ được load tự động từ file itsm-widget-config.json
|
|
35
35
|
authToken: 'your-jwt-token-here' // JWT token từ đăng nhập thành công
|
|
36
36
|
});
|
|
37
37
|
```
|
|
38
38
|
|
|
39
|
+
**⚠️ QUAN TRỌNG:** `baseUrl` **CHỈ** được lấy từ file `itsm-widget-config.json` - đây là cách duy nhất để cấu hình URL của Backend API. Xem [CONFIG.md](./CONFIG.md) để biết thêm chi tiết.
|
|
40
|
+
|
|
39
41
|
### Options
|
|
40
42
|
|
|
41
43
|
| Option | Type | Default | Mô tả |
|
|
42
44
|
|--------|------|---------|-------|
|
|
43
|
-
| `baseUrl` | string | `''` | Base URL của Backend API (bắt buộc).
|
|
45
|
+
| `baseUrl` | string | `''` | **KHÔNG truyền vào constructor** - Base URL của Backend API được load tự động từ file `itsm-widget-config.json` (bắt buộc). |
|
|
44
46
|
| `authToken` | string | `''` | Authorization Bearer token (JWT token từ đăng nhập thành công) (bắt buộc). Đây KHÔNG phải là apiKey. |
|
|
45
47
|
|
|
46
48
|
## Methods
|
|
@@ -177,7 +179,72 @@ const requestInfo = await apiService.getRequest('18391');
|
|
|
177
179
|
console.log(requestInfo);
|
|
178
180
|
```
|
|
179
181
|
|
|
180
|
-
### 5.
|
|
182
|
+
### 5. getAllCategories()
|
|
183
|
+
|
|
184
|
+
Lấy tất cả categories từ Backend API.
|
|
185
|
+
|
|
186
|
+
**Returns:** `Promise<Object>` - Response với format:
|
|
187
|
+
```json
|
|
188
|
+
{
|
|
189
|
+
"categories": [...],
|
|
190
|
+
"list_info": {...},
|
|
191
|
+
"response_status": [...]
|
|
192
|
+
}
|
|
193
|
+
```
|
|
194
|
+
|
|
195
|
+
**Ví dụ:**
|
|
196
|
+
```javascript
|
|
197
|
+
const categoriesData = await apiService.getAllCategories();
|
|
198
|
+
console.log('Categories:', categoriesData.categories);
|
|
199
|
+
```
|
|
200
|
+
|
|
201
|
+
### 6. getSubcategoriesByCategoryId(categoryId)
|
|
202
|
+
|
|
203
|
+
Lấy danh sách subcategories theo category ID.
|
|
204
|
+
|
|
205
|
+
**Parameters:**
|
|
206
|
+
- `categoryId` (string): ID của category
|
|
207
|
+
|
|
208
|
+
**Returns:** `Promise<Object>` - Response với format:
|
|
209
|
+
```json
|
|
210
|
+
{
|
|
211
|
+
"subcategories": [...],
|
|
212
|
+
"list_info": {...},
|
|
213
|
+
"response_status": [...]
|
|
214
|
+
}
|
|
215
|
+
```
|
|
216
|
+
|
|
217
|
+
**Ví dụ:**
|
|
218
|
+
```javascript
|
|
219
|
+
const subcategoriesData = await apiService.getSubcategoriesByCategoryId('301');
|
|
220
|
+
console.log('Subcategories:', subcategoriesData.subcategories);
|
|
221
|
+
```
|
|
222
|
+
|
|
223
|
+
### 7. getItemsBySubcategoryId(subcategoryId)
|
|
224
|
+
|
|
225
|
+
Lấy danh sách items theo subcategory ID.
|
|
226
|
+
|
|
227
|
+
**Parameters:**
|
|
228
|
+
- `subcategoryId` (string): ID của subcategory
|
|
229
|
+
|
|
230
|
+
**Returns:** `Promise<Object>` - Response với format:
|
|
231
|
+
```json
|
|
232
|
+
{
|
|
233
|
+
"items": [...],
|
|
234
|
+
"list_info": {...},
|
|
235
|
+
"response_status": [...]
|
|
236
|
+
}
|
|
237
|
+
```
|
|
238
|
+
|
|
239
|
+
**Ví dụ:**
|
|
240
|
+
```javascript
|
|
241
|
+
const itemsData = await apiService.getItemsBySubcategoryId('302');
|
|
242
|
+
console.log('Items:', itemsData.items);
|
|
243
|
+
```
|
|
244
|
+
|
|
245
|
+
### 8. mapPriority(priority)
|
|
246
|
+
|
|
247
|
+
### 8. mapPriority(priority)
|
|
181
248
|
|
|
182
249
|
Helper method để map priority từ form widget sang format API.
|
|
183
250
|
|
|
@@ -191,7 +258,7 @@ Helper method để map priority từ form widget sang format API.
|
|
|
191
258
|
const priority = apiService.mapPriority('high'); // Trả về: 'Cao'
|
|
192
259
|
```
|
|
193
260
|
|
|
194
|
-
###
|
|
261
|
+
### 9. mapCategory(category)
|
|
195
262
|
|
|
196
263
|
Helper method để map category từ form widget sang format API.
|
|
197
264
|
|
|
@@ -206,7 +273,7 @@ const category = apiService.mapCategory('hardware');
|
|
|
206
273
|
// Trả về: 'A01A00 - Quản lý an toàn thông tin'
|
|
207
274
|
```
|
|
208
275
|
|
|
209
|
-
###
|
|
276
|
+
### 10. buildRequestData(formData, options)
|
|
210
277
|
|
|
211
278
|
Build request data từ form data của widget sang format API.
|
|
212
279
|
|
|
@@ -346,7 +413,64 @@ try {
|
|
|
346
413
|
}
|
|
347
414
|
```
|
|
348
415
|
|
|
349
|
-
|
|
416
|
+
### 4. Get All Categories
|
|
417
|
+
- **URL:** `POST {baseUrl}/spcit/categories`
|
|
418
|
+
- **Headers:**
|
|
419
|
+
- `Authorization`: `Bearer {authToken}`
|
|
420
|
+
- `Content-Type`: `application/json`
|
|
421
|
+
- **Body:** JSON với `list_info`:
|
|
422
|
+
```json
|
|
423
|
+
{
|
|
424
|
+
"list_info": {
|
|
425
|
+
"start_index": 1,
|
|
426
|
+
"page": 1,
|
|
427
|
+
"row_count": 100,
|
|
428
|
+
"sort_field": "name",
|
|
429
|
+
"sort_order": "asc",
|
|
430
|
+
"get_total_count": true
|
|
431
|
+
}
|
|
432
|
+
}
|
|
433
|
+
```
|
|
434
|
+
|
|
435
|
+
### 5. Get Subcategories by Category ID
|
|
436
|
+
- **URL:** `POST {baseUrl}/spcit/categories/{categoryId}/subcategories`
|
|
437
|
+
- **Headers:**
|
|
438
|
+
- `Authorization`: `Bearer {authToken}`
|
|
439
|
+
- `Content-Type`: `application/json`
|
|
440
|
+
- **Body:** JSON với `list_info`:
|
|
441
|
+
```json
|
|
442
|
+
{
|
|
443
|
+
"list_info": {
|
|
444
|
+
"start_index": 0,
|
|
445
|
+
"row_count": 100,
|
|
446
|
+
"sort_field": "name",
|
|
447
|
+
"sort_order": "asc",
|
|
448
|
+
"get_total_count": true
|
|
449
|
+
}
|
|
450
|
+
}
|
|
451
|
+
```
|
|
452
|
+
|
|
453
|
+
### 6. Get Items by Subcategory ID
|
|
454
|
+
- **URL:** `POST {baseUrl}/spcit/subcategories/{subcategoryId}/items`
|
|
455
|
+
- **Headers:**
|
|
456
|
+
- `Authorization`: `Bearer {authToken}`
|
|
457
|
+
- `Content-Type`: `application/json`
|
|
458
|
+
- **Body:** JSON với `list_info`:
|
|
459
|
+
```json
|
|
460
|
+
{
|
|
461
|
+
"list_info": {
|
|
462
|
+
"start_index": 0,
|
|
463
|
+
"row_count": 100,
|
|
464
|
+
"sort_field": "name",
|
|
465
|
+
"sort_order": "asc",
|
|
466
|
+
"get_total_count": true
|
|
467
|
+
}
|
|
468
|
+
}
|
|
469
|
+
```
|
|
470
|
+
|
|
471
|
+
**Lưu ý:**
|
|
472
|
+
- `apiKey` (authtoken) và `tenant` được xử lý ở Backend, không cần truyền từ Frontend.
|
|
473
|
+
- `{baseUrl}` được load từ file `itsm-widget-config.json`, không truyền vào constructor.
|
|
350
474
|
|
|
351
475
|
## Xem thêm
|
|
352
476
|
|
package/README.md
CHANGED
|
@@ -18,9 +18,13 @@ Plugin HTML **standalone** để Tạo phiếu yêu cầu ITSM. Widget sử dụ
|
|
|
18
18
|
- 🎯 Icon nổi ở góc dưới bên phải màn hình
|
|
19
19
|
- 📝 Form nhập phiếu yêu cầu ITSM với các trường:
|
|
20
20
|
- Tiêu đề (bắt buộc)
|
|
21
|
-
- Mô tả (bắt buộc)
|
|
22
|
-
- Danh mục
|
|
23
|
-
-
|
|
21
|
+
- Mô tả (bắt buộc) - Rich text editor với formatting
|
|
22
|
+
- Danh mục dịch vụ (tải từ API, có filter tìm kiếm)
|
|
23
|
+
- Dịch vụ con (tải từ API theo danh mục, có filter tìm kiếm)
|
|
24
|
+
- Chi tiết dịch vụ (tải từ API theo dịch vụ con, có filter tìm kiếm)
|
|
25
|
+
- Mức độ ưu tiên (Thấp, Trung bình, Cao)
|
|
26
|
+
- Loại hỗ trợ (dropdown)
|
|
27
|
+
- Loại thiết bị sử dụng (dropdown)
|
|
24
28
|
- Thông tin liên hệ
|
|
25
29
|
- Tệp đính kèm (nhiều file)
|
|
26
30
|
- 🎨 Giao diện native HTML/CSS đẹp mắt
|
|
@@ -87,7 +91,7 @@ import 'itsm-widget/dist/itsm-widget.min.js';
|
|
|
87
91
|
<script>
|
|
88
92
|
// Cấu hình widget
|
|
89
93
|
const itsmWidget = new ITSMWidget({
|
|
90
|
-
|
|
94
|
+
// apiBaseUrl sẽ được load tự động từ file itsm-widget-config.json
|
|
91
95
|
authToken: 'your-jwt-token-here', // JWT token từ đăng nhập thành công
|
|
92
96
|
position: 'bottom-right',
|
|
93
97
|
iconText: '📝',
|
|
@@ -152,7 +156,7 @@ export class AppComponent implements OnInit {
|
|
|
152
156
|
ngOnInit() {
|
|
153
157
|
// Khởi tạo ITSM Widget
|
|
154
158
|
const itsmWidget = new ITSMWidget({
|
|
155
|
-
|
|
159
|
+
// apiBaseUrl sẽ được load tự động từ file itsm-widget-config.json
|
|
156
160
|
authToken: 'your-jwt-token-here', // JWT token từ đăng nhập thành công
|
|
157
161
|
position: 'bottom-right',
|
|
158
162
|
iconText: '📝',
|
|
@@ -173,9 +177,14 @@ export class AppComponent implements OnInit {
|
|
|
173
177
|
### Cách 4: Auto-initialize với data attributes
|
|
174
178
|
|
|
175
179
|
```html
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
180
|
+
<!-- Không khuyến nghị dùng data attributes vì apiBaseUrl phải lấy từ itsm-widget-config.json -->
|
|
181
|
+
<script src="path/to/itsm-widget.min.js"></script>
|
|
182
|
+
<script>
|
|
183
|
+
const widget = new ITSMWidget({
|
|
184
|
+
// apiBaseUrl sẽ được load tự động từ file itsm-widget-config.json
|
|
185
|
+
authToken: 'your-jwt-token',
|
|
186
|
+
iconColor: '#007bff'
|
|
187
|
+
});
|
|
179
188
|
</script>
|
|
180
189
|
```
|
|
181
190
|
|
|
@@ -183,15 +192,20 @@ export class AppComponent implements OnInit {
|
|
|
183
192
|
|
|
184
193
|
> **📖 Xem chi tiết**: [CONFIG.md](./CONFIG.md) - Hướng dẫn cấu hình `apiBaseUrl` qua file external
|
|
185
194
|
|
|
186
|
-
|
|
195
|
+
**⚠️ QUAN TRỌNG:** `apiBaseUrl` **CHỈ** được lấy từ file `itsm-widget-config.json` - đây là cách duy nhất để cấu hình URL của Backend API.
|
|
196
|
+
|
|
197
|
+
Widget **BẮT BUỘC** phải có file `itsm-widget-config.json` để hoạt động. Đặt file config cùng thư mục với `itsm-widget.min.js`:
|
|
187
198
|
|
|
188
199
|
```json
|
|
189
200
|
{
|
|
190
|
-
"apiBaseUrl": "http://localhost:
|
|
201
|
+
"apiBaseUrl": "http://localhost:2411"
|
|
191
202
|
}
|
|
192
203
|
```
|
|
193
204
|
|
|
194
|
-
|
|
205
|
+
**Lưu ý:**
|
|
206
|
+
- Widget sẽ tự động load config từ file này khi khởi tạo
|
|
207
|
+
- **KHÔNG** truyền `apiBaseUrl` trong constructor - nó sẽ bị bỏ qua
|
|
208
|
+
- Nếu file không tồn tại hoặc không có `apiBaseUrl`, widget sẽ throw error và không khởi tạo được
|
|
195
209
|
|
|
196
210
|
## Build từ source
|
|
197
211
|
|
|
@@ -240,7 +254,7 @@ Rebuild tự động khi có thay đổi (không có dev server)
|
|
|
240
254
|
|
|
241
255
|
| Option | Type | Default | Mô tả |
|
|
242
256
|
|--------|------|---------|-------|
|
|
243
|
-
| `apiBaseUrl` | string | `''` | Base URL của Backend API
|
|
257
|
+
| `apiBaseUrl` | string | `''` | **KHÔNG truyền vào constructor** - Base URL của Backend API được load tự động từ file `itsm-widget-config.json` (bắt buộc). Xem [CONFIG.md](./CONFIG.md) để biết thêm chi tiết. |
|
|
244
258
|
| `authToken` | string | `''` | Authorization Bearer token (JWT token từ đăng nhập thành công) (bắt buộc). Đây KHÔNG phải là apiKey. |
|
|
245
259
|
| `position` | string | `'bottom-right'` | Vị trí icon: `'bottom-right'` hoặc `'bottom-left'` |
|
|
246
260
|
| `iconText` | string | `'📝'` | Text/emoji hiển thị trên icon (mặc định: 📝) |
|
|
@@ -278,6 +292,8 @@ Content-Type: application/json
|
|
|
278
292
|
"request": {
|
|
279
293
|
"requester": { "name": "..." },
|
|
280
294
|
"category": { "name": "..." },
|
|
295
|
+
"subcategory": { "name": "..." },
|
|
296
|
+
"item": { "name": "..." },
|
|
281
297
|
"priority": { "name": "..." },
|
|
282
298
|
"subject": "...",
|
|
283
299
|
"description": "...",
|
|
@@ -300,6 +316,79 @@ Content-Type: multipart/form-data
|
|
|
300
316
|
**Body (FormData):**
|
|
301
317
|
- `files`: File hoặc mảng các file
|
|
302
318
|
|
|
319
|
+
**3. Lấy danh sách categories:**
|
|
320
|
+
```
|
|
321
|
+
POST {apiBaseUrl}/spcit/categories
|
|
322
|
+
```
|
|
323
|
+
|
|
324
|
+
**Headers:**
|
|
325
|
+
```
|
|
326
|
+
Authorization: Bearer {authToken}
|
|
327
|
+
Content-Type: application/json
|
|
328
|
+
```
|
|
329
|
+
|
|
330
|
+
**Body (JSON):**
|
|
331
|
+
```json
|
|
332
|
+
{
|
|
333
|
+
"list_info": {
|
|
334
|
+
"start_index": 1,
|
|
335
|
+
"page": 1,
|
|
336
|
+
"row_count": 100,
|
|
337
|
+
"sort_field": "name",
|
|
338
|
+
"sort_order": "asc",
|
|
339
|
+
"get_total_count": true
|
|
340
|
+
}
|
|
341
|
+
}
|
|
342
|
+
```
|
|
343
|
+
|
|
344
|
+
**4. Lấy danh sách subcategories theo category:**
|
|
345
|
+
```
|
|
346
|
+
POST {apiBaseUrl}/spcit/categories/{categoryId}/subcategories
|
|
347
|
+
```
|
|
348
|
+
|
|
349
|
+
**Headers:**
|
|
350
|
+
```
|
|
351
|
+
Authorization: Bearer {authToken}
|
|
352
|
+
Content-Type: application/json
|
|
353
|
+
```
|
|
354
|
+
|
|
355
|
+
**Body (JSON):**
|
|
356
|
+
```json
|
|
357
|
+
{
|
|
358
|
+
"list_info": {
|
|
359
|
+
"start_index": 0,
|
|
360
|
+
"row_count": 100,
|
|
361
|
+
"sort_field": "name",
|
|
362
|
+
"sort_order": "asc",
|
|
363
|
+
"get_total_count": true
|
|
364
|
+
}
|
|
365
|
+
}
|
|
366
|
+
```
|
|
367
|
+
|
|
368
|
+
**5. Lấy danh sách items theo subcategory:**
|
|
369
|
+
```
|
|
370
|
+
POST {apiBaseUrl}/spcit/subcategories/{subcategoryId}/items
|
|
371
|
+
```
|
|
372
|
+
|
|
373
|
+
**Headers:**
|
|
374
|
+
```
|
|
375
|
+
Authorization: Bearer {authToken}
|
|
376
|
+
Content-Type: application/json
|
|
377
|
+
```
|
|
378
|
+
|
|
379
|
+
**Body (JSON):**
|
|
380
|
+
```json
|
|
381
|
+
{
|
|
382
|
+
"list_info": {
|
|
383
|
+
"start_index": 0,
|
|
384
|
+
"row_count": 100,
|
|
385
|
+
"sort_field": "name",
|
|
386
|
+
"sort_order": "asc",
|
|
387
|
+
"get_total_count": true
|
|
388
|
+
}
|
|
389
|
+
}
|
|
390
|
+
```
|
|
391
|
+
|
|
303
392
|
**Response mẫu (tạo request thành công):**
|
|
304
393
|
```json
|
|
305
394
|
{
|
|
@@ -335,7 +424,7 @@ Xem chi tiết API tại file tài liệu trong `src/assets/13082025 API v2 SDP
|
|
|
335
424
|
|
|
336
425
|
```javascript
|
|
337
426
|
const widget = new ITSMWidget({
|
|
338
|
-
|
|
427
|
+
// apiBaseUrl sẽ được load tự động từ file itsm-widget-config.json
|
|
339
428
|
authToken: 'your-jwt-token-here', // JWT token từ đăng nhập thành công
|
|
340
429
|
iconColor: '#28a745',
|
|
341
430
|
requesterName: 'Nguyễn Văn A', // Optional
|
|
@@ -350,7 +439,8 @@ const widget = new ITSMWidget({
|
|
|
350
439
|
**Lưu ý:**
|
|
351
440
|
- `apiKey` và `tenant` đã được config ở Backend (không cần truyền từ FE)
|
|
352
441
|
- `authToken` là JWT token từ đăng nhập, không phải `apiKey`
|
|
353
|
-
- `apiBaseUrl`
|
|
442
|
+
- `apiBaseUrl` **BẮT BUỘC** phải có trong file `itsm-widget-config.json` (xem [CONFIG.md](./CONFIG.md))
|
|
443
|
+
- **KHÔNG** truyền `apiBaseUrl` vào constructor - nó sẽ bị bỏ qua
|
|
354
444
|
|
|
355
445
|
### Custom styling
|
|
356
446
|
|
package/dist/itsm-widget.min.css
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
.itsm-widget-button{align-items:center;background-color:#fff;border:3px solid transparent;border-radius:50%;cursor:pointer;display:flex;justify-content:center;overflow:visible;padding:4px;position:fixed;transition:transform .3s ease,box-shadow .3s ease;z-index:9998}.itsm-widget-button:hover{box-shadow:0 4px 12px rgba(0,0,0,.15);transform:scale(1.1)}.itsm-position-bottom-right{bottom:24px;right:24px}.itsm-position-bottom-left{bottom:24px;left:24px}.itsm-widget-icon{align-items:center;background-color:#fff;border-radius:50%;color:#fff;display:flex;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica Neue,Arial,sans-serif;font-size:18px;font-weight:700;height:48px;justify-content:center;overflow:hidden;padding:8px;-webkit-user-select:none;-moz-user-select:none;user-select:none;width:48px}.itsm-widget-icon-img{filter:brightness(0) saturate(100%) invert(27%) sepia(78%) saturate(1250%) hue-rotate(197deg) brightness(96%) contrast(95%);height:100%;-o-object-fit:contain;object-fit:contain;width:100%}.itsm-modal-overlay{align-items:center;background-color:rgba(0,0,0,.5);bottom:0;display:none;justify-content:center;left:0;opacity:0;padding:16px;position:fixed;right:0;top:0;transition:opacity .3s ease;z-index:9999}.itsm-modal-overlay.itsm-modal-active{display:flex;opacity:1}.itsm-modal-container{background:#fff;border-radius:6px;box-shadow:0 11px 15px -7px rgba(0,0,0,.2),0 24px 38px 3px rgba(0,0,0,.14),0 9px 46px 8px rgba(0,0,0,.12);display:flex;flex-direction:column;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica Neue,Arial,sans-serif;max-height:90vh;max-width:50vw;transform:scale(.9);transition:transform .3s ease;width:100%}.itsm-modal-overlay.itsm-modal-active .itsm-modal-container{transform:scale(1)}.itsm-modal-header{align-items:center;background-color:#fff;border-bottom:1px solid #e9ecef;border-radius:6px 6px 0 0;display:flex;flex-shrink:0;justify-content:space-between;padding:1.5rem}.itsm-modal-title{color:#212529;flex:1;font-size:1.5rem;font-weight:600;margin:0}.itsm-modal-header-icons{align-items:center;display:flex;gap:.5rem}.itsm-modal-close{align-items:center;background:transparent;border:none;border-radius:50%;color:#6c757d;cursor:pointer;display:flex;font-size:1.5rem;height:2rem;justify-content:center;line-height:1;padding:.5rem;transition:background-color .2s ease,color .2s ease;width:2rem}.itsm-modal-close:hover{background-color:#e9ecef;color:#212529}.itsm-modal-close span{font-size:1.5rem;line-height:1}.itsm-modal-content{flex:1;overflow-y:auto;padding:1.5rem}.itsm-modal-footer{background-color:#fff;border-radius:0 0 6px 6px;border-top:1px solid #e9ecef;display:flex;flex-shrink:0;gap:.5rem;justify-content:flex-end;padding:1rem 1.5rem}.itsm-form{flex-direction:column}.itsm-form,.itsm-form-row{display:flex;gap:1rem}.itsm-form-group{display:flex;flex-direction:column;gap:.5rem}.itsm-form-group-half{flex:1}.itsm-form-group label{color:#495057;display:block;font-size:.875rem;font-weight:500;margin-bottom:.25rem}.itsm-required{color:#dc3545;margin-left:2px}.itsm-input{background-color:#fff;border:1px solid #ced4da;border-radius:4px;box-sizing:border-box;color:#495057;font-family:inherit;font-size:1rem;line-height:1.5;padding:.5rem .75rem;transition:background-color .2s,border-color .2s,box-shadow .2s;width:100%}.itsm-input:hover{border-color:#adb5bd}.itsm-input:focus{border-color:#007bff;box-shadow:0 0 0 .2rem rgba(0,123,255,.25);outline:0 none;outline-offset:0}.itsm-input:disabled{background-color:#e9ecef;cursor:not-allowed;opacity:1}.itsm-textarea{background-color:#fff;border:1px solid #ced4da;border-radius:4px;box-sizing:border-box;color:#495057;font-family:inherit;font-size:1rem;line-height:1.5;min-height:100px;padding:.5rem .75rem;resize:vertical;transition:background-color .2s,border-color .2s,box-shadow .2s;width:100%}.itsm-textarea:hover{border-color:#adb5bd}.itsm-textarea:focus{border-color:#007bff;box-shadow:0 0 0 .2rem rgba(0,123,255,.25);outline:0 none;outline-offset:0}.itsm-textarea:disabled{background-color:#e9ecef;cursor:not-allowed;opacity:1}.itsm-editor-container{background-color:#fff;border:1px solid #ced4da;border-radius:4px;transition:border-color .2s,box-shadow .2s}.itsm-editor-container:focus-within{border-color:#007bff;box-shadow:0 0 0 .2rem rgba(0,123,255,.25)}.itsm-editor-toolbar{align-items:center;background-color:#f8f9fa;border-bottom:1px solid #e9ecef;display:flex;flex-wrap:wrap;gap:.25rem;padding:.5rem}.itsm-editor-btn{align-items:center;background-color:#fff;border:1px solid #ced4da;border-radius:3px;color:#495057;cursor:pointer;display:inline-flex;font-family:inherit;font-size:.875rem;height:2rem;justify-content:center;min-width:2rem;padding:.25rem .5rem;transition:background-color .2s,border-color .2s}.itsm-editor-btn:hover{background-color:#e9ecef;border-color:#adb5bd}.itsm-editor-btn:active{background-color:#dee2e6}.itsm-editor-separator{background-color:#ced4da;height:1.5rem;margin:0 .25rem;width:1px}.itsm-editor-file-btn{align-items:center;background-color:#fff;border:1px solid #ced4da;border-radius:3px;color:#495057;cursor:pointer;display:inline-flex;font-family:inherit;font-size:.875rem;justify-content:center;margin-left:auto;padding:.25rem .5rem;transition:background-color .2s,border-color .2s}.itsm-editor-file-btn:hover{background-color:#e9ecef;border-color:#adb5bd}.itsm-editor-content{color:#495057;font-family:inherit;font-size:1rem;line-height:1.5;max-height:400px;min-height:150px;outline:none;overflow-y:auto;padding:.75rem}.itsm-editor-content:empty:before{color:#6c757d;content:attr(data-placeholder);pointer-events:none}.itsm-editor-content:focus:empty:before{content:""}.itsm-editor-content img{height:auto;margin:.5rem 0;max-width:100%}.itsm-editor-content ol,.itsm-editor-content ul{margin:.5rem 0;padding-left:1.5rem}.itsm-editor-content p{margin:.5rem 0}.itsm-editor-content p:first-child{margin-top:0}.itsm-editor-content p:last-child{margin-bottom:0}.itsm-select{background-color:#fff;border:1px solid #ced4da;border-radius:4px;box-sizing:border-box;color:#495057;cursor:pointer;font-family:inherit;font-size:1rem;line-height:1.5;padding:.5rem .75rem;transition:background-color .2s,border-color .2s,box-shadow .2s;width:100%}.itsm-select:hover{border-color:#adb5bd}.itsm-select:focus{border-color:#007bff;box-shadow:0 0 0 .2rem rgba(0,123,255,.25);outline:0 none;outline-offset:0}.itsm-select:disabled{background-color:#e9ecef;cursor:not-allowed;opacity:.6}.itsm-btn{align-items:center;border:1px solid transparent;border-radius:4px;cursor:pointer;display:inline-flex;font-family:inherit;font-size:1rem;font-weight:400;justify-content:center;line-height:1.5;overflow:hidden;padding:.5rem 1rem;position:relative;text-align:center;transition:background-color .2s,border-color .2s,box-shadow .2s;-webkit-user-select:none;-moz-user-select:none;user-select:none}.itsm-btn:disabled{cursor:default;opacity:.6}.itsm-btn-text{line-height:inherit}.itsm-btn-primary{background-color:#007bff;border-color:#007bff;color:#fff}.itsm-btn-primary:hover:not(:disabled){background-color:#0056b3;border-color:#0056b3}.itsm-btn-primary:focus{box-shadow:0 0 0 .2rem rgba(0,123,255,.5);outline:0 none;outline-offset:0}.itsm-btn-primary:active:not(:disabled){background-color:#004085;border-color:#004085}.itsm-btn-secondary{background-color:#6c757d;border-color:#6c757d;color:#fff}.itsm-btn-secondary:hover:not(:disabled){background-color:#5a6268;border-color:#545b62}.itsm-btn-secondary:focus{box-shadow:0 0 0 .2rem hsla(208,7%,46%,.5);outline:0 none;outline-offset:0}.itsm-btn-secondary:active:not(:disabled){background-color:#545b62;border-color:#4e555b}.itsm-file-list{display:flex;flex-direction:column;gap:.5rem;margin-top:.5rem}.itsm-file-item{align-items:center;background-color:#f8f9fa;border-radius:4px;display:flex;font-size:.875rem;justify-content:space-between;padding:.5rem}.itsm-file-name{color:#495057;flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.itsm-file-size{color:#6c757d;margin-left:.5rem}.itsm-message{border-radius:4px;box-shadow:0 4px 6px rgba(0,0,0,.1);font-family:inherit;font-size:.875rem;max-width:500px;min-width:300px;padding:1rem 1.5rem;position:fixed;right:20px;top:20px;transform:translateX(400px);transition:transform .3s ease;z-index:10000}.itsm-message.itsm-message-show{transform:translateX(0)}.itsm-message-success{background-color:#d4edda;border:1px solid #c3e6cb;color:#155724}.itsm-message-error{background-color:#f8d7da;border:1px solid #f5c6cb;color:#721c24}.itsm-message-info{background-color:#d1ecf1;border:1px solid #bee5eb;color:#0c5460}@media (max-width:768px){.itsm-modal-container{max-height:95vh;max-width:95%}.itsm-form-row{flex-direction:column}.itsm-form-group-half{flex:none}.itsm-modal-content,.itsm-modal-footer,.itsm-modal-header{padding:1rem}}
|
|
1
|
+
.itsm-widget-button{align-items:center;background-color:#fff;border:3px solid transparent;border-radius:50%;cursor:pointer;display:flex;justify-content:center;overflow:visible;padding:4px;position:fixed;transition:transform .3s ease,box-shadow .3s ease;z-index:9998}.itsm-widget-button:hover{box-shadow:0 4px 12px rgba(0,0,0,.15);transform:scale(1.1)}.itsm-position-bottom-right{bottom:24px;right:24px}.itsm-position-bottom-left{bottom:24px;left:24px}.itsm-widget-icon{align-items:center;background-color:#fff;border-radius:50%;color:#fff;display:flex;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica Neue,Arial,sans-serif;font-size:18px;font-weight:700;height:48px;justify-content:center;overflow:hidden;padding:8px;-webkit-user-select:none;-moz-user-select:none;user-select:none;width:48px}.itsm-widget-icon-img{filter:brightness(0) saturate(100%) invert(27%) sepia(78%) saturate(1250%) hue-rotate(197deg) brightness(96%) contrast(95%);height:100%;-o-object-fit:contain;object-fit:contain;width:100%}.itsm-modal-overlay{align-items:center;background-color:rgba(0,0,0,.5);bottom:0;display:none;justify-content:center;left:0;opacity:0;padding:16px;position:fixed;right:0;top:0;transition:opacity .3s ease;z-index:9999}.itsm-modal-overlay.itsm-modal-active{display:flex;opacity:1}.itsm-modal-container{background:#fff;border-radius:6px;box-shadow:0 11px 15px -7px rgba(0,0,0,.2),0 24px 38px 3px rgba(0,0,0,.14),0 9px 46px 8px rgba(0,0,0,.12);display:flex;flex-direction:column;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica Neue,Arial,sans-serif;max-height:90vh;max-width:50vw;transform:scale(.9);transition:transform .3s ease;width:100%}.itsm-modal-overlay.itsm-modal-active .itsm-modal-container{transform:scale(1)}.itsm-modal-header{align-items:center;background-color:#fff;border-bottom:1px solid #e9ecef;border-radius:6px 6px 0 0;display:flex;flex-shrink:0;justify-content:space-between;padding:1.5rem}.itsm-modal-title{color:#212529;flex:1;font-size:1.5rem;font-weight:600;margin:0}.itsm-modal-header-icons{align-items:center;display:flex;gap:.5rem}.itsm-modal-close{align-items:center;background:transparent;border:none;border-radius:50%;color:#6c757d;cursor:pointer;display:flex;font-size:1.5rem;height:2rem;justify-content:center;line-height:1;padding:.5rem;transition:background-color .2s ease,color .2s ease;width:2rem}.itsm-modal-close:hover{background-color:#e9ecef;color:#212529}.itsm-modal-close span{font-size:1.5rem;line-height:1}.itsm-modal-content{flex:1;overflow-y:auto;padding:1.5rem}.itsm-modal-footer{background-color:#fff;border-radius:0 0 6px 6px;border-top:1px solid #e9ecef;display:flex;flex-shrink:0;gap:.5rem;justify-content:flex-end;padding:1rem 1.5rem}.itsm-form{flex-direction:column}.itsm-form,.itsm-form-row{display:flex;gap:1rem}.itsm-form-group{display:flex;flex-direction:column;gap:.5rem}.itsm-form-group-half{flex:1}.itsm-form-group label{color:#495057;display:block;font-size:.875rem;font-weight:500;margin-bottom:.25rem}.itsm-required{color:#dc3545;margin-left:2px}.itsm-input{background-color:#fff;border:1px solid #ced4da;border-radius:4px;box-sizing:border-box;color:#495057;font-family:inherit;font-size:1rem;line-height:1.5;padding:.5rem .75rem;transition:background-color .2s,border-color .2s,box-shadow .2s;width:100%}.itsm-input:hover{border-color:#adb5bd}.itsm-input:focus{border-color:#007bff;box-shadow:0 0 0 .2rem rgba(0,123,255,.25);outline:0 none;outline-offset:0}.itsm-input:disabled{background-color:#e9ecef;cursor:not-allowed;opacity:1}.itsm-textarea{background-color:#fff;border:1px solid #ced4da;border-radius:4px;box-sizing:border-box;color:#495057;font-family:inherit;font-size:1rem;line-height:1.5;min-height:100px;padding:.5rem .75rem;resize:vertical;transition:background-color .2s,border-color .2s,box-shadow .2s;width:100%}.itsm-textarea:hover{border-color:#adb5bd}.itsm-textarea:focus{border-color:#007bff;box-shadow:0 0 0 .2rem rgba(0,123,255,.25);outline:0 none;outline-offset:0}.itsm-textarea:disabled{background-color:#e9ecef;cursor:not-allowed;opacity:1}.itsm-editor-container{background-color:#fff;border:1px solid #ced4da;border-radius:4px;transition:border-color .2s,box-shadow .2s}.itsm-editor-container:focus-within{border-color:#007bff;box-shadow:0 0 0 .2rem rgba(0,123,255,.25)}.itsm-editor-toolbar{align-items:center;background-color:#f8f9fa;border-bottom:1px solid #e9ecef;display:flex;flex-wrap:wrap;gap:.25rem;padding:.5rem}.itsm-editor-btn{align-items:center;background-color:#fff;border:1px solid #ced4da;border-radius:3px;color:#495057;cursor:pointer;display:inline-flex;font-family:inherit;font-size:.875rem;height:2rem;justify-content:center;min-width:2rem;padding:.25rem .5rem;transition:background-color .2s,border-color .2s}.itsm-editor-btn:hover{background-color:#e9ecef;border-color:#adb5bd}.itsm-editor-btn:active{background-color:#dee2e6}.itsm-editor-separator{background-color:#ced4da;height:1.5rem;margin:0 .25rem;width:1px}.itsm-editor-file-btn{align-items:center;background-color:#fff;border:1px solid #ced4da;border-radius:3px;color:#495057;cursor:pointer;display:inline-flex;font-family:inherit;font-size:.875rem;justify-content:center;margin-left:auto;padding:.25rem .5rem;transition:background-color .2s,border-color .2s}.itsm-editor-file-btn:hover{background-color:#e9ecef;border-color:#adb5bd}.itsm-editor-content{color:#495057;font-family:inherit;font-size:1rem;line-height:1.5;max-height:400px;min-height:150px;outline:none;overflow-y:auto;padding:.75rem}.itsm-editor-content:empty:before{color:#6c757d;content:attr(data-placeholder);pointer-events:none}.itsm-editor-content:focus:empty:before{content:""}.itsm-editor-content img{height:auto;margin:.5rem 0;max-width:100%}.itsm-editor-content ol,.itsm-editor-content ul{margin:.5rem 0;padding-left:1.5rem}.itsm-editor-content p{margin:.5rem 0}.itsm-editor-content p:first-child{margin-top:0}.itsm-editor-content p:last-child{margin-bottom:0}.itsm-filter-input{background-color:#fff;border:1px solid #ced4da;border-bottom:none;border-radius:4px 4px 0 0;box-sizing:border-box;color:#495057;font-family:inherit;font-size:.875rem;line-height:1.5;margin-bottom:0;padding:.5rem .75rem;transition:background-color .2s,border-color .2s,box-shadow .2s;width:100%}.itsm-filter-input:hover{border-color:#adb5bd}.itsm-filter-input:focus{border-color:#007bff #007bff #ced4da;box-shadow:0 0 0 .2rem rgba(0,123,255,.25);outline:0 none;outline-offset:0}.itsm-filter-input:disabled{background-color:#e9ecef;cursor:not-allowed;opacity:1}.itsm-select{background-color:#fff;border:1px solid #ced4da;border-radius:4px;box-sizing:border-box;color:#495057;cursor:pointer;font-family:inherit;font-size:1rem;line-height:1.5;padding:.5rem .75rem;transition:background-color .2s,border-color .2s,box-shadow .2s;width:100%}.itsm-form-group:has(.itsm-filter-input) .itsm-select{border-radius:0 0 4px 4px;border-top:none}.itsm-select:hover{border-color:#adb5bd}.itsm-select:focus{border-color:#007bff;box-shadow:0 0 0 .2rem rgba(0,123,255,.25);outline:0 none;outline-offset:0}.itsm-select:disabled{background-color:#e9ecef;cursor:not-allowed;opacity:.6}.itsm-custom-select{position:relative;width:100%}.itsm-select-display{align-items:center;background-color:#fff;border:1px solid #ced4da;border-radius:4px;box-sizing:border-box;color:#495057;cursor:pointer;display:flex;font-family:inherit;font-size:1rem;justify-content:space-between;line-height:1.5;padding:.5rem .75rem;transition:background-color .2s,border-color .2s,box-shadow .2s;-webkit-user-select:none;-moz-user-select:none;user-select:none;width:100%}.itsm-select-display:hover:not(.disabled){border-color:#adb5bd}.itsm-select-display:focus{border-color:#007bff;box-shadow:0 0 0 .2rem rgba(0,123,255,.25);outline:0 none;outline-offset:0}.itsm-select-display.disabled{background-color:#e9ecef;cursor:not-allowed;opacity:.6}.itsm-select-text{flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.itsm-select-arrow{color:#6c757d;font-size:.75rem;margin-left:.5rem;transition:transform .2s}.itsm-custom-select[data-disabled=true] .itsm-select-arrow{opacity:.5}.itsm-select-dropdown{background-color:#fff;border:1px solid #ced4da;border-radius:4px;box-shadow:0 4px 6px rgba(0,0,0,.1);display:none;flex-direction:column;left:0;margin-top:.25rem;max-height:300px;overflow:hidden;position:absolute;right:0;top:100%;z-index:1000}.itsm-select-dropdown.open{display:flex}.itsm-select-filter{background-color:#fff;border:none;border-bottom:1px solid #e9ecef;box-sizing:border-box;color:#495057;font-family:inherit;font-size:.875rem;line-height:1.5;outline:none;padding:.5rem .75rem;width:100%}.itsm-select-filter:focus{border-bottom-color:#007bff}.itsm-select-filter:disabled{background-color:#f8f9fa;cursor:not-allowed}.itsm-select-options{max-height:250px;overflow-y:auto;padding:.25rem 0}.itsm-select-option{color:#495057;cursor:pointer;font-size:1rem;line-height:1.5;padding:.5rem .75rem;transition:background-color .15s;-webkit-user-select:none;-moz-user-select:none;user-select:none}.itsm-select-option:hover{background-color:#f8f9fa}.itsm-select-option:active{background-color:#e9ecef}.itsm-select-option[style*="display: none"]{display:none!important}.itsm-btn{align-items:center;border:1px solid transparent;border-radius:4px;cursor:pointer;display:inline-flex;font-family:inherit;font-size:1rem;font-weight:400;justify-content:center;line-height:1.5;overflow:hidden;padding:.5rem 1rem;position:relative;text-align:center;transition:background-color .2s,border-color .2s,box-shadow .2s;-webkit-user-select:none;-moz-user-select:none;user-select:none}.itsm-btn:disabled{cursor:default;opacity:.6}.itsm-btn-text{line-height:inherit}.itsm-btn-primary{background-color:#007bff;border-color:#007bff;color:#fff}.itsm-btn-primary:hover:not(:disabled){background-color:#0056b3;border-color:#0056b3}.itsm-btn-primary:focus{box-shadow:0 0 0 .2rem rgba(0,123,255,.5);outline:0 none;outline-offset:0}.itsm-btn-primary:active:not(:disabled){background-color:#004085;border-color:#004085}.itsm-btn-secondary{background-color:#6c757d;border-color:#6c757d;color:#fff}.itsm-btn-secondary:hover:not(:disabled){background-color:#5a6268;border-color:#545b62}.itsm-btn-secondary:focus{box-shadow:0 0 0 .2rem hsla(208,7%,46%,.5);outline:0 none;outline-offset:0}.itsm-btn-secondary:active:not(:disabled){background-color:#545b62;border-color:#4e555b}.itsm-file-list{display:flex;flex-direction:column;gap:.5rem;margin-top:.5rem}.itsm-file-item{align-items:center;background-color:#f8f9fa;border-radius:4px;display:flex;font-size:.875rem;justify-content:space-between;padding:.5rem}.itsm-file-name{color:#495057;flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.itsm-file-size{color:#6c757d;margin-left:.5rem}.itsm-message{border-radius:4px;box-shadow:0 4px 6px rgba(0,0,0,.1);font-family:inherit;font-size:.875rem;max-width:500px;min-width:300px;padding:1rem 1.5rem;position:fixed;right:20px;top:20px;transform:translateX(400px);transition:transform .3s ease;z-index:10000}.itsm-message.itsm-message-show{transform:translateX(0)}.itsm-message-success{background-color:#d4edda;border:1px solid #c3e6cb;color:#155724}.itsm-message-error{background-color:#f8d7da;border:1px solid #f5c6cb;color:#721c24}.itsm-message-info{background-color:#d1ecf1;border:1px solid #bee5eb;color:#0c5460}@media (max-width:768px){.itsm-modal-container{max-height:95vh;max-width:95%}.itsm-form-row{flex-direction:column}.itsm-form-group-half{flex:none}.itsm-modal-content,.itsm-modal-footer,.itsm-modal-header{padding:1rem}}
|