@blueking/bk-user-selector 0.0.39-beta.3 → 0.1.1-beta.1
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/README.md +316 -88
- package/package.json +2 -2
- package/typings/api/user.d.ts +42 -21
- package/typings/components/me-tag.vue.d.ts +14 -35
- package/typings/components/selection-popover.vue.d.ts +48 -197
- package/typings/components/user-render.d.ts +20 -1
- package/typings/components/user-selector.vue.d.ts +23 -29
- package/typings/components/user-tag.vue.d.ts +16 -0
- package/typings/constants/index.d.ts +25 -0
- package/typings/hooks/use-current-user.d.ts +30 -0
- package/typings/hooks/use-focus-state.d.ts +48 -0
- package/typings/hooks/use-input-handler.d.ts +44 -0
- package/typings/hooks/use-resize-observer.d.ts +17 -0
- package/typings/hooks/use-selected-users.d.ts +78 -0
- package/typings/hooks/use-sortable.d.ts +41 -0
- package/typings/hooks/use-tenant-data.d.ts +17 -0
- package/typings/hooks/use-user-search.d.ts +38 -0
- package/typings/hooks/use-user-selection.d.ts +32 -0
- package/typings/hooks/use-visible-tags.d.ts +51 -0
- package/typings/types/index.d.ts +127 -98
- package/typings/utils/logger.d.ts +47 -0
- package/vue2/index.es.min.js +3308 -4631
- package/vue2/index.iife.min.js +4610 -5899
- package/vue2/index.umd.min.js +3300 -4623
- package/vue2/vue2.css +34 -81
- package/vue3/index.es.min.js +1393 -1597
- package/vue3/index.iife.min.js +3298 -4621
- package/vue3/index.umd.min.js +1392 -1596
- package/vue3/vue3.css +34 -67
package/vue3/index.es.min.js
CHANGED
|
@@ -1,586 +1,225 @@
|
|
|
1
|
-
import { unref, ref, onBeforeMount, defineComponent, openBlock, createElementBlock, normalizeClass, withModifiers, toDisplayString, createCommentVNode, h,
|
|
2
|
-
import { Popover, Loading, Tag,
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
};
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
1
|
+
import { unref, ref, watch, onUnmounted, onBeforeMount, computed, defineComponent, openBlock, createElementBlock, normalizeClass, withModifiers, toDisplayString, createCommentVNode, h, createBlock, withCtx, createElementVNode, createVNode, Fragment, renderList, renderSlot, toRef, nextTick, onMounted, withDirectives, mergeProps, isRef, normalizeStyle, vModelText, vShow, createTextVNode } from "vue";
|
|
2
|
+
import { Popover, Loading, Tag, provideGlobalConfig } from "bkui-vue";
|
|
3
|
+
var commonjsGlobal = typeof globalThis !== "undefined" ? globalThis : typeof window !== "undefined" ? window : typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : {};
|
|
4
|
+
function getDefaultExportFromCjs(x) {
|
|
5
|
+
return x && x.__esModule && Object.prototype.hasOwnProperty.call(x, "default") ? x["default"] : x;
|
|
6
|
+
}
|
|
7
|
+
var Sortable$1 = { exports: {} };
|
|
8
|
+
/**!
|
|
9
|
+
* Sortable 1.15.6
|
|
10
|
+
* @author RubaXa <trash@rubaxa.org>
|
|
11
|
+
* @author owenm <owen23355@gmail.com>
|
|
12
|
+
* @license MIT
|
|
13
|
+
*/
|
|
14
|
+
(function(module, exports) {
|
|
15
|
+
(function(global2, factory) {
|
|
16
|
+
module.exports = factory();
|
|
17
|
+
})(commonjsGlobal, function() {
|
|
18
|
+
function ownKeys(object, enumerableOnly) {
|
|
19
|
+
var keys = Object.keys(object);
|
|
20
|
+
if (Object.getOwnPropertySymbols) {
|
|
21
|
+
var symbols = Object.getOwnPropertySymbols(object);
|
|
22
|
+
if (enumerableOnly) {
|
|
23
|
+
symbols = symbols.filter(function(sym) {
|
|
24
|
+
return Object.getOwnPropertyDescriptor(object, sym).enumerable;
|
|
25
|
+
});
|
|
26
|
+
}
|
|
27
|
+
keys.push.apply(keys, symbols);
|
|
19
28
|
}
|
|
20
|
-
|
|
21
|
-
|
|
29
|
+
return keys;
|
|
30
|
+
}
|
|
31
|
+
function _objectSpread2(target) {
|
|
32
|
+
for (var i = 1; i < arguments.length; i++) {
|
|
33
|
+
var source = arguments[i] != null ? arguments[i] : {};
|
|
34
|
+
if (i % 2) {
|
|
35
|
+
ownKeys(Object(source), true).forEach(function(key) {
|
|
36
|
+
_defineProperty(target, key, source[key]);
|
|
37
|
+
});
|
|
38
|
+
} else if (Object.getOwnPropertyDescriptors) {
|
|
39
|
+
Object.defineProperties(target, Object.getOwnPropertyDescriptors(source));
|
|
40
|
+
} else {
|
|
41
|
+
ownKeys(Object(source)).forEach(function(key) {
|
|
42
|
+
Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key));
|
|
43
|
+
});
|
|
44
|
+
}
|
|
22
45
|
}
|
|
23
|
-
|
|
24
|
-
|
|
46
|
+
return target;
|
|
47
|
+
}
|
|
48
|
+
function _typeof(obj) {
|
|
49
|
+
"@babel/helpers - typeof";
|
|
50
|
+
if (typeof Symbol === "function" && typeof Symbol.iterator === "symbol") {
|
|
51
|
+
_typeof = function(obj2) {
|
|
52
|
+
return typeof obj2;
|
|
53
|
+
};
|
|
54
|
+
} else {
|
|
55
|
+
_typeof = function(obj2) {
|
|
56
|
+
return obj2 && typeof Symbol === "function" && obj2.constructor === Symbol && obj2 !== Symbol.prototype ? "symbol" : typeof obj2;
|
|
57
|
+
};
|
|
25
58
|
}
|
|
26
|
-
|
|
27
|
-
window[callbackName] = (data) => {
|
|
28
|
-
cleanup();
|
|
29
|
-
resolve(data.data || data);
|
|
30
|
-
};
|
|
31
|
-
timeoutId = setTimeout(() => {
|
|
32
|
-
cleanup();
|
|
33
|
-
reject(new Error(`JSONP request timeout: ${url}`));
|
|
34
|
-
}, timeout);
|
|
35
|
-
script.onerror = () => {
|
|
36
|
-
cleanup();
|
|
37
|
-
reject(new Error(`JSONP request failed: ${url}`));
|
|
38
|
-
};
|
|
39
|
-
const separator = url.includes("?") ? "&" : "?";
|
|
40
|
-
const paramsStr = params ? `&${Object.entries(params).map(([key, value]) => value ? `${key}=${value}` : "").filter(Boolean).join("&")}` : "";
|
|
41
|
-
script.src = `${url}${separator}callback=${callbackName}${paramsStr}`;
|
|
42
|
-
document.head.appendChild(script);
|
|
43
|
-
});
|
|
44
|
-
};
|
|
45
|
-
const getTenants = async (apiBaseUrl, tenantId) => {
|
|
46
|
-
if (!apiBaseUrl || !tenantId) {
|
|
47
|
-
console.warn("获取租户信息需要提供有效的apiBaseUrl和租户ID");
|
|
48
|
-
return [];
|
|
49
|
-
}
|
|
50
|
-
try {
|
|
51
|
-
const url = `${apiBaseUrl}/api/v3/open-web/tenant/data-source-owner-tenants/`;
|
|
52
|
-
const response = await fetch(url, {
|
|
53
|
-
method: "GET",
|
|
54
|
-
headers: {
|
|
55
|
-
"x-bk-tenant-id": tenantId
|
|
56
|
-
},
|
|
57
|
-
credentials: "include"
|
|
58
|
-
});
|
|
59
|
-
if (!response.ok) {
|
|
60
|
-
throw new Error(`获取租户信息失败: ${response.status} ${response.statusText}`);
|
|
59
|
+
return _typeof(obj);
|
|
61
60
|
}
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
pageSize: 100,
|
|
75
|
-
page: 1
|
|
76
|
-
}).catch(() => {
|
|
77
|
-
return [];
|
|
78
|
-
});
|
|
79
|
-
return userList;
|
|
80
|
-
}
|
|
81
|
-
if (!keyword || !apiBaseUrl || !tenantId) {
|
|
82
|
-
console.warn("搜索用户需要提供有效的apiBaseUrl、租户ID和关键词");
|
|
83
|
-
return [];
|
|
84
|
-
}
|
|
85
|
-
try {
|
|
86
|
-
const url = `${apiBaseUrl}/api/v3/open-web/tenant/users/-/search/?keyword=${encodeURIComponent(keyword)}`;
|
|
87
|
-
const response = await fetch(url, {
|
|
88
|
-
method: "GET",
|
|
89
|
-
headers: {
|
|
90
|
-
"x-bk-tenant-id": tenantId
|
|
91
|
-
},
|
|
92
|
-
credentials: "include"
|
|
93
|
-
});
|
|
94
|
-
if (!response.ok) {
|
|
95
|
-
throw new Error(`搜索用户失败: ${response.status} ${response.statusText}`);
|
|
61
|
+
function _defineProperty(obj, key, value) {
|
|
62
|
+
if (key in obj) {
|
|
63
|
+
Object.defineProperty(obj, key, {
|
|
64
|
+
value,
|
|
65
|
+
enumerable: true,
|
|
66
|
+
configurable: true,
|
|
67
|
+
writable: true
|
|
68
|
+
});
|
|
69
|
+
} else {
|
|
70
|
+
obj[key] = value;
|
|
71
|
+
}
|
|
72
|
+
return obj;
|
|
96
73
|
}
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
}).catch(() => {
|
|
111
|
-
return [];
|
|
112
|
-
});
|
|
113
|
-
return users.map((user) => userList.find((u) => u.username === user)).filter(Boolean);
|
|
114
|
-
}
|
|
115
|
-
if (users.length === 0 || !apiBaseUrl || !tenantId) {
|
|
116
|
-
console.warn("批量查找用户需要提供有效的apiBaseUrl、租户ID和至少一个用户名");
|
|
117
|
-
return [];
|
|
118
|
-
}
|
|
119
|
-
try {
|
|
120
|
-
const url = `${apiBaseUrl}/api/v3/open-web/tenant/users/-/lookup/?lookups=${users.join(",")}&lookup_fields=${exactSearchKey}`;
|
|
121
|
-
const response = await fetch(url, {
|
|
122
|
-
method: "GET",
|
|
123
|
-
headers: {
|
|
124
|
-
"x-bk-tenant-id": tenantId
|
|
125
|
-
},
|
|
126
|
-
credentials: "include"
|
|
127
|
-
});
|
|
128
|
-
if (!response.ok) {
|
|
129
|
-
throw new Error(`批量查找用户失败: ${response.status} ${response.statusText}`);
|
|
74
|
+
function _extends() {
|
|
75
|
+
_extends = Object.assign || function(target) {
|
|
76
|
+
for (var i = 1; i < arguments.length; i++) {
|
|
77
|
+
var source = arguments[i];
|
|
78
|
+
for (var key in source) {
|
|
79
|
+
if (Object.prototype.hasOwnProperty.call(source, key)) {
|
|
80
|
+
target[key] = source[key];
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
return target;
|
|
85
|
+
};
|
|
86
|
+
return _extends.apply(this, arguments);
|
|
130
87
|
}
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
...user,
|
|
143
|
-
id: user.username,
|
|
144
|
-
name: `${user.display_name}(${user.username})`,
|
|
145
|
-
tenantId: user.owner_tenant_id
|
|
146
|
-
}));
|
|
147
|
-
}
|
|
148
|
-
return users.map((user) => ({
|
|
149
|
-
id: user.bk_username,
|
|
150
|
-
name: user.display_name,
|
|
151
|
-
tenantId: user.owner_tenant_id,
|
|
152
|
-
...user
|
|
153
|
-
}));
|
|
154
|
-
};
|
|
155
|
-
const getUserList = async (url, params) => {
|
|
156
|
-
const { userIds, keyword, pageSize = 20, page, appCode } = params;
|
|
157
|
-
const data = await jsonpRequest(url, {
|
|
158
|
-
params: {
|
|
159
|
-
exact_lookups: (userIds == null ? void 0 : userIds.join(",")) || void 0,
|
|
160
|
-
fuzzy_lookups: keyword || void 0,
|
|
161
|
-
page_size: Math.max((userIds == null ? void 0 : userIds.length) || 0, 20, Number(pageSize)).toString(),
|
|
162
|
-
page: (page == null ? void 0 : page.toString()) || "1",
|
|
163
|
-
app_code: appCode || "bk-magicbox"
|
|
88
|
+
function _objectWithoutPropertiesLoose(source, excluded) {
|
|
89
|
+
if (source == null) return {};
|
|
90
|
+
var target = {};
|
|
91
|
+
var sourceKeys = Object.keys(source);
|
|
92
|
+
var key, i;
|
|
93
|
+
for (i = 0; i < sourceKeys.length; i++) {
|
|
94
|
+
key = sourceKeys[i];
|
|
95
|
+
if (excluded.indexOf(key) >= 0) continue;
|
|
96
|
+
target[key] = source[key];
|
|
97
|
+
}
|
|
98
|
+
return target;
|
|
164
99
|
}
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
100
|
+
function _objectWithoutProperties(source, excluded) {
|
|
101
|
+
if (source == null) return {};
|
|
102
|
+
var target = _objectWithoutPropertiesLoose(source, excluded);
|
|
103
|
+
var key, i;
|
|
104
|
+
if (Object.getOwnPropertySymbols) {
|
|
105
|
+
var sourceSymbolKeys = Object.getOwnPropertySymbols(source);
|
|
106
|
+
for (i = 0; i < sourceSymbolKeys.length; i++) {
|
|
107
|
+
key = sourceSymbolKeys[i];
|
|
108
|
+
if (excluded.indexOf(key) >= 0) continue;
|
|
109
|
+
if (!Object.prototype.propertyIsEnumerable.call(source, key)) continue;
|
|
110
|
+
target[key] = source[key];
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
return target;
|
|
174
114
|
}
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
}
|
|
178
|
-
var defaultConverter = {
|
|
179
|
-
read: function(value) {
|
|
180
|
-
if (value[0] === '"') {
|
|
181
|
-
value = value.slice(1, -1);
|
|
115
|
+
function _toConsumableArray(arr) {
|
|
116
|
+
return _arrayWithoutHoles(arr) || _iterableToArray(arr) || _unsupportedIterableToArray(arr) || _nonIterableSpread();
|
|
182
117
|
}
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
write: function(value) {
|
|
186
|
-
return encodeURIComponent(value).replace(
|
|
187
|
-
/%(2[346BF]|3[AC-F]|40|5[BDE]|60|7[BCD])/g,
|
|
188
|
-
decodeURIComponent
|
|
189
|
-
);
|
|
190
|
-
}
|
|
191
|
-
};
|
|
192
|
-
function init(converter, defaultAttributes) {
|
|
193
|
-
function set(name, value, attributes) {
|
|
194
|
-
if (typeof document === "undefined") {
|
|
195
|
-
return;
|
|
196
|
-
}
|
|
197
|
-
attributes = assign({}, defaultAttributes, attributes);
|
|
198
|
-
if (typeof attributes.expires === "number") {
|
|
199
|
-
attributes.expires = new Date(Date.now() + attributes.expires * 864e5);
|
|
118
|
+
function _arrayWithoutHoles(arr) {
|
|
119
|
+
if (Array.isArray(arr)) return _arrayLikeToArray(arr);
|
|
200
120
|
}
|
|
201
|
-
|
|
202
|
-
|
|
121
|
+
function _iterableToArray(iter) {
|
|
122
|
+
if (typeof Symbol !== "undefined" && iter[Symbol.iterator] != null || iter["@@iterator"] != null) return Array.from(iter);
|
|
203
123
|
}
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
if (attributes[attributeName] === true) {
|
|
212
|
-
continue;
|
|
213
|
-
}
|
|
214
|
-
stringifiedAttributes += "=" + attributes[attributeName].split(";")[0];
|
|
124
|
+
function _unsupportedIterableToArray(o, minLen) {
|
|
125
|
+
if (!o) return;
|
|
126
|
+
if (typeof o === "string") return _arrayLikeToArray(o, minLen);
|
|
127
|
+
var n = Object.prototype.toString.call(o).slice(8, -1);
|
|
128
|
+
if (n === "Object" && o.constructor) n = o.constructor.name;
|
|
129
|
+
if (n === "Map" || n === "Set") return Array.from(o);
|
|
130
|
+
if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen);
|
|
215
131
|
}
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
return;
|
|
132
|
+
function _arrayLikeToArray(arr, len) {
|
|
133
|
+
if (len == null || len > arr.length) len = arr.length;
|
|
134
|
+
for (var i = 0, arr2 = new Array(len); i < len; i++) arr2[i] = arr[i];
|
|
135
|
+
return arr2;
|
|
221
136
|
}
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
for (var i = 0; i < cookies.length; i++) {
|
|
225
|
-
var parts = cookies[i].split("=");
|
|
226
|
-
var value = parts.slice(1).join("=");
|
|
227
|
-
try {
|
|
228
|
-
var found = decodeURIComponent(parts[0]);
|
|
229
|
-
jar[found] = converter.read(value, found);
|
|
230
|
-
if (name === found) {
|
|
231
|
-
break;
|
|
232
|
-
}
|
|
233
|
-
} catch (e) {
|
|
234
|
-
}
|
|
137
|
+
function _nonIterableSpread() {
|
|
138
|
+
throw new TypeError("Invalid attempt to spread non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.");
|
|
235
139
|
}
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
set,
|
|
241
|
-
get,
|
|
242
|
-
remove: function(name, attributes) {
|
|
243
|
-
set(
|
|
244
|
-
name,
|
|
245
|
-
"",
|
|
246
|
-
assign({}, attributes, {
|
|
247
|
-
expires: -1
|
|
248
|
-
})
|
|
249
|
-
);
|
|
250
|
-
},
|
|
251
|
-
withAttributes: function(attributes) {
|
|
252
|
-
return init(this.converter, assign({}, this.attributes, attributes));
|
|
253
|
-
},
|
|
254
|
-
withConverter: function(converter2) {
|
|
255
|
-
return init(assign({}, this.converter, converter2), this.attributes);
|
|
140
|
+
var version = "1.15.6";
|
|
141
|
+
function userAgent(pattern) {
|
|
142
|
+
if (typeof window !== "undefined" && window.navigator) {
|
|
143
|
+
return !!/* @__PURE__ */ navigator.userAgent.match(pattern);
|
|
256
144
|
}
|
|
257
|
-
},
|
|
258
|
-
{
|
|
259
|
-
attributes: { value: Object.freeze(defaultAttributes) },
|
|
260
|
-
converter: { value: Object.freeze(converter) }
|
|
261
145
|
}
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
var
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
我: "我",
|
|
275
|
-
请输入人员名称搜索: "请输入人员名称搜索",
|
|
276
|
-
用户群组: "用户群组",
|
|
277
|
-
无匹配人员: "无匹配人员",
|
|
278
|
-
虚拟账号: "虚拟账号",
|
|
279
|
-
用户: "用户"
|
|
280
|
-
};
|
|
281
|
-
const BLUEKINNG_LANGUAGE = "blueking_language";
|
|
282
|
-
const languageMap = {
|
|
283
|
-
"en-US": enUS,
|
|
284
|
-
"zh-CN": zhCN
|
|
285
|
-
};
|
|
286
|
-
const getPath = (obj, path, variables) => {
|
|
287
|
-
const pathStack = /^\w/.test(path) ? path.split(".") : [path];
|
|
288
|
-
const { length } = pathStack;
|
|
289
|
-
let target = obj;
|
|
290
|
-
let i = 0;
|
|
291
|
-
while (i <= length && target) {
|
|
292
|
-
if (typeof target === "string") {
|
|
293
|
-
return target;
|
|
146
|
+
var IE11OrLess = userAgent(/(?:Trident.*rv[ :]?11\.|msie|iemobile|Windows Phone)/i);
|
|
147
|
+
var Edge = userAgent(/Edge/i);
|
|
148
|
+
var FireFox = userAgent(/firefox/i);
|
|
149
|
+
var Safari = userAgent(/safari/i) && !userAgent(/chrome/i) && !userAgent(/android/i);
|
|
150
|
+
var IOS = userAgent(/iP(ad|od|hone)/i);
|
|
151
|
+
var ChromeForAndroid = userAgent(/chrome/i) && userAgent(/android/i);
|
|
152
|
+
var captureMode = {
|
|
153
|
+
capture: false,
|
|
154
|
+
passive: false
|
|
155
|
+
};
|
|
156
|
+
function on(el, event, fn) {
|
|
157
|
+
el.addEventListener(event, fn, !IE11OrLess && captureMode);
|
|
294
158
|
}
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
Object.keys(variables).forEach((key) => {
|
|
298
|
-
target = target.replace(`{${key}}`, variables[key]);
|
|
299
|
-
});
|
|
300
|
-
} else {
|
|
301
|
-
target = target[pathStack[i]];
|
|
159
|
+
function off(el, event, fn) {
|
|
160
|
+
el.removeEventListener(event, fn, !IE11OrLess && captureMode);
|
|
302
161
|
}
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
162
|
+
function matches(el, selector) {
|
|
163
|
+
if (!selector) return;
|
|
164
|
+
selector[0] === ">" && (selector = selector.substring(1));
|
|
165
|
+
if (el) {
|
|
166
|
+
try {
|
|
167
|
+
if (el.matches) {
|
|
168
|
+
return el.matches(selector);
|
|
169
|
+
} else if (el.msMatchesSelector) {
|
|
170
|
+
return el.msMatchesSelector(selector);
|
|
171
|
+
} else if (el.webkitMatchesSelector) {
|
|
172
|
+
return el.webkitMatchesSelector(selector);
|
|
173
|
+
}
|
|
174
|
+
} catch (_) {
|
|
175
|
+
return false;
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
return false;
|
|
306
179
|
}
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
};
|
|
310
|
-
const useI18n = () => {
|
|
311
|
-
let localeLanguage = "zh-CN";
|
|
312
|
-
const bluekingLanguage = api.get(BLUEKINNG_LANGUAGE);
|
|
313
|
-
if (bluekingLanguage && bluekingLanguage.toLowerCase() === "en") {
|
|
314
|
-
localeLanguage = "en-US";
|
|
315
|
-
}
|
|
316
|
-
const languagePackage = languageMap[localeLanguage];
|
|
317
|
-
const t = (path, variable) => {
|
|
318
|
-
const value = getPath(languagePackage, path, variable);
|
|
319
|
-
if (value === void 0) {
|
|
320
|
-
console.warn(`缺少索引 * ${path} *`);
|
|
180
|
+
function getParentOrHost(el) {
|
|
181
|
+
return el.host && el !== document && el.host.nodeType ? el.host : el.parentNode;
|
|
321
182
|
}
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
}
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
if (!apiBaseUrl || !tenantId) {
|
|
334
|
-
console.warn("获取租户需要提供有效的API基础URL和租户ID");
|
|
335
|
-
return;
|
|
183
|
+
function closest(el, selector, ctx, includeCTX) {
|
|
184
|
+
if (el) {
|
|
185
|
+
ctx = ctx || document;
|
|
186
|
+
do {
|
|
187
|
+
if (selector != null && (selector[0] === ">" ? el.parentNode === ctx && matches(el, selector) : matches(el, selector)) || includeCTX && el === ctx) {
|
|
188
|
+
return el;
|
|
189
|
+
}
|
|
190
|
+
if (el === ctx) break;
|
|
191
|
+
} while (el = getParentOrHost(el));
|
|
192
|
+
}
|
|
193
|
+
return null;
|
|
336
194
|
}
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
195
|
+
var R_SPACE = /\s+/g;
|
|
196
|
+
function toggleClass(el, name, state) {
|
|
197
|
+
if (el && name) {
|
|
198
|
+
if (el.classList) {
|
|
199
|
+
el.classList[state ? "add" : "remove"](name);
|
|
200
|
+
} else {
|
|
201
|
+
var className = (" " + el.className + " ").replace(R_SPACE, " ").replace(" " + name + " ", " ");
|
|
202
|
+
el.className = (className + (state ? " " + name : "")).replace(R_SPACE, " ");
|
|
344
203
|
}
|
|
345
|
-
}
|
|
346
|
-
tenants.value = tenantMap;
|
|
347
|
-
} catch (error) {
|
|
348
|
-
console.error("获取租户数据失败:", error);
|
|
349
|
-
} finally {
|
|
350
|
-
loading.value = false;
|
|
204
|
+
}
|
|
351
205
|
}
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
}
|
|
368
|
-
|
|
369
|
-
/**!
|
|
370
|
-
* Sortable 1.15.6
|
|
371
|
-
* @author RubaXa <trash@rubaxa.org>
|
|
372
|
-
* @author owenm <owen23355@gmail.com>
|
|
373
|
-
* @license MIT
|
|
374
|
-
*/
|
|
375
|
-
(function(module, exports) {
|
|
376
|
-
(function(global2, factory) {
|
|
377
|
-
module.exports = factory();
|
|
378
|
-
})(commonjsGlobal, function() {
|
|
379
|
-
function ownKeys(object, enumerableOnly) {
|
|
380
|
-
var keys = Object.keys(object);
|
|
381
|
-
if (Object.getOwnPropertySymbols) {
|
|
382
|
-
var symbols = Object.getOwnPropertySymbols(object);
|
|
383
|
-
if (enumerableOnly) {
|
|
384
|
-
symbols = symbols.filter(function(sym) {
|
|
385
|
-
return Object.getOwnPropertyDescriptor(object, sym).enumerable;
|
|
386
|
-
});
|
|
387
|
-
}
|
|
388
|
-
keys.push.apply(keys, symbols);
|
|
389
|
-
}
|
|
390
|
-
return keys;
|
|
391
|
-
}
|
|
392
|
-
function _objectSpread2(target) {
|
|
393
|
-
for (var i = 1; i < arguments.length; i++) {
|
|
394
|
-
var source = arguments[i] != null ? arguments[i] : {};
|
|
395
|
-
if (i % 2) {
|
|
396
|
-
ownKeys(Object(source), true).forEach(function(key) {
|
|
397
|
-
_defineProperty(target, key, source[key]);
|
|
398
|
-
});
|
|
399
|
-
} else if (Object.getOwnPropertyDescriptors) {
|
|
400
|
-
Object.defineProperties(target, Object.getOwnPropertyDescriptors(source));
|
|
401
|
-
} else {
|
|
402
|
-
ownKeys(Object(source)).forEach(function(key) {
|
|
403
|
-
Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key));
|
|
404
|
-
});
|
|
405
|
-
}
|
|
406
|
-
}
|
|
407
|
-
return target;
|
|
408
|
-
}
|
|
409
|
-
function _typeof(obj) {
|
|
410
|
-
"@babel/helpers - typeof";
|
|
411
|
-
if (typeof Symbol === "function" && typeof Symbol.iterator === "symbol") {
|
|
412
|
-
_typeof = function(obj2) {
|
|
413
|
-
return typeof obj2;
|
|
414
|
-
};
|
|
415
|
-
} else {
|
|
416
|
-
_typeof = function(obj2) {
|
|
417
|
-
return obj2 && typeof Symbol === "function" && obj2.constructor === Symbol && obj2 !== Symbol.prototype ? "symbol" : typeof obj2;
|
|
418
|
-
};
|
|
419
|
-
}
|
|
420
|
-
return _typeof(obj);
|
|
421
|
-
}
|
|
422
|
-
function _defineProperty(obj, key, value) {
|
|
423
|
-
if (key in obj) {
|
|
424
|
-
Object.defineProperty(obj, key, {
|
|
425
|
-
value,
|
|
426
|
-
enumerable: true,
|
|
427
|
-
configurable: true,
|
|
428
|
-
writable: true
|
|
429
|
-
});
|
|
430
|
-
} else {
|
|
431
|
-
obj[key] = value;
|
|
432
|
-
}
|
|
433
|
-
return obj;
|
|
434
|
-
}
|
|
435
|
-
function _extends() {
|
|
436
|
-
_extends = Object.assign || function(target) {
|
|
437
|
-
for (var i = 1; i < arguments.length; i++) {
|
|
438
|
-
var source = arguments[i];
|
|
439
|
-
for (var key in source) {
|
|
440
|
-
if (Object.prototype.hasOwnProperty.call(source, key)) {
|
|
441
|
-
target[key] = source[key];
|
|
442
|
-
}
|
|
443
|
-
}
|
|
444
|
-
}
|
|
445
|
-
return target;
|
|
446
|
-
};
|
|
447
|
-
return _extends.apply(this, arguments);
|
|
448
|
-
}
|
|
449
|
-
function _objectWithoutPropertiesLoose(source, excluded) {
|
|
450
|
-
if (source == null) return {};
|
|
451
|
-
var target = {};
|
|
452
|
-
var sourceKeys = Object.keys(source);
|
|
453
|
-
var key, i;
|
|
454
|
-
for (i = 0; i < sourceKeys.length; i++) {
|
|
455
|
-
key = sourceKeys[i];
|
|
456
|
-
if (excluded.indexOf(key) >= 0) continue;
|
|
457
|
-
target[key] = source[key];
|
|
458
|
-
}
|
|
459
|
-
return target;
|
|
460
|
-
}
|
|
461
|
-
function _objectWithoutProperties(source, excluded) {
|
|
462
|
-
if (source == null) return {};
|
|
463
|
-
var target = _objectWithoutPropertiesLoose(source, excluded);
|
|
464
|
-
var key, i;
|
|
465
|
-
if (Object.getOwnPropertySymbols) {
|
|
466
|
-
var sourceSymbolKeys = Object.getOwnPropertySymbols(source);
|
|
467
|
-
for (i = 0; i < sourceSymbolKeys.length; i++) {
|
|
468
|
-
key = sourceSymbolKeys[i];
|
|
469
|
-
if (excluded.indexOf(key) >= 0) continue;
|
|
470
|
-
if (!Object.prototype.propertyIsEnumerable.call(source, key)) continue;
|
|
471
|
-
target[key] = source[key];
|
|
472
|
-
}
|
|
473
|
-
}
|
|
474
|
-
return target;
|
|
475
|
-
}
|
|
476
|
-
function _toConsumableArray(arr) {
|
|
477
|
-
return _arrayWithoutHoles(arr) || _iterableToArray(arr) || _unsupportedIterableToArray(arr) || _nonIterableSpread();
|
|
478
|
-
}
|
|
479
|
-
function _arrayWithoutHoles(arr) {
|
|
480
|
-
if (Array.isArray(arr)) return _arrayLikeToArray(arr);
|
|
481
|
-
}
|
|
482
|
-
function _iterableToArray(iter) {
|
|
483
|
-
if (typeof Symbol !== "undefined" && iter[Symbol.iterator] != null || iter["@@iterator"] != null) return Array.from(iter);
|
|
484
|
-
}
|
|
485
|
-
function _unsupportedIterableToArray(o, minLen) {
|
|
486
|
-
if (!o) return;
|
|
487
|
-
if (typeof o === "string") return _arrayLikeToArray(o, minLen);
|
|
488
|
-
var n = Object.prototype.toString.call(o).slice(8, -1);
|
|
489
|
-
if (n === "Object" && o.constructor) n = o.constructor.name;
|
|
490
|
-
if (n === "Map" || n === "Set") return Array.from(o);
|
|
491
|
-
if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen);
|
|
492
|
-
}
|
|
493
|
-
function _arrayLikeToArray(arr, len) {
|
|
494
|
-
if (len == null || len > arr.length) len = arr.length;
|
|
495
|
-
for (var i = 0, arr2 = new Array(len); i < len; i++) arr2[i] = arr[i];
|
|
496
|
-
return arr2;
|
|
497
|
-
}
|
|
498
|
-
function _nonIterableSpread() {
|
|
499
|
-
throw new TypeError("Invalid attempt to spread non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.");
|
|
500
|
-
}
|
|
501
|
-
var version = "1.15.6";
|
|
502
|
-
function userAgent(pattern) {
|
|
503
|
-
if (typeof window !== "undefined" && window.navigator) {
|
|
504
|
-
return !!/* @__PURE__ */ navigator.userAgent.match(pattern);
|
|
505
|
-
}
|
|
506
|
-
}
|
|
507
|
-
var IE11OrLess = userAgent(/(?:Trident.*rv[ :]?11\.|msie|iemobile|Windows Phone)/i);
|
|
508
|
-
var Edge = userAgent(/Edge/i);
|
|
509
|
-
var FireFox = userAgent(/firefox/i);
|
|
510
|
-
var Safari = userAgent(/safari/i) && !userAgent(/chrome/i) && !userAgent(/android/i);
|
|
511
|
-
var IOS = userAgent(/iP(ad|od|hone)/i);
|
|
512
|
-
var ChromeForAndroid = userAgent(/chrome/i) && userAgent(/android/i);
|
|
513
|
-
var captureMode = {
|
|
514
|
-
capture: false,
|
|
515
|
-
passive: false
|
|
516
|
-
};
|
|
517
|
-
function on(el, event, fn) {
|
|
518
|
-
el.addEventListener(event, fn, !IE11OrLess && captureMode);
|
|
519
|
-
}
|
|
520
|
-
function off(el, event, fn) {
|
|
521
|
-
el.removeEventListener(event, fn, !IE11OrLess && captureMode);
|
|
522
|
-
}
|
|
523
|
-
function matches(el, selector) {
|
|
524
|
-
if (!selector) return;
|
|
525
|
-
selector[0] === ">" && (selector = selector.substring(1));
|
|
526
|
-
if (el) {
|
|
527
|
-
try {
|
|
528
|
-
if (el.matches) {
|
|
529
|
-
return el.matches(selector);
|
|
530
|
-
} else if (el.msMatchesSelector) {
|
|
531
|
-
return el.msMatchesSelector(selector);
|
|
532
|
-
} else if (el.webkitMatchesSelector) {
|
|
533
|
-
return el.webkitMatchesSelector(selector);
|
|
534
|
-
}
|
|
535
|
-
} catch (_) {
|
|
536
|
-
return false;
|
|
537
|
-
}
|
|
538
|
-
}
|
|
539
|
-
return false;
|
|
540
|
-
}
|
|
541
|
-
function getParentOrHost(el) {
|
|
542
|
-
return el.host && el !== document && el.host.nodeType ? el.host : el.parentNode;
|
|
543
|
-
}
|
|
544
|
-
function closest(el, selector, ctx, includeCTX) {
|
|
545
|
-
if (el) {
|
|
546
|
-
ctx = ctx || document;
|
|
547
|
-
do {
|
|
548
|
-
if (selector != null && (selector[0] === ">" ? el.parentNode === ctx && matches(el, selector) : matches(el, selector)) || includeCTX && el === ctx) {
|
|
549
|
-
return el;
|
|
550
|
-
}
|
|
551
|
-
if (el === ctx) break;
|
|
552
|
-
} while (el = getParentOrHost(el));
|
|
553
|
-
}
|
|
554
|
-
return null;
|
|
555
|
-
}
|
|
556
|
-
var R_SPACE = /\s+/g;
|
|
557
|
-
function toggleClass(el, name, state) {
|
|
558
|
-
if (el && name) {
|
|
559
|
-
if (el.classList) {
|
|
560
|
-
el.classList[state ? "add" : "remove"](name);
|
|
561
|
-
} else {
|
|
562
|
-
var className = (" " + el.className + " ").replace(R_SPACE, " ").replace(" " + name + " ", " ");
|
|
563
|
-
el.className = (className + (state ? " " + name : "")).replace(R_SPACE, " ");
|
|
564
|
-
}
|
|
565
|
-
}
|
|
566
|
-
}
|
|
567
|
-
function css(el, prop, val) {
|
|
568
|
-
var style = el && el.style;
|
|
569
|
-
if (style) {
|
|
570
|
-
if (val === void 0) {
|
|
571
|
-
if (document.defaultView && document.defaultView.getComputedStyle) {
|
|
572
|
-
val = document.defaultView.getComputedStyle(el, "");
|
|
573
|
-
} else if (el.currentStyle) {
|
|
574
|
-
val = el.currentStyle;
|
|
575
|
-
}
|
|
576
|
-
return prop === void 0 ? val : val[prop];
|
|
577
|
-
} else {
|
|
578
|
-
if (!(prop in style) && prop.indexOf("webkit") === -1) {
|
|
579
|
-
prop = "-webkit-" + prop;
|
|
580
|
-
}
|
|
581
|
-
style[prop] = val + (typeof val === "string" ? "" : "px");
|
|
582
|
-
}
|
|
583
|
-
}
|
|
206
|
+
function css(el, prop, val) {
|
|
207
|
+
var style = el && el.style;
|
|
208
|
+
if (style) {
|
|
209
|
+
if (val === void 0) {
|
|
210
|
+
if (document.defaultView && document.defaultView.getComputedStyle) {
|
|
211
|
+
val = document.defaultView.getComputedStyle(el, "");
|
|
212
|
+
} else if (el.currentStyle) {
|
|
213
|
+
val = el.currentStyle;
|
|
214
|
+
}
|
|
215
|
+
return prop === void 0 ? val : val[prop];
|
|
216
|
+
} else {
|
|
217
|
+
if (!(prop in style) && prop.indexOf("webkit") === -1) {
|
|
218
|
+
prop = "-webkit-" + prop;
|
|
219
|
+
}
|
|
220
|
+
style[prop] = val + (typeof val === "string" ? "" : "px");
|
|
221
|
+
}
|
|
222
|
+
}
|
|
584
223
|
}
|
|
585
224
|
function matrix(el, selfOnly) {
|
|
586
225
|
var appliedTransforms = "";
|
|
@@ -3119,15 +2758,583 @@ var Sortable$1 = { exports: {} };
|
|
|
3119
2758
|
multiDragElement.parentNode && multiDragElement.parentNode.removeChild(multiDragElement);
|
|
3120
2759
|
});
|
|
3121
2760
|
}
|
|
3122
|
-
Sortable2.mount(new AutoScrollPlugin());
|
|
3123
|
-
Sortable2.mount(Remove, Revert);
|
|
3124
|
-
Sortable2.mount(new SwapPlugin());
|
|
3125
|
-
Sortable2.mount(new MultiDragPlugin());
|
|
3126
|
-
return Sortable2;
|
|
2761
|
+
Sortable2.mount(new AutoScrollPlugin());
|
|
2762
|
+
Sortable2.mount(Remove, Revert);
|
|
2763
|
+
Sortable2.mount(new SwapPlugin());
|
|
2764
|
+
Sortable2.mount(new MultiDragPlugin());
|
|
2765
|
+
return Sortable2;
|
|
2766
|
+
});
|
|
2767
|
+
})(Sortable$1);
|
|
2768
|
+
var SortableExports = Sortable$1.exports;
|
|
2769
|
+
const Sortable = /* @__PURE__ */ getDefaultExportFromCjs(SortableExports);
|
|
2770
|
+
const RESERVED_SPACE_FOR_INPUT = 100;
|
|
2771
|
+
const SEARCH_DEBOUNCE_DELAY = 300;
|
|
2772
|
+
const DEFAULT_EXACT_SEARCH_KEY = "bk_username";
|
|
2773
|
+
const USER_TYPE = {
|
|
2774
|
+
/** 普通用户 */
|
|
2775
|
+
USER: "user",
|
|
2776
|
+
/** 虚拟账号 */
|
|
2777
|
+
VIRTUAL: "virtual",
|
|
2778
|
+
/** 自定义用户 */
|
|
2779
|
+
CUSTOM: "custom",
|
|
2780
|
+
/** 用户群组 */
|
|
2781
|
+
USER_GROUP: "userGroup"
|
|
2782
|
+
};
|
|
2783
|
+
const DEFAULT_PAGE_SIZE = 100;
|
|
2784
|
+
const generateCallbackName = () => {
|
|
2785
|
+
const timestamp = Date.now();
|
|
2786
|
+
const random = Math.random().toString(36).slice(2, 9);
|
|
2787
|
+
return `__jsonp_callback_${timestamp}_${random}`;
|
|
2788
|
+
};
|
|
2789
|
+
const jsonpRequest = (requestUrl, options = {}) => {
|
|
2790
|
+
return new Promise((resolve, reject) => {
|
|
2791
|
+
const url = unref(requestUrl);
|
|
2792
|
+
const { timeout = 1e3 * 60 * 2, params } = options;
|
|
2793
|
+
const callbackName = generateCallbackName();
|
|
2794
|
+
const script = document.createElement("script");
|
|
2795
|
+
let timeoutId = null;
|
|
2796
|
+
script.setAttribute("type", "text/javascript");
|
|
2797
|
+
const cleanup = () => {
|
|
2798
|
+
if (timeoutId) {
|
|
2799
|
+
clearTimeout(timeoutId);
|
|
2800
|
+
}
|
|
2801
|
+
if (script.parentNode) {
|
|
2802
|
+
script.parentNode.removeChild(script);
|
|
2803
|
+
}
|
|
2804
|
+
if (window[callbackName]) {
|
|
2805
|
+
delete window[callbackName];
|
|
2806
|
+
}
|
|
2807
|
+
};
|
|
2808
|
+
window[callbackName] = (data) => {
|
|
2809
|
+
cleanup();
|
|
2810
|
+
resolve(data.data || data);
|
|
2811
|
+
};
|
|
2812
|
+
timeoutId = setTimeout(() => {
|
|
2813
|
+
cleanup();
|
|
2814
|
+
reject(new Error(`JSONP request timeout: ${url}`));
|
|
2815
|
+
}, timeout);
|
|
2816
|
+
script.onerror = () => {
|
|
2817
|
+
cleanup();
|
|
2818
|
+
reject(new Error(`JSONP request failed: ${url}`));
|
|
2819
|
+
};
|
|
2820
|
+
const separator = url.includes("?") ? "&" : "?";
|
|
2821
|
+
const paramsStr = params ? `&${Object.entries(params).map(([key, value]) => value ? `${key}=${value}` : "").filter(Boolean).join("&")}` : "";
|
|
2822
|
+
script.src = `${url}${separator}callback=${callbackName}${paramsStr}`;
|
|
2823
|
+
document.head.appendChild(script);
|
|
2824
|
+
});
|
|
2825
|
+
};
|
|
2826
|
+
const logger = {
|
|
2827
|
+
/**
|
|
2828
|
+
* 调试日志
|
|
2829
|
+
*/
|
|
2830
|
+
debug: (message, ...args) => {
|
|
2831
|
+
},
|
|
2832
|
+
/**
|
|
2833
|
+
* 信息日志
|
|
2834
|
+
*/
|
|
2835
|
+
info: (message, ...args) => {
|
|
2836
|
+
},
|
|
2837
|
+
/**
|
|
2838
|
+
* 警告日志
|
|
2839
|
+
*/
|
|
2840
|
+
warn: (message, ...args) => {
|
|
2841
|
+
},
|
|
2842
|
+
/**
|
|
2843
|
+
* 错误日志
|
|
2844
|
+
*/
|
|
2845
|
+
error: (message, error) => {
|
|
2846
|
+
}
|
|
2847
|
+
};
|
|
2848
|
+
const warnMissingParams = (operation, params) => {
|
|
2849
|
+
logger.warn(`${operation}需要提供有效的参数: ${params.join(", ")}`);
|
|
2850
|
+
};
|
|
2851
|
+
const getTenants = async (apiBaseUrl, tenantId) => {
|
|
2852
|
+
if (!apiBaseUrl || !tenantId) {
|
|
2853
|
+
warnMissingParams("获取租户信息", ["apiBaseUrl", "tenantId"]);
|
|
2854
|
+
return [];
|
|
2855
|
+
}
|
|
2856
|
+
try {
|
|
2857
|
+
const url = `${apiBaseUrl}/api/v3/open-web/tenant/data-source-owner-tenants/`;
|
|
2858
|
+
const response = await fetch(url, {
|
|
2859
|
+
method: "GET",
|
|
2860
|
+
headers: {
|
|
2861
|
+
"x-bk-tenant-id": tenantId
|
|
2862
|
+
},
|
|
2863
|
+
credentials: "include"
|
|
2864
|
+
});
|
|
2865
|
+
if (!response.ok) {
|
|
2866
|
+
throw new Error(`${response.status} ${response.statusText}`);
|
|
2867
|
+
}
|
|
2868
|
+
const data = await response.json();
|
|
2869
|
+
return data.data || [];
|
|
2870
|
+
} catch (error) {
|
|
2871
|
+
return [];
|
|
2872
|
+
}
|
|
2873
|
+
};
|
|
2874
|
+
const searchUsers = async (params) => {
|
|
2875
|
+
const { apiBaseUrl, tenantId, keyword, enableMultiTenantMode = true } = params;
|
|
2876
|
+
if (!enableMultiTenantMode) {
|
|
2877
|
+
try {
|
|
2878
|
+
return await getUserList(apiBaseUrl, {
|
|
2879
|
+
keyword,
|
|
2880
|
+
pageSize: DEFAULT_PAGE_SIZE,
|
|
2881
|
+
page: 1
|
|
2882
|
+
});
|
|
2883
|
+
} catch {
|
|
2884
|
+
return [];
|
|
2885
|
+
}
|
|
2886
|
+
}
|
|
2887
|
+
if (!keyword || !apiBaseUrl || !tenantId) {
|
|
2888
|
+
warnMissingParams("搜索用户", ["apiBaseUrl", "tenantId", "keyword"]);
|
|
2889
|
+
return [];
|
|
2890
|
+
}
|
|
2891
|
+
try {
|
|
2892
|
+
const url = `${apiBaseUrl}/api/v3/open-web/tenant/users/-/search/?keyword=${encodeURIComponent(keyword)}`;
|
|
2893
|
+
const response = await fetch(url, {
|
|
2894
|
+
method: "GET",
|
|
2895
|
+
headers: {
|
|
2896
|
+
"x-bk-tenant-id": tenantId
|
|
2897
|
+
},
|
|
2898
|
+
credentials: "include"
|
|
2899
|
+
});
|
|
2900
|
+
if (!response.ok) {
|
|
2901
|
+
throw new Error(`${response.status} ${response.statusText}`);
|
|
2902
|
+
}
|
|
2903
|
+
const data = await response.json();
|
|
2904
|
+
return data.data || [];
|
|
2905
|
+
} catch (error) {
|
|
2906
|
+
return [];
|
|
2907
|
+
}
|
|
2908
|
+
};
|
|
2909
|
+
const lookupUsers = async (params) => {
|
|
2910
|
+
const { apiBaseUrl, tenantId, exactSearchKey = "bk_username", usersList = [], enableMultiTenantMode = true } = params;
|
|
2911
|
+
const users = usersList.filter(Boolean).map((user) => typeof user === "string" ? user.trim() : String(user).trim());
|
|
2912
|
+
if (!enableMultiTenantMode) {
|
|
2913
|
+
try {
|
|
2914
|
+
const userList = await getUserList(apiBaseUrl, { userIds: users });
|
|
2915
|
+
return users.map((user) => userList.find((u) => u.username === user)).filter(Boolean);
|
|
2916
|
+
} catch {
|
|
2917
|
+
return [];
|
|
2918
|
+
}
|
|
2919
|
+
}
|
|
2920
|
+
if (users.length === 0 || !apiBaseUrl || !tenantId) {
|
|
2921
|
+
warnMissingParams("批量查找用户", ["apiBaseUrl", "tenantId", "usersList"]);
|
|
2922
|
+
return [];
|
|
2923
|
+
}
|
|
2924
|
+
try {
|
|
2925
|
+
const url = `${apiBaseUrl}/api/v3/open-web/tenant/users/-/lookup/?lookups=${users.join(",")}&lookup_fields=${exactSearchKey}`;
|
|
2926
|
+
const response = await fetch(url, {
|
|
2927
|
+
method: "GET",
|
|
2928
|
+
headers: {
|
|
2929
|
+
"x-bk-tenant-id": tenantId
|
|
2930
|
+
},
|
|
2931
|
+
credentials: "include"
|
|
2932
|
+
});
|
|
2933
|
+
if (!response.ok) {
|
|
2934
|
+
throw new Error(`${response.status} ${response.statusText}`);
|
|
2935
|
+
}
|
|
2936
|
+
const data = await response.json();
|
|
2937
|
+
return data.data || [];
|
|
2938
|
+
} catch (error) {
|
|
2939
|
+
return [];
|
|
2940
|
+
}
|
|
2941
|
+
};
|
|
2942
|
+
const formatUsers = (users, enableMultiTenantMode = true) => {
|
|
2943
|
+
if (!users || !Array.isArray(users)) return [];
|
|
2944
|
+
if (!enableMultiTenantMode) {
|
|
2945
|
+
return users.map((user) => ({
|
|
2946
|
+
...user,
|
|
2947
|
+
id: user.username,
|
|
2948
|
+
name: `${user.display_name}(${user.username})`,
|
|
2949
|
+
type: user.data_source_type,
|
|
2950
|
+
tenantId: user.owner_tenant_id
|
|
2951
|
+
}));
|
|
2952
|
+
}
|
|
2953
|
+
return users.map((user) => ({
|
|
2954
|
+
id: user.bk_username,
|
|
2955
|
+
name: user.display_name,
|
|
2956
|
+
type: user.data_source_type,
|
|
2957
|
+
tenantId: user.owner_tenant_id,
|
|
2958
|
+
...user
|
|
2959
|
+
}));
|
|
2960
|
+
};
|
|
2961
|
+
const getUserList = async (url, params) => {
|
|
2962
|
+
const { userIds, keyword, pageSize = 20, page = 1, appCode = "bk-magicbox" } = params;
|
|
2963
|
+
const data = await jsonpRequest(url, {
|
|
2964
|
+
params: {
|
|
2965
|
+
exact_lookups: (userIds == null ? void 0 : userIds.join(",")) || void 0,
|
|
2966
|
+
fuzzy_lookups: keyword || void 0,
|
|
2967
|
+
page_size: Math.max((userIds == null ? void 0 : userIds.length) || 0, 20, Number(pageSize)).toString(),
|
|
2968
|
+
page: page.toString(),
|
|
2969
|
+
app_code: appCode
|
|
2970
|
+
}
|
|
2971
|
+
});
|
|
2972
|
+
return (data == null ? void 0 : data.results) || [];
|
|
2973
|
+
};
|
|
2974
|
+
const useCurrentUser = (options) => {
|
|
2975
|
+
const {
|
|
2976
|
+
apiBaseUrl,
|
|
2977
|
+
tenantId,
|
|
2978
|
+
currentUserId,
|
|
2979
|
+
exactSearchKey = DEFAULT_EXACT_SEARCH_KEY,
|
|
2980
|
+
enableMultiTenantMode = true
|
|
2981
|
+
} = options;
|
|
2982
|
+
const loading = ref(false);
|
|
2983
|
+
const fetchCurrentUser = async () => {
|
|
2984
|
+
if (!currentUserId) {
|
|
2985
|
+
return null;
|
|
2986
|
+
}
|
|
2987
|
+
loading.value = true;
|
|
2988
|
+
try {
|
|
2989
|
+
const result = await lookupUsers({
|
|
2990
|
+
apiBaseUrl,
|
|
2991
|
+
tenantId,
|
|
2992
|
+
exactSearchKey,
|
|
2993
|
+
usersList: [currentUserId],
|
|
2994
|
+
enableMultiTenantMode
|
|
2995
|
+
});
|
|
2996
|
+
const formattedUsers = formatUsers(result, enableMultiTenantMode);
|
|
2997
|
+
return formattedUsers.length > 0 ? formattedUsers[0] : null;
|
|
2998
|
+
} catch (error) {
|
|
2999
|
+
console.error("获取当前用户信息失败:", error);
|
|
3000
|
+
return null;
|
|
3001
|
+
} finally {
|
|
3002
|
+
loading.value = false;
|
|
3003
|
+
}
|
|
3004
|
+
};
|
|
3005
|
+
return {
|
|
3006
|
+
loading,
|
|
3007
|
+
fetchCurrentUser
|
|
3008
|
+
};
|
|
3009
|
+
};
|
|
3010
|
+
/*! js-cookie v3.0.5 | MIT */
|
|
3011
|
+
function assign(target) {
|
|
3012
|
+
for (var i = 1; i < arguments.length; i++) {
|
|
3013
|
+
var source = arguments[i];
|
|
3014
|
+
for (var key in source) {
|
|
3015
|
+
target[key] = source[key];
|
|
3016
|
+
}
|
|
3017
|
+
}
|
|
3018
|
+
return target;
|
|
3019
|
+
}
|
|
3020
|
+
var defaultConverter = {
|
|
3021
|
+
read: function(value) {
|
|
3022
|
+
if (value[0] === '"') {
|
|
3023
|
+
value = value.slice(1, -1);
|
|
3024
|
+
}
|
|
3025
|
+
return value.replace(/(%[\dA-F]{2})+/gi, decodeURIComponent);
|
|
3026
|
+
},
|
|
3027
|
+
write: function(value) {
|
|
3028
|
+
return encodeURIComponent(value).replace(
|
|
3029
|
+
/%(2[346BF]|3[AC-F]|40|5[BDE]|60|7[BCD])/g,
|
|
3030
|
+
decodeURIComponent
|
|
3031
|
+
);
|
|
3032
|
+
}
|
|
3033
|
+
};
|
|
3034
|
+
function init(converter, defaultAttributes) {
|
|
3035
|
+
function set(name, value, attributes) {
|
|
3036
|
+
if (typeof document === "undefined") {
|
|
3037
|
+
return;
|
|
3038
|
+
}
|
|
3039
|
+
attributes = assign({}, defaultAttributes, attributes);
|
|
3040
|
+
if (typeof attributes.expires === "number") {
|
|
3041
|
+
attributes.expires = new Date(Date.now() + attributes.expires * 864e5);
|
|
3042
|
+
}
|
|
3043
|
+
if (attributes.expires) {
|
|
3044
|
+
attributes.expires = attributes.expires.toUTCString();
|
|
3045
|
+
}
|
|
3046
|
+
name = encodeURIComponent(name).replace(/%(2[346B]|5E|60|7C)/g, decodeURIComponent).replace(/[()]/g, escape);
|
|
3047
|
+
var stringifiedAttributes = "";
|
|
3048
|
+
for (var attributeName in attributes) {
|
|
3049
|
+
if (!attributes[attributeName]) {
|
|
3050
|
+
continue;
|
|
3051
|
+
}
|
|
3052
|
+
stringifiedAttributes += "; " + attributeName;
|
|
3053
|
+
if (attributes[attributeName] === true) {
|
|
3054
|
+
continue;
|
|
3055
|
+
}
|
|
3056
|
+
stringifiedAttributes += "=" + attributes[attributeName].split(";")[0];
|
|
3057
|
+
}
|
|
3058
|
+
return document.cookie = name + "=" + converter.write(value, name) + stringifiedAttributes;
|
|
3059
|
+
}
|
|
3060
|
+
function get(name) {
|
|
3061
|
+
if (typeof document === "undefined" || arguments.length && !name) {
|
|
3062
|
+
return;
|
|
3063
|
+
}
|
|
3064
|
+
var cookies = document.cookie ? document.cookie.split("; ") : [];
|
|
3065
|
+
var jar = {};
|
|
3066
|
+
for (var i = 0; i < cookies.length; i++) {
|
|
3067
|
+
var parts = cookies[i].split("=");
|
|
3068
|
+
var value = parts.slice(1).join("=");
|
|
3069
|
+
try {
|
|
3070
|
+
var found = decodeURIComponent(parts[0]);
|
|
3071
|
+
jar[found] = converter.read(value, found);
|
|
3072
|
+
if (name === found) {
|
|
3073
|
+
break;
|
|
3074
|
+
}
|
|
3075
|
+
} catch (e) {
|
|
3076
|
+
}
|
|
3077
|
+
}
|
|
3078
|
+
return name ? jar[name] : jar;
|
|
3079
|
+
}
|
|
3080
|
+
return Object.create(
|
|
3081
|
+
{
|
|
3082
|
+
set,
|
|
3083
|
+
get,
|
|
3084
|
+
remove: function(name, attributes) {
|
|
3085
|
+
set(
|
|
3086
|
+
name,
|
|
3087
|
+
"",
|
|
3088
|
+
assign({}, attributes, {
|
|
3089
|
+
expires: -1
|
|
3090
|
+
})
|
|
3091
|
+
);
|
|
3092
|
+
},
|
|
3093
|
+
withAttributes: function(attributes) {
|
|
3094
|
+
return init(this.converter, assign({}, this.attributes, attributes));
|
|
3095
|
+
},
|
|
3096
|
+
withConverter: function(converter2) {
|
|
3097
|
+
return init(assign({}, this.converter, converter2), this.attributes);
|
|
3098
|
+
}
|
|
3099
|
+
},
|
|
3100
|
+
{
|
|
3101
|
+
attributes: { value: Object.freeze(defaultAttributes) },
|
|
3102
|
+
converter: { value: Object.freeze(converter) }
|
|
3103
|
+
}
|
|
3104
|
+
);
|
|
3105
|
+
}
|
|
3106
|
+
var api = init(defaultConverter, { path: "/" });
|
|
3107
|
+
const enUS = {
|
|
3108
|
+
我: "Me",
|
|
3109
|
+
请输入人员名称搜索: "Please enter the name of the user to search",
|
|
3110
|
+
用户群组: "User Group",
|
|
3111
|
+
无匹配人员: "No matching users",
|
|
3112
|
+
虚拟账号: "Virtual Account",
|
|
3113
|
+
用户: "User"
|
|
3114
|
+
};
|
|
3115
|
+
const zhCN = {
|
|
3116
|
+
我: "我",
|
|
3117
|
+
请输入人员名称搜索: "请输入人员名称搜索",
|
|
3118
|
+
用户群组: "用户群组",
|
|
3119
|
+
无匹配人员: "无匹配人员",
|
|
3120
|
+
虚拟账号: "虚拟账号",
|
|
3121
|
+
用户: "用户"
|
|
3122
|
+
};
|
|
3123
|
+
const BLUEKINNG_LANGUAGE = "blueking_language";
|
|
3124
|
+
const languageMap = {
|
|
3125
|
+
"en-US": enUS,
|
|
3126
|
+
"zh-CN": zhCN
|
|
3127
|
+
};
|
|
3128
|
+
const getPath = (obj, path, variables) => {
|
|
3129
|
+
const safePath = typeof path === "string" ? path : String(path ?? "");
|
|
3130
|
+
const pathStack = /^\w/.test(safePath) ? safePath.split(".") : [safePath];
|
|
3131
|
+
const { length } = pathStack;
|
|
3132
|
+
let target = obj;
|
|
3133
|
+
let i = 0;
|
|
3134
|
+
while (i <= length && target) {
|
|
3135
|
+
if (typeof target === "string") {
|
|
3136
|
+
return target;
|
|
3137
|
+
}
|
|
3138
|
+
if (variables) {
|
|
3139
|
+
target = target[pathStack[i]];
|
|
3140
|
+
if (typeof target === "string") {
|
|
3141
|
+
Object.keys(variables).forEach((key) => {
|
|
3142
|
+
target = target.replace(`{${key}}`, variables[key]);
|
|
3143
|
+
});
|
|
3144
|
+
}
|
|
3145
|
+
} else {
|
|
3146
|
+
target = target[pathStack[i]];
|
|
3147
|
+
}
|
|
3148
|
+
i = i + 1;
|
|
3149
|
+
if (!target) {
|
|
3150
|
+
return target;
|
|
3151
|
+
}
|
|
3152
|
+
}
|
|
3153
|
+
return target;
|
|
3154
|
+
};
|
|
3155
|
+
const useI18n = () => {
|
|
3156
|
+
let localeLanguage = "zh-CN";
|
|
3157
|
+
const bluekingLanguage = api.get(BLUEKINNG_LANGUAGE);
|
|
3158
|
+
if (bluekingLanguage && bluekingLanguage.toLowerCase() === "en") {
|
|
3159
|
+
localeLanguage = "en-US";
|
|
3160
|
+
}
|
|
3161
|
+
const languagePackage = languageMap[localeLanguage];
|
|
3162
|
+
const t = (path, variable) => {
|
|
3163
|
+
const value = getPath(languagePackage, path, variable);
|
|
3164
|
+
if (value === void 0) {
|
|
3165
|
+
console.warn(`缺少索引 * ${path} *`);
|
|
3166
|
+
}
|
|
3167
|
+
return value;
|
|
3168
|
+
};
|
|
3169
|
+
return {
|
|
3170
|
+
local: localeLanguage,
|
|
3171
|
+
t
|
|
3172
|
+
};
|
|
3173
|
+
};
|
|
3174
|
+
const useInputHandler = (options) => {
|
|
3175
|
+
const {
|
|
3176
|
+
apiBaseUrl,
|
|
3177
|
+
tenantId,
|
|
3178
|
+
searchQuery,
|
|
3179
|
+
selectedUsers,
|
|
3180
|
+
allowCreate = false,
|
|
3181
|
+
freePaste = false,
|
|
3182
|
+
enableMultiTenantMode = true,
|
|
3183
|
+
maxCount = 0,
|
|
3184
|
+
onAddUser,
|
|
3185
|
+
onBatchAddUsers
|
|
3186
|
+
} = options;
|
|
3187
|
+
const isPasting = ref(false);
|
|
3188
|
+
const createCustomUser = (loginName) => ({
|
|
3189
|
+
id: loginName,
|
|
3190
|
+
name: loginName,
|
|
3191
|
+
type: USER_TYPE.CUSTOM,
|
|
3192
|
+
tenantId: "",
|
|
3193
|
+
login_name: loginName
|
|
3194
|
+
});
|
|
3195
|
+
const parsePastedText = (text) => {
|
|
3196
|
+
const usersList = text.split(/[,,;\n\s]+/).filter(Boolean);
|
|
3197
|
+
return usersList.map((user) => user.trim().replace(/\s*\(.*?\)\s*/, "")).filter(Boolean);
|
|
3198
|
+
};
|
|
3199
|
+
const mergeUsers = (existingUsers, newUsers) => {
|
|
3200
|
+
const userMap = /* @__PURE__ */ new Map();
|
|
3201
|
+
for (const user of [...existingUsers, ...newUsers]) {
|
|
3202
|
+
if (!userMap.has(user.id)) {
|
|
3203
|
+
userMap.set(user.id, user);
|
|
3204
|
+
}
|
|
3205
|
+
}
|
|
3206
|
+
return Array.from(userMap.values());
|
|
3207
|
+
};
|
|
3208
|
+
const handleEnterCreate = (event) => {
|
|
3209
|
+
if (event.key !== "Enter" || !allowCreate || !searchQuery.value.trim()) {
|
|
3210
|
+
return;
|
|
3211
|
+
}
|
|
3212
|
+
const customUser = createCustomUser(searchQuery.value.trim());
|
|
3213
|
+
const isDuplicate = selectedUsers.value.some((user) => user.id === customUser.id);
|
|
3214
|
+
if (!isDuplicate) {
|
|
3215
|
+
onAddUser(customUser);
|
|
3216
|
+
}
|
|
3217
|
+
};
|
|
3218
|
+
const handlePaste = async (event) => {
|
|
3219
|
+
var _a, _b;
|
|
3220
|
+
event.preventDefault();
|
|
3221
|
+
const pastedText = (_b = (_a = event.clipboardData) == null ? void 0 : _a.getData("text")) == null ? void 0 : _b.trim();
|
|
3222
|
+
if (!pastedText) return;
|
|
3223
|
+
isPasting.value = true;
|
|
3224
|
+
try {
|
|
3225
|
+
const usersList = parsePastedText(pastedText);
|
|
3226
|
+
if (usersList.length === 0) return;
|
|
3227
|
+
const result = await lookupUsers({
|
|
3228
|
+
apiBaseUrl,
|
|
3229
|
+
tenantId,
|
|
3230
|
+
exactSearchKey: "login_name",
|
|
3231
|
+
usersList,
|
|
3232
|
+
enableMultiTenantMode
|
|
3233
|
+
});
|
|
3234
|
+
const formattedUsers = formatUsers(result, enableMultiTenantMode);
|
|
3235
|
+
if (onBatchAddUsers) {
|
|
3236
|
+
let mergedUsers = mergeUsers(selectedUsers.value, formattedUsers);
|
|
3237
|
+
if (freePaste) {
|
|
3238
|
+
for (const loginName of usersList) {
|
|
3239
|
+
const isDuplicate = mergedUsers.some((item) => item.login_name === loginName || item.id === loginName);
|
|
3240
|
+
if (!isDuplicate) {
|
|
3241
|
+
mergedUsers.push(createCustomUser(loginName));
|
|
3242
|
+
}
|
|
3243
|
+
}
|
|
3244
|
+
}
|
|
3245
|
+
if (maxCount > 0 && mergedUsers.length > maxCount) {
|
|
3246
|
+
mergedUsers = mergedUsers.slice(0, maxCount);
|
|
3247
|
+
}
|
|
3248
|
+
onBatchAddUsers(mergedUsers);
|
|
3249
|
+
} else {
|
|
3250
|
+
if (formattedUsers.length > 0) {
|
|
3251
|
+
onAddUser(formattedUsers[0]);
|
|
3252
|
+
} else if (freePaste && usersList.length > 0) {
|
|
3253
|
+
onAddUser(createCustomUser(usersList[0]));
|
|
3254
|
+
}
|
|
3255
|
+
}
|
|
3256
|
+
} catch (error) {
|
|
3257
|
+
console.error("精准查找用户失败:", error);
|
|
3258
|
+
} finally {
|
|
3259
|
+
isPasting.value = false;
|
|
3260
|
+
}
|
|
3261
|
+
};
|
|
3262
|
+
return {
|
|
3263
|
+
isPasting,
|
|
3264
|
+
parsePastedText,
|
|
3265
|
+
handleEnterCreate,
|
|
3266
|
+
handlePaste
|
|
3267
|
+
};
|
|
3268
|
+
};
|
|
3269
|
+
const useResizeObserver = (target, callback, options = {}) => {
|
|
3270
|
+
const { immediate = true } = options;
|
|
3271
|
+
let observer = null;
|
|
3272
|
+
const cleanup = () => {
|
|
3273
|
+
if (observer) {
|
|
3274
|
+
observer.disconnect();
|
|
3275
|
+
observer = null;
|
|
3276
|
+
}
|
|
3277
|
+
};
|
|
3278
|
+
const observe = () => {
|
|
3279
|
+
cleanup();
|
|
3280
|
+
if (!target.value) return;
|
|
3281
|
+
observer = new ResizeObserver((entries) => {
|
|
3282
|
+
for (const entry of entries) {
|
|
3283
|
+
callback(entry);
|
|
3284
|
+
}
|
|
3285
|
+
});
|
|
3286
|
+
observer.observe(target.value);
|
|
3287
|
+
if (immediate && target.value) {
|
|
3288
|
+
const rect = target.value.getBoundingClientRect();
|
|
3289
|
+
const entry = {
|
|
3290
|
+
target: target.value,
|
|
3291
|
+
contentRect: rect,
|
|
3292
|
+
borderBoxSize: [{ blockSize: rect.height, inlineSize: rect.width }],
|
|
3293
|
+
contentBoxSize: [{ blockSize: rect.height, inlineSize: rect.width }],
|
|
3294
|
+
devicePixelContentBoxSize: [{ blockSize: rect.height, inlineSize: rect.width }]
|
|
3295
|
+
};
|
|
3296
|
+
callback(entry);
|
|
3297
|
+
}
|
|
3298
|
+
};
|
|
3299
|
+
watch(target, observe, { immediate: true });
|
|
3300
|
+
onUnmounted(cleanup);
|
|
3301
|
+
return cleanup;
|
|
3302
|
+
};
|
|
3303
|
+
const useTenantData = (apiBaseUrl, tenantId, enableMultiTenantMode = true) => {
|
|
3304
|
+
const tenants = ref({});
|
|
3305
|
+
const loading = ref(false);
|
|
3306
|
+
const fetchTenants = async () => {
|
|
3307
|
+
if (!apiBaseUrl || !tenantId) {
|
|
3308
|
+
console.warn("获取租户需要提供有效的API基础URL和租户ID");
|
|
3309
|
+
return;
|
|
3310
|
+
}
|
|
3311
|
+
loading.value = true;
|
|
3312
|
+
try {
|
|
3313
|
+
const result = await getTenants(apiBaseUrl, tenantId);
|
|
3314
|
+
const tenantMap = {};
|
|
3315
|
+
result.forEach((item) => {
|
|
3316
|
+
if (item.id && item.name) {
|
|
3317
|
+
tenantMap[item.id] = item.name;
|
|
3318
|
+
}
|
|
3319
|
+
});
|
|
3320
|
+
tenants.value = tenantMap;
|
|
3321
|
+
} catch (error) {
|
|
3322
|
+
console.error("获取租户数据失败:", error);
|
|
3323
|
+
} finally {
|
|
3324
|
+
loading.value = false;
|
|
3325
|
+
}
|
|
3326
|
+
};
|
|
3327
|
+
onBeforeMount(() => {
|
|
3328
|
+
if (enableMultiTenantMode) {
|
|
3329
|
+
fetchTenants();
|
|
3330
|
+
}
|
|
3127
3331
|
});
|
|
3128
|
-
|
|
3129
|
-
|
|
3130
|
-
|
|
3332
|
+
return {
|
|
3333
|
+
tenants,
|
|
3334
|
+
loading,
|
|
3335
|
+
fetchTenants
|
|
3336
|
+
};
|
|
3337
|
+
};
|
|
3131
3338
|
const debounce = (fn, delay) => {
|
|
3132
3339
|
let timer = null;
|
|
3133
3340
|
return function(...args) {
|
|
@@ -3166,10 +3373,12 @@ const useUserSearch = (apiBaseUrl, tenantId, enableMultiTenantMode = true) => {
|
|
|
3166
3373
|
const performSearch = async (keyword) => {
|
|
3167
3374
|
if (!(keyword == null ? void 0 : keyword.length)) {
|
|
3168
3375
|
searchResults.value = [];
|
|
3376
|
+
loading.value = false;
|
|
3169
3377
|
return;
|
|
3170
3378
|
}
|
|
3171
3379
|
if (enableMultiTenantMode && (!apiBaseUrl || !tenantId)) {
|
|
3172
3380
|
console.warn("执行用户搜索需要提供有效的API基础URL和租户ID");
|
|
3381
|
+
loading.value = false;
|
|
3173
3382
|
return;
|
|
3174
3383
|
}
|
|
3175
3384
|
loading.value = true;
|
|
@@ -3188,14 +3397,16 @@ const useUserSearch = (apiBaseUrl, tenantId, enableMultiTenantMode = true) => {
|
|
|
3188
3397
|
loading.value = false;
|
|
3189
3398
|
}
|
|
3190
3399
|
};
|
|
3191
|
-
const debouncedSearch = debounce(performSearch,
|
|
3400
|
+
const debouncedSearch = debounce(performSearch, SEARCH_DEBOUNCE_DELAY);
|
|
3192
3401
|
const handleSearchInput = (value) => {
|
|
3193
|
-
|
|
3194
|
-
|
|
3402
|
+
loading.value = true;
|
|
3403
|
+
searchQuery.value = typeof value === "string" ? value.trim() : String(value ?? "").trim();
|
|
3404
|
+
debouncedSearch(searchQuery.value);
|
|
3195
3405
|
};
|
|
3196
3406
|
const clearSearch = () => {
|
|
3197
3407
|
searchQuery.value = "";
|
|
3198
3408
|
searchResults.value = [];
|
|
3409
|
+
loading.value = false;
|
|
3199
3410
|
};
|
|
3200
3411
|
return {
|
|
3201
3412
|
searchResults,
|
|
@@ -3206,26 +3417,57 @@ const useUserSearch = (apiBaseUrl, tenantId, enableMultiTenantMode = true) => {
|
|
|
3206
3417
|
clearSearch
|
|
3207
3418
|
};
|
|
3208
3419
|
};
|
|
3209
|
-
const
|
|
3420
|
+
const useUserSelection = (options) => {
|
|
3421
|
+
const { selectedUserIds, excludeUserIds, userGroup, searchQuery } = options;
|
|
3422
|
+
const createCustomUser = (loginName) => ({
|
|
3423
|
+
id: loginName,
|
|
3424
|
+
name: loginName,
|
|
3425
|
+
type: USER_TYPE.CUSTOM,
|
|
3426
|
+
tenantId: "",
|
|
3427
|
+
login_name: loginName
|
|
3428
|
+
});
|
|
3429
|
+
const isUserSelected = (userId) => {
|
|
3430
|
+
return selectedUserIds.value.includes(userId);
|
|
3431
|
+
};
|
|
3432
|
+
const filterOptions = (options2) => {
|
|
3433
|
+
return options2.filter((user) => !isUserSelected(user.id)).filter((user) => {
|
|
3434
|
+
var _a;
|
|
3435
|
+
return !((_a = excludeUserIds == null ? void 0 : excludeUserIds.value) == null ? void 0 : _a.includes(user.id));
|
|
3436
|
+
});
|
|
3437
|
+
};
|
|
3438
|
+
const filteredUserGroup = computed(() => {
|
|
3439
|
+
var _a;
|
|
3440
|
+
if (!((_a = userGroup == null ? void 0 : userGroup.value) == null ? void 0 : _a.length)) {
|
|
3441
|
+
return [];
|
|
3442
|
+
}
|
|
3443
|
+
return userGroup.value.filter((group) => {
|
|
3444
|
+
var _a2, _b;
|
|
3445
|
+
const isNotSelectedAndVisible = !isUserSelected(group.id) && !group.hidden;
|
|
3446
|
+
if (!isNotSelectedAndVisible) {
|
|
3447
|
+
return false;
|
|
3448
|
+
}
|
|
3449
|
+
const query = searchQuery.value.trim();
|
|
3450
|
+
if (!query) {
|
|
3451
|
+
return true;
|
|
3452
|
+
}
|
|
3453
|
+
return ((_a2 = group.id) == null ? void 0 : _a2.includes(query)) || ((_b = group.name) == null ? void 0 : _b.includes(query));
|
|
3454
|
+
});
|
|
3455
|
+
});
|
|
3456
|
+
return {
|
|
3457
|
+
createCustomUser,
|
|
3458
|
+
isUserSelected,
|
|
3459
|
+
filterOptions,
|
|
3460
|
+
filteredUserGroup
|
|
3461
|
+
};
|
|
3462
|
+
};
|
|
3463
|
+
const _sfc_main$3 = /* @__PURE__ */ defineComponent({
|
|
3210
3464
|
...{
|
|
3211
3465
|
name: "MeTag"
|
|
3212
3466
|
},
|
|
3213
3467
|
__name: "me-tag",
|
|
3214
3468
|
props: {
|
|
3215
|
-
|
|
3216
|
-
|
|
3217
|
-
*/
|
|
3218
|
-
currentUserId: {
|
|
3219
|
-
type: String,
|
|
3220
|
-
default: ""
|
|
3221
|
-
},
|
|
3222
|
-
/**
|
|
3223
|
-
* 是否禁用
|
|
3224
|
-
*/
|
|
3225
|
-
isDisabled: {
|
|
3226
|
-
type: Boolean,
|
|
3227
|
-
default: false
|
|
3228
|
-
}
|
|
3469
|
+
currentUserId: { default: "" },
|
|
3470
|
+
isDisabled: { type: Boolean, default: false }
|
|
3229
3471
|
},
|
|
3230
3472
|
emits: ["click"],
|
|
3231
3473
|
setup(__props, { emit: __emit }) {
|
|
@@ -3237,11 +3479,11 @@ const _sfc_main$5 = /* @__PURE__ */ defineComponent({
|
|
|
3237
3479
|
emit("click");
|
|
3238
3480
|
};
|
|
3239
3481
|
return (_ctx, _cache) => {
|
|
3240
|
-
return
|
|
3482
|
+
return _ctx.currentUserId ? (openBlock(), createElementBlock(
|
|
3241
3483
|
"div",
|
|
3242
3484
|
{
|
|
3243
3485
|
key: 0,
|
|
3244
|
-
class: normalizeClass(["me-tag", { disabled:
|
|
3486
|
+
class: normalizeClass(["me-tag", { disabled: _ctx.isDisabled }]),
|
|
3245
3487
|
onClick: withModifiers(handleClick, ["stop"])
|
|
3246
3488
|
},
|
|
3247
3489
|
toDisplayString(unref(t)("我")),
|
|
@@ -3258,7 +3500,10 @@ const _export_sfc = (sfc, props) => {
|
|
|
3258
3500
|
}
|
|
3259
3501
|
return target;
|
|
3260
3502
|
};
|
|
3261
|
-
const MeTag = /* @__PURE__ */ _export_sfc(_sfc_main$
|
|
3503
|
+
const MeTag = /* @__PURE__ */ _export_sfc(_sfc_main$3, [["__scopeId", "data-v-4f251ce1"]]);
|
|
3504
|
+
const UserGroupAvatar = "data:image/svg+xml,%3csvg%20viewBox='0%200%201024%201024'%20version='1.1'%20xmlns='http://www.w3.org/2000/svg'%20style='fill:%20%23A3C5FD;'%3e%3cpath%20fill-rule='evenodd'%20d='M405.7858816%20162.66256256C416.4461344%20160.6535248%20439.8986944%20159.44810208%20457.3815104%20160.25171712%20484.2453504%20161.05533248%20494.052784%20163.4661776%20516.226112%20174.7167888%20567.8217376%20200.43247136%20597.670448%20242.22045568%20606.6250624%20301.28616416%20617.711728%20374.415136%20593.4063488%20443.5260352%20535.8409792%20500.180896%20509.8299584%20525.8965792%20505.565856%20537.5489984%20514.0940608%20557.237568%20521.3430336%20572.9080608%20546.0748224%20586.5695168%20629.2248%20620.3213504%20691.054272%20645.2334208%20760.985536%20687.4232096%20767.8080992%20703.8973216%20774.6306624%20720.3714304%20784.8645056%20752.114224%20791.6870688%20777.4280992%20799.7888608%20807.1618592%20793.3927072%20818.8142784%20761.8383584%20832.4757344%20720.4765728%20850.155264%20669.3073536%20857.3878016%20546.9276416%20862.2094912%20392.9935776%20868.2366048%20227.12002944%20858.5932224%20162.30568672%20840.1100768%20134.5890272%20832.4757344%20108.15159776%20815.1980096%20100.47621504%20799.5275136%2093.6536528%20786.2678656%2094.08006304%20784.2588288%20105.59313696%20746.4889184%20116.67980096%20709.924432%20119.23826176%20705.5045504%20141.41158944%20685.4141728%20143.84821888%20683.2001312%20146.05397248%20681.2036448%20148.2232096%20679.3252416L152.13038144%20676.0501632C159.5946992%20670.0236288%20167.98497088%20664.6722176%20184.94031712%20656.0863296L191.29263904%20652.915344C215.97973152%20640.7492736%20256.51622304%20622.3959904%20329.458464%20589.3821696%20359.7335872%20575.3189056%20371.2466592%20563.6664896%20375.084352%20542.772496%20377.2164032%20530.316464%20374.6579424%20526.7001952%20345.2356416%20496.9664352%20295.34565344%20446.338688%20274.02514592%20396.9163584%20273.59873568%20331.0199232%20273.59873568%20291.24097568%20282.12693888%20265.52529312%20307.71154784%20228.15719168%20332.8697472%20191.19089792%20365.703328%20169.49329056%20405.7858816%20162.66256256ZM668.7713728%20226.60405184C756.683056%20211.50282816%20820.4190272%20263.09867616%20827.0124032%20354.9644544%20831.8475456%20416.6277856%20815.1443264%20461.931456%20770.3093664%20510.1714752%20752.287472%20529.4674848%20747.891888%20536.5986176%20748.3314464%20548.344016%20748.7710048%20555.8946272%20751.4083552%20565.123152%20754.485264%20568.8984576%20757.5621728%20572.2542848%20788.331264%20588.1944672%20823.0563776%20604.1346464%20944.3745024%20659.92528%20966.791984%20682.996592%20958.4403712%20744.6599232%20954.923904%20771.9260224%20956.6821376%20771.0870656%20890.308816%20787.0272448%20867.4517792%20792.8999456%20845.0343008%20798.3531648%20841.0782752%20799.6116%20835.3640128%20801.2895136%20833.1662208%20797.9336864%20830.5288704%20781.5740256%20824.3750528%20739.6261824%20812.0674176%20710.6821696%20790.0894976%20687.6108576%20752.287472%20647.3409248%20703.9360448%20619.6553504%20624.3759712%20593.6476864%20597.5629088%20584.4191616%20560.64%20550.8608864%20560.64%20534.920704%20560.64%20527.7895712%20569.8707264%20514.7857408%20589.6508544%20494.6507744%20620.859504%20461.931456%20639.7605152%20429.631616%20648.5516832%20394.8149056%20655.5846208%20366.7098496%20652.0681504%20283.23364096%20642.837424%20254.7091072%20635.3649312%20231.63779328%20634.4858144%20232.47675008%20668.7713728%20226.60405184Z'%3e%3c/path%3e%3c/svg%3e";
|
|
3505
|
+
const UserAvatar = "data:image/svg+xml,%3c?xml%20version='1.0'%20encoding='UTF-8'?%3e%3csvg%20width='32px'%20height='32px'%20viewBox='0%200%2032%2032'%20version='1.1'%20xmlns='http://www.w3.org/2000/svg'%20xmlns:xlink='http://www.w3.org/1999/xlink'%3e%3ctitle%3eIcon/用户%3c/title%3e%3cg%20id='Icon/用户'%20stroke='none'%20stroke-width='1'%20fill='none'%20fill-rule='evenodd'%3e%3cg%20id='user-(1)'%20transform='translate(3,%202)'%20fill='%23A3C5FD'%20fill-rule='nonzero'%3e%3cpath%20d='M13.0077612,27.9989067%20C10.3002732,27.9989067%207.59285518,28.0018792%204.88515705,27.997455%20C3.95018807,27.9959342%203.05044678,27.8282323%202.22816433,27.3628696%20C0.998627601,26.6672451%200.29953695,25.6114692%200.0864200465,24.2387462%20C-0.0656962495,23.259079%200.0147040645,22.4675755%200.0874005263,21.4879775%20C0.187970957,20.13461%200.423078914,19.3321844%200.863249688,18.0430358%20C1.22365046,16.9873982%201.73014453,16.0067633%202.49702917,15.175719%20C3.42254341,14.1726178%204.6014447,13.7297906%205.9255989,13.6440041%20C6.33292322,13.6073668%206.66741099,13.712025%206.9979768,13.9263185%20C7.58886318,14.3094892%208.17393665,14.7060014%208.79220674,15.0421658%20C10.1097776,15.758321%2011.5447274,16.1099698%2013.0616182,16.0930337%20C14.6806203,16.0750607%2016.2142496,15.63963%2017.592821,14.8169502%20C18.0555431,14.5407189%2018.5150436,14.256538%2018.9569652,13.9491996%20C19.3610679,13.6681294%2019.7808585,13.5749462%2020.274326,13.6337733%20C21.462472,13.7340074%2022.3872158,14.1103345%2023.2340106,14.8851094%20C23.902636,15.496952%2024.3685096,16.2520257%2024.7518119,17.0611566%20C25.272453,18.1598604%2025.5462904,18.7976948%2025.7441396,19.9861253%20C25.9499728,21.2233595%2026.0256808,22.2792045%2025.9924842,23.5308171%20C25.9627193,24.6543374%2025.6405577,25.6840525%2024.8535729,26.5307194%20C24.1686994,27.2671979%2023.3129402,27.7090574%2022.3211027,27.8808379%20C21.9232331,27.9495501%2021.5154185,27.9922014%2021.1120162,27.9935148%20C18.4104811,28.0036073%2015.7090862,27.9989067%2013.0077612,27.9989067%20L13.0077612,27.9989067%20Z%20M5.91775495,6.98479749%20C5.84814002,3.25685016%209.08684454,-0.00255470186%2013.0162355,1.5025268e-06%20C16.9117994,0.00256071584%2020.1304739,3.23452217%2020.1095656,7.04113598%20C20.0884528,10.8082092%2016.8998935,14.015354%2013.0058002,14.0149393%20C9.10134181,14.0145245%205.83322254,10.7695672%205.91775495,6.98479749%20Z'%20id='形状'%3e%3c/path%3e%3c/g%3e%3c/g%3e%3c/svg%3e";
|
|
3506
|
+
const VirtualAvatar = "data:image/svg+xml,%3c?xml%20version='1.0'%20encoding='UTF-8'?%3e%3csvg%20width='32px'%20height='32px'%20viewBox='0%200%2032%2032'%20version='1.1'%20xmlns='http://www.w3.org/2000/svg'%20xmlns:xlink='http://www.w3.org/1999/xlink'%3e%3ctitle%3eIcon/虚拟icon%3c/title%3e%3cg%20id='Icon/虚拟icon'%20stroke='none'%20stroke-width='1'%20fill='none'%20fill-rule='evenodd'%3e%3cpath%20d='M27.4705882,3%20C28.315259,3%2029,3.68474098%2029,4.52941178%20L29,22.4623054%20C29,23.3069762%2028.315259,23.9917172%2027.4705882,23.9917172%20L20.5882353,23.9917172%20L20.5882353,27.0244081%20L24.0294118,27.0244081%20C24.2405794,27.0244081%2024.4117647,27.1955933%2024.4117647,27.406761%20L24.4117647,28.617647%20C24.4117647,28.8288148%2024.2405795,29%2024.0294118,29%20L7.97058824,29%20C7.75942054,29%207.58823529,28.8288148%207.58823529,28.617647%20L7.58823529,27.406761%20C7.58823531,27.1955933%207.75942055,27.0244081%207.97058824,27.0244081%20L11.4117647,27.0244081%20L11.4117647,23.9917172%20L4.52941178,23.9917172%20C3.68474098,23.9917172%203,23.3069762%203,22.4623054%20L3,4.52941178%20C3,3.68474098%203.68474098,3%204.52941178,3%20L27.4705882,3%20Z%20M19,24%20L13,24%20L13,27%20L19,27%20L19,24%20Z%20M23.4117647,7%20L8.58823529,7%20C8.03595054,7%207.58823529,7.44771525%207.58823529,8%20L7.58823529,19%20C7.58823529,19.5522847%208.03595054,20%208.58823529,20%20L23.4117647,20%20C23.9640495,20%2024.4117647,19.5522847%2024.4117647,19%20L24.4117647,8%20C24.4117647,7.44771525%2023.9640495,7%2023.4117647,7%20Z%20M12,10%20C12.5522847,10%2013,10.4477153%2013,11%20L13,13%20C13,13.5522847%2012.5522847,14%2012,14%20C11.4477153,14%2011,13.5522847%2011,13%20L11,11%20C11,10.4477153%2011.4477153,10%2012,10%20Z%20M20,10%20C20.5522847,10%2021,10.4477153%2021,11%20L21,13%20C21,13.5522847%2020.5522847,14%2020,14%20C19.4477153,14%2019,13.5522847%2019,13%20L19,11%20C19,10.4477153%2019.4477153,10%2020,10%20Z%20M26,5%20C25.4477153,5%2025,5.44771525%2025,6%20C25,6.55228475%2025.4477153,7%2026,7%20C26.5522847,7%2027,6.55228475%2027,6%20C27,5.44771525%2026.5522847,5%2026,5%20Z'%20id='蒙版'%20fill='%23A3C5FD'%20fill-rule='nonzero'%3e%3c/path%3e%3c/g%3e%3c/svg%3e";
|
|
3262
3507
|
const UserRender = defineComponent({
|
|
3263
3508
|
name: "UserRender",
|
|
3264
3509
|
props: {
|
|
@@ -3277,23 +3522,63 @@ const UserRender = defineComponent({
|
|
|
3277
3522
|
render: {
|
|
3278
3523
|
type: Function,
|
|
3279
3524
|
required: false
|
|
3525
|
+
},
|
|
3526
|
+
hasAvatar: {
|
|
3527
|
+
type: Boolean,
|
|
3528
|
+
default: false
|
|
3529
|
+
},
|
|
3530
|
+
avatarBaseUrl: {
|
|
3531
|
+
type: String,
|
|
3532
|
+
default: ""
|
|
3280
3533
|
}
|
|
3281
3534
|
},
|
|
3282
3535
|
setup(props) {
|
|
3536
|
+
const getAvatarUrl = (user) => {
|
|
3537
|
+
if (user.type === "virtual") {
|
|
3538
|
+
return VirtualAvatar;
|
|
3539
|
+
}
|
|
3540
|
+
if (user.type === "userGroup") {
|
|
3541
|
+
return UserGroupAvatar;
|
|
3542
|
+
}
|
|
3543
|
+
if (!props.avatarBaseUrl) {
|
|
3544
|
+
return UserAvatar;
|
|
3545
|
+
}
|
|
3546
|
+
const loginName = user.login_name || user.bk_username || user.id;
|
|
3547
|
+
return `${props.avatarBaseUrl}${loginName}.png?default_when_absent=true`;
|
|
3548
|
+
};
|
|
3283
3549
|
const defaultRender = (h2, props2) => {
|
|
3284
|
-
return h2(
|
|
3285
|
-
|
|
3286
|
-
|
|
3287
|
-
|
|
3288
|
-
|
|
3550
|
+
return h2(
|
|
3551
|
+
"div",
|
|
3552
|
+
{
|
|
3553
|
+
style: {
|
|
3554
|
+
display: "flex",
|
|
3555
|
+
alignItems: "center"
|
|
3556
|
+
}
|
|
3557
|
+
},
|
|
3558
|
+
[
|
|
3559
|
+
props2.hasAvatar ? h2("img", {
|
|
3560
|
+
src: getAvatarUrl(props2.user),
|
|
3289
3561
|
style: {
|
|
3290
|
-
|
|
3291
|
-
|
|
3562
|
+
width: "20px",
|
|
3563
|
+
height: "20px",
|
|
3564
|
+
borderRadius: "50%",
|
|
3565
|
+
marginRight: "6px",
|
|
3566
|
+
flexShrink: 0
|
|
3292
3567
|
}
|
|
3293
|
-
},
|
|
3294
|
-
|
|
3295
|
-
|
|
3296
|
-
|
|
3568
|
+
}) : null,
|
|
3569
|
+
h2("span", props2.user.name),
|
|
3570
|
+
props2.user.tenantId !== props2.tenantId && props2.user.tenantId ? h2(
|
|
3571
|
+
"span",
|
|
3572
|
+
{
|
|
3573
|
+
style: {
|
|
3574
|
+
color: "#f59500",
|
|
3575
|
+
marginLeft: "4px"
|
|
3576
|
+
}
|
|
3577
|
+
},
|
|
3578
|
+
`@${props2.tenants[props2.user.tenantId] || props2.user.tenantId}`
|
|
3579
|
+
) : null
|
|
3580
|
+
]
|
|
3581
|
+
);
|
|
3297
3582
|
};
|
|
3298
3583
|
return () => {
|
|
3299
3584
|
try {
|
|
@@ -3305,106 +3590,38 @@ const UserRender = defineComponent({
|
|
|
3305
3590
|
};
|
|
3306
3591
|
}
|
|
3307
3592
|
});
|
|
3308
|
-
const _hoisted_1$
|
|
3593
|
+
const _hoisted_1$1 = {
|
|
3309
3594
|
key: 0,
|
|
3310
3595
|
class: "no-data"
|
|
3311
3596
|
};
|
|
3312
|
-
const _hoisted_2$
|
|
3597
|
+
const _hoisted_2$1 = { class: "group-name" };
|
|
3313
3598
|
const _hoisted_3$1 = { class: "group-count" };
|
|
3314
|
-
const _hoisted_4
|
|
3315
|
-
const _sfc_main$
|
|
3599
|
+
const _hoisted_4 = ["onClick"];
|
|
3600
|
+
const _sfc_main$2 = /* @__PURE__ */ defineComponent({
|
|
3316
3601
|
...{
|
|
3317
3602
|
name: "SelectionPopover"
|
|
3318
3603
|
},
|
|
3319
3604
|
__name: "selection-popover",
|
|
3320
3605
|
props: {
|
|
3321
|
-
|
|
3322
|
-
|
|
3323
|
-
|
|
3324
|
-
|
|
3325
|
-
|
|
3326
|
-
|
|
3327
|
-
},
|
|
3328
|
-
|
|
3329
|
-
|
|
3330
|
-
|
|
3331
|
-
|
|
3332
|
-
|
|
3333
|
-
|
|
3334
|
-
},
|
|
3335
|
-
/**
|
|
3336
|
-
* popover crossAxis 偏移量
|
|
3337
|
-
*/
|
|
3338
|
-
crossAxisOffset: {
|
|
3339
|
-
type: Number,
|
|
3340
|
-
default: 0
|
|
3341
|
-
},
|
|
3342
|
-
/**
|
|
3343
|
-
* 是否加载中
|
|
3344
|
-
*/
|
|
3345
|
-
loading: {
|
|
3346
|
-
type: Boolean,
|
|
3347
|
-
default: false
|
|
3348
|
-
},
|
|
3349
|
-
/**
|
|
3350
|
-
* 搜索结果选项
|
|
3351
|
-
*/
|
|
3352
|
-
options: {
|
|
3353
|
-
type: Array,
|
|
3354
|
-
default: () => []
|
|
3355
|
-
},
|
|
3356
|
-
/**
|
|
3357
|
-
* 搜索关键词
|
|
3358
|
-
*/
|
|
3359
|
-
searchQuery: {
|
|
3360
|
-
type: String,
|
|
3361
|
-
default: ""
|
|
3362
|
-
},
|
|
3363
|
-
/**
|
|
3364
|
-
* 当前租户ID
|
|
3365
|
-
*/
|
|
3366
|
-
tenantId: {
|
|
3367
|
-
type: String,
|
|
3368
|
-
default: ""
|
|
3369
|
-
},
|
|
3370
|
-
/**
|
|
3371
|
-
* 租户信息映射
|
|
3372
|
-
*/
|
|
3373
|
-
tenants: {
|
|
3374
|
-
type: Object,
|
|
3375
|
-
default: () => ({})
|
|
3376
|
-
},
|
|
3377
|
-
/**
|
|
3378
|
-
* 用户组
|
|
3379
|
-
*/
|
|
3380
|
-
userGroup: {
|
|
3381
|
-
type: Array,
|
|
3382
|
-
default: () => []
|
|
3383
|
-
},
|
|
3384
|
-
/**
|
|
3385
|
-
* 用户组名称
|
|
3386
|
-
*/
|
|
3387
|
-
userGroupName: {
|
|
3388
|
-
type: String,
|
|
3389
|
-
default: ""
|
|
3390
|
-
},
|
|
3391
|
-
/**
|
|
3392
|
-
* 无匹配人员时的提示文本
|
|
3393
|
-
*/
|
|
3394
|
-
emptyText: {
|
|
3395
|
-
type: String,
|
|
3396
|
-
default: ""
|
|
3397
|
-
},
|
|
3398
|
-
/**
|
|
3399
|
-
* 渲染列表项
|
|
3400
|
-
*/
|
|
3401
|
-
renderListItem: {
|
|
3402
|
-
type: Function
|
|
3403
|
-
}
|
|
3606
|
+
avatarBaseUrl: { default: "" },
|
|
3607
|
+
containerWidth: { default: "auto" },
|
|
3608
|
+
emptyText: { default: "" },
|
|
3609
|
+
hasAvatar: { type: Boolean, default: false },
|
|
3610
|
+
isShow: { type: Boolean, default: false },
|
|
3611
|
+
loading: { type: Boolean, default: false },
|
|
3612
|
+
options: { default: () => [] },
|
|
3613
|
+
renderListItem: {},
|
|
3614
|
+
searchQuery: { default: "" },
|
|
3615
|
+
tenantId: { default: "" },
|
|
3616
|
+
tenants: { default: () => ({}) },
|
|
3617
|
+
userGroup: { default: () => [] },
|
|
3618
|
+
userGroupName: { default: "" }
|
|
3404
3619
|
},
|
|
3405
|
-
emits: ["
|
|
3620
|
+
emits: ["click-outside", "select-user"],
|
|
3406
3621
|
setup(__props, { emit: __emit }) {
|
|
3407
3622
|
const { t } = useI18n();
|
|
3623
|
+
const slotContainerRef = ref(null);
|
|
3624
|
+
const contentContainerRef = ref(null);
|
|
3408
3625
|
const props = __props;
|
|
3409
3626
|
const emit = __emit;
|
|
3410
3627
|
const groupedUsers = computed(() => {
|
|
@@ -3413,11 +3630,11 @@ const _sfc_main$4 = /* @__PURE__ */ defineComponent({
|
|
|
3413
3630
|
groups[props.userGroupName] = props.userGroup.map((group) => ({
|
|
3414
3631
|
...group,
|
|
3415
3632
|
tenantId: "",
|
|
3416
|
-
type:
|
|
3633
|
+
type: USER_TYPE.USER_GROUP
|
|
3417
3634
|
}));
|
|
3418
3635
|
}
|
|
3419
3636
|
props.options.forEach((user) => {
|
|
3420
|
-
const groupName = user.data_source_type ===
|
|
3637
|
+
const groupName = user.data_source_type === USER_TYPE.VIRTUAL ? t("虚拟账号") : t("用户");
|
|
3421
3638
|
if (!groups[groupName]) {
|
|
3422
3639
|
groups[groupName] = [];
|
|
3423
3640
|
}
|
|
@@ -3429,114 +3646,150 @@ const _sfc_main$4 = /* @__PURE__ */ defineComponent({
|
|
|
3429
3646
|
emit("select-user", user);
|
|
3430
3647
|
};
|
|
3431
3648
|
const handleClickOutside = ({ event }) => {
|
|
3649
|
+
var _a, _b;
|
|
3650
|
+
const target = event.target;
|
|
3651
|
+
if ((_a = slotContainerRef.value) == null ? void 0 : _a.contains(target)) {
|
|
3652
|
+
return;
|
|
3653
|
+
}
|
|
3654
|
+
if ((_b = contentContainerRef.value) == null ? void 0 : _b.contains(target)) {
|
|
3655
|
+
return;
|
|
3656
|
+
}
|
|
3432
3657
|
emit("click-outside", event);
|
|
3433
3658
|
};
|
|
3434
3659
|
return (_ctx, _cache) => {
|
|
3435
3660
|
return openBlock(), createBlock(unref(Popover), {
|
|
3436
3661
|
arrow: false,
|
|
3437
3662
|
"ext-cls": "bk-user-selector-popover",
|
|
3438
|
-
"is-show":
|
|
3439
|
-
offset: { mainAxis: 4
|
|
3663
|
+
"is-show": _ctx.isShow,
|
|
3664
|
+
offset: { mainAxis: 4 },
|
|
3440
3665
|
placement: "bottom-start",
|
|
3441
3666
|
theme: "light",
|
|
3442
3667
|
trigger: "manual",
|
|
3443
|
-
width:
|
|
3668
|
+
width: _ctx.containerWidth,
|
|
3444
3669
|
onClickoutside: handleClickOutside
|
|
3445
3670
|
}, {
|
|
3446
3671
|
content: withCtx(() => [
|
|
3447
|
-
|
|
3448
|
-
|
|
3449
|
-
|
|
3450
|
-
|
|
3451
|
-
|
|
3452
|
-
|
|
3453
|
-
|
|
3454
|
-
|
|
3455
|
-
|
|
3456
|
-
|
|
3457
|
-
|
|
3458
|
-
|
|
3459
|
-
|
|
3460
|
-
|
|
3461
|
-
|
|
3462
|
-
|
|
3463
|
-
|
|
3464
|
-
{ key: 1 },
|
|
3465
|
-
renderList(groupedUsers.value, (group, groupName) => {
|
|
3466
|
-
return openBlock(), createElementBlock("div", {
|
|
3467
|
-
key: groupName,
|
|
3468
|
-
class: "user-group"
|
|
3469
|
-
}, [
|
|
3470
|
-
Object.keys(groupedUsers.value).length > 1 || group.some((user) => user.type === "userGroup") ? (openBlock(), createElementBlock("div", {
|
|
3471
|
-
key: 0,
|
|
3472
|
-
class: "group-header",
|
|
3473
|
-
onClick: _cache[0] || (_cache[0] = withModifiers(() => {
|
|
3474
|
-
}, ["prevent"]))
|
|
3475
|
-
}, [
|
|
3476
|
-
createElementVNode(
|
|
3477
|
-
"span",
|
|
3478
|
-
_hoisted_2$2,
|
|
3479
|
-
toDisplayString(groupName),
|
|
3480
|
-
1
|
|
3481
|
-
/* TEXT */
|
|
3482
|
-
),
|
|
3483
|
-
createElementVNode(
|
|
3484
|
-
"span",
|
|
3485
|
-
_hoisted_3$1,
|
|
3486
|
-
"(" + toDisplayString(group.length) + ")",
|
|
3487
|
-
1
|
|
3488
|
-
/* TEXT */
|
|
3489
|
-
)
|
|
3490
|
-
])) : createCommentVNode("v-if", true),
|
|
3491
|
-
(openBlock(true), createElementBlock(
|
|
3492
|
-
Fragment,
|
|
3672
|
+
createElementVNode(
|
|
3673
|
+
"div",
|
|
3674
|
+
{
|
|
3675
|
+
ref_key: "contentContainerRef",
|
|
3676
|
+
ref: contentContainerRef
|
|
3677
|
+
},
|
|
3678
|
+
[
|
|
3679
|
+
createVNode(unref(Loading), {
|
|
3680
|
+
class: "dropdown-content",
|
|
3681
|
+
loading: _ctx.loading,
|
|
3682
|
+
mode: "spin",
|
|
3683
|
+
size: "mini"
|
|
3684
|
+
}, {
|
|
3685
|
+
default: withCtx(() => [
|
|
3686
|
+
_ctx.options.length === 0 && _ctx.userGroup.length === 0 ? (openBlock(), createElementBlock("div", _hoisted_1$1, [
|
|
3687
|
+
createElementVNode(
|
|
3688
|
+
"span",
|
|
3493
3689
|
null,
|
|
3494
|
-
|
|
3495
|
-
|
|
3496
|
-
|
|
3497
|
-
|
|
3498
|
-
|
|
3690
|
+
toDisplayString(_ctx.emptyText),
|
|
3691
|
+
1
|
|
3692
|
+
/* TEXT */
|
|
3693
|
+
)
|
|
3694
|
+
])) : (openBlock(true), createElementBlock(
|
|
3695
|
+
Fragment,
|
|
3696
|
+
{ key: 1 },
|
|
3697
|
+
renderList(groupedUsers.value, (group, groupName) => {
|
|
3698
|
+
return openBlock(), createElementBlock("div", {
|
|
3699
|
+
key: groupName,
|
|
3700
|
+
class: "user-group"
|
|
3701
|
+
}, [
|
|
3702
|
+
Object.keys(groupedUsers.value).length > 1 || group.some((user) => user.type === "userGroup") ? (openBlock(), createElementBlock("div", {
|
|
3703
|
+
key: 0,
|
|
3704
|
+
class: "group-header",
|
|
3705
|
+
onClick: _cache[0] || (_cache[0] = withModifiers(() => {
|
|
3706
|
+
}, ["prevent"]))
|
|
3499
3707
|
}, [
|
|
3500
|
-
|
|
3501
|
-
|
|
3502
|
-
|
|
3503
|
-
|
|
3504
|
-
|
|
3505
|
-
|
|
3506
|
-
|
|
3507
|
-
|
|
3508
|
-
|
|
3509
|
-
|
|
3510
|
-
|
|
3511
|
-
|
|
3512
|
-
|
|
3513
|
-
|
|
3514
|
-
|
|
3515
|
-
|
|
3516
|
-
|
|
3517
|
-
|
|
3518
|
-
|
|
3519
|
-
|
|
3708
|
+
createElementVNode(
|
|
3709
|
+
"span",
|
|
3710
|
+
_hoisted_2$1,
|
|
3711
|
+
toDisplayString(groupName),
|
|
3712
|
+
1
|
|
3713
|
+
/* TEXT */
|
|
3714
|
+
),
|
|
3715
|
+
createElementVNode(
|
|
3716
|
+
"span",
|
|
3717
|
+
_hoisted_3$1,
|
|
3718
|
+
"(" + toDisplayString(group.length) + ")",
|
|
3719
|
+
1
|
|
3720
|
+
/* TEXT */
|
|
3721
|
+
)
|
|
3722
|
+
])) : createCommentVNode("v-if", true),
|
|
3723
|
+
(openBlock(true), createElementBlock(
|
|
3724
|
+
Fragment,
|
|
3725
|
+
null,
|
|
3726
|
+
renderList(group, (user) => {
|
|
3727
|
+
return openBlock(), createElementBlock("div", {
|
|
3728
|
+
key: user.id,
|
|
3729
|
+
class: "user-option",
|
|
3730
|
+
onClick: withModifiers(($event) => selectUser(user), ["prevent"]),
|
|
3731
|
+
onMousedown: _cache[1] || (_cache[1] = withModifiers(() => {
|
|
3732
|
+
}, ["prevent"]))
|
|
3733
|
+
}, [
|
|
3734
|
+
createVNode(unref(UserRender), {
|
|
3735
|
+
"avatar-base-url": _ctx.avatarBaseUrl,
|
|
3736
|
+
"has-avatar": _ctx.hasAvatar,
|
|
3737
|
+
render: _ctx.renderListItem,
|
|
3738
|
+
"tenant-id": _ctx.tenantId,
|
|
3739
|
+
tenants: _ctx.tenants,
|
|
3740
|
+
user
|
|
3741
|
+
}, null, 8, ["avatar-base-url", "has-avatar", "render", "tenant-id", "tenants", "user"])
|
|
3742
|
+
], 40, _hoisted_4);
|
|
3743
|
+
}),
|
|
3744
|
+
128
|
|
3745
|
+
/* KEYED_FRAGMENT */
|
|
3746
|
+
))
|
|
3747
|
+
]);
|
|
3748
|
+
}),
|
|
3749
|
+
128
|
|
3750
|
+
/* KEYED_FRAGMENT */
|
|
3751
|
+
))
|
|
3752
|
+
]),
|
|
3753
|
+
_: 1
|
|
3754
|
+
/* STABLE */
|
|
3755
|
+
}, 8, ["loading"])
|
|
3756
|
+
],
|
|
3757
|
+
512
|
|
3758
|
+
/* NEED_PATCH */
|
|
3759
|
+
)
|
|
3520
3760
|
]),
|
|
3521
3761
|
default: withCtx(() => [
|
|
3522
|
-
|
|
3762
|
+
createElementVNode(
|
|
3763
|
+
"div",
|
|
3764
|
+
{
|
|
3765
|
+
ref_key: "slotContainerRef",
|
|
3766
|
+
ref: slotContainerRef
|
|
3767
|
+
},
|
|
3768
|
+
[
|
|
3769
|
+
renderSlot(_ctx.$slots, "default", {}, void 0, true)
|
|
3770
|
+
],
|
|
3771
|
+
512
|
|
3772
|
+
/* NEED_PATCH */
|
|
3773
|
+
)
|
|
3523
3774
|
]),
|
|
3524
3775
|
_: 3
|
|
3525
3776
|
/* FORWARDED */
|
|
3526
|
-
}, 8, ["is-show", "
|
|
3777
|
+
}, 8, ["is-show", "width"]);
|
|
3527
3778
|
};
|
|
3528
3779
|
}
|
|
3529
3780
|
});
|
|
3530
|
-
const SelectionPopover = /* @__PURE__ */ _export_sfc(_sfc_main$
|
|
3531
|
-
const _sfc_main$
|
|
3781
|
+
const SelectionPopover = /* @__PURE__ */ _export_sfc(_sfc_main$2, [["__scopeId", "data-v-d5a338f0"]]);
|
|
3782
|
+
const _sfc_main$1 = /* @__PURE__ */ defineComponent({
|
|
3532
3783
|
...{
|
|
3533
3784
|
name: "UserTag"
|
|
3534
3785
|
},
|
|
3535
3786
|
__name: "user-tag",
|
|
3536
3787
|
props: {
|
|
3537
3788
|
active: { type: Boolean },
|
|
3789
|
+
avatarBaseUrl: {},
|
|
3538
3790
|
currentTenantId: {},
|
|
3539
3791
|
draggable: { type: Boolean },
|
|
3792
|
+
hasAvatar: { type: Boolean },
|
|
3540
3793
|
renderTag: { type: Function },
|
|
3541
3794
|
showTenant: { type: Boolean },
|
|
3542
3795
|
tenants: {},
|
|
@@ -3561,11 +3814,13 @@ const _sfc_main$3 = /* @__PURE__ */ defineComponent({
|
|
|
3561
3814
|
}, {
|
|
3562
3815
|
default: withCtx(() => [
|
|
3563
3816
|
createVNode(unref(UserRender), {
|
|
3817
|
+
"avatar-base-url": _ctx.avatarBaseUrl,
|
|
3818
|
+
"has-avatar": _ctx.hasAvatar,
|
|
3564
3819
|
render: _ctx.renderTag,
|
|
3565
3820
|
"tenant-id": _ctx.currentTenantId,
|
|
3566
3821
|
tenants: _ctx.tenants,
|
|
3567
3822
|
user: _ctx.user
|
|
3568
|
-
}, null, 8, ["render", "tenant-id", "tenants", "user"])
|
|
3823
|
+
}, null, 8, ["avatar-base-url", "has-avatar", "render", "tenant-id", "tenants", "user"])
|
|
3569
3824
|
]),
|
|
3570
3825
|
_: 1
|
|
3571
3826
|
/* STABLE */
|
|
@@ -3573,84 +3828,176 @@ const _sfc_main$3 = /* @__PURE__ */ defineComponent({
|
|
|
3573
3828
|
};
|
|
3574
3829
|
}
|
|
3575
3830
|
});
|
|
3576
|
-
const UserTag = /* @__PURE__ */ _export_sfc(_sfc_main$
|
|
3577
|
-
const _hoisted_1
|
|
3578
|
-
const _hoisted_2
|
|
3579
|
-
const _hoisted_3 =
|
|
3580
|
-
const
|
|
3581
|
-
const _sfc_main$2 = /* @__PURE__ */ defineComponent({
|
|
3831
|
+
const UserTag = /* @__PURE__ */ _export_sfc(_sfc_main$1, [["__scopeId", "data-v-1f2e0737"]]);
|
|
3832
|
+
const _hoisted_1 = ["placeholder"];
|
|
3833
|
+
const _hoisted_2 = { class: "hidden-users" };
|
|
3834
|
+
const _hoisted_3 = ["placeholder"];
|
|
3835
|
+
const _sfc_main = /* @__PURE__ */ defineComponent({
|
|
3582
3836
|
...{
|
|
3583
|
-
name: "
|
|
3837
|
+
name: "BkUserSelector"
|
|
3584
3838
|
},
|
|
3585
|
-
__name: "
|
|
3839
|
+
__name: "user-selector",
|
|
3586
3840
|
props: {
|
|
3587
3841
|
draggable: { type: Boolean, default: false },
|
|
3588
|
-
|
|
3589
|
-
modelValue: { default:
|
|
3590
|
-
|
|
3591
|
-
tenants: { default: () => ({}) },
|
|
3842
|
+
maxCount: { default: 0 },
|
|
3843
|
+
modelValue: { default: "" },
|
|
3844
|
+
multiple: { type: Boolean, default: false },
|
|
3592
3845
|
allowCreate: { type: Boolean, default: false },
|
|
3593
3846
|
apiBaseUrl: { default: "" },
|
|
3847
|
+
avatarBaseUrl: { default: "" },
|
|
3594
3848
|
currentUserId: { default: "" },
|
|
3595
|
-
disabled: { type: Boolean },
|
|
3849
|
+
disabled: { type: Boolean, default: false },
|
|
3596
3850
|
emptyText: { default: "" },
|
|
3597
|
-
enableMultiTenantMode: { type: Boolean },
|
|
3598
|
-
exactSearchKey: { default:
|
|
3851
|
+
enableMultiTenantMode: { type: Boolean, default: true },
|
|
3852
|
+
exactSearchKey: { default: DEFAULT_EXACT_SEARCH_KEY },
|
|
3599
3853
|
excludeUserIds: { default: () => [] },
|
|
3854
|
+
freePaste: { type: Boolean, default: false },
|
|
3855
|
+
hasAvatar: { type: Boolean, default: false },
|
|
3600
3856
|
placeholder: { default: "" },
|
|
3601
|
-
tenantId: { default: "" },
|
|
3602
|
-
userGroupName: { default: "" },
|
|
3603
3857
|
renderListItem: {},
|
|
3604
3858
|
renderTag: {},
|
|
3605
|
-
|
|
3859
|
+
tenantId: { default: "" },
|
|
3860
|
+
userGroup: { default: () => [] },
|
|
3861
|
+
userGroupName: { default: "" }
|
|
3606
3862
|
},
|
|
3607
|
-
emits: [
|
|
3608
|
-
"update:selectedUsers",
|
|
3609
|
-
"add-user",
|
|
3610
|
-
"remove-user",
|
|
3611
|
-
"dragStart",
|
|
3612
|
-
"dragEnd",
|
|
3613
|
-
"focus",
|
|
3614
|
-
"blur"
|
|
3615
|
-
],
|
|
3863
|
+
emits: ["blur", "change", "dragEnd", "dragStart", "focus", "update:modelValue"],
|
|
3616
3864
|
setup(__props, { emit: __emit }) {
|
|
3865
|
+
const { t } = useI18n();
|
|
3866
|
+
provideGlobalConfig({
|
|
3867
|
+
prefix: "bk"
|
|
3868
|
+
});
|
|
3617
3869
|
const props = __props;
|
|
3618
3870
|
const emit = __emit;
|
|
3871
|
+
const { tenants = {} } = useTenantData(props.apiBaseUrl, props.tenantId, props.enableMultiTenantMode);
|
|
3619
3872
|
const {
|
|
3620
3873
|
searchResults,
|
|
3621
3874
|
loading: searchLoading,
|
|
3622
3875
|
searchQuery,
|
|
3623
|
-
|
|
3876
|
+
clearSearch,
|
|
3624
3877
|
handleSearchInput
|
|
3625
3878
|
} = useUserSearch(props.apiBaseUrl, props.tenantId, props.enableMultiTenantMode);
|
|
3879
|
+
const { fetchCurrentUser } = useCurrentUser({
|
|
3880
|
+
apiBaseUrl: props.apiBaseUrl,
|
|
3881
|
+
tenantId: props.tenantId,
|
|
3882
|
+
currentUserId: props.currentUserId || "",
|
|
3883
|
+
exactSearchKey: props.exactSearchKey,
|
|
3884
|
+
enableMultiTenantMode: props.enableMultiTenantMode
|
|
3885
|
+
});
|
|
3626
3886
|
const containerRef = ref(null);
|
|
3627
|
-
const tagsContainerRef = ref(null);
|
|
3628
3887
|
const sortableContainerRef = ref(null);
|
|
3629
3888
|
const collapsedContainerRef = ref(null);
|
|
3630
3889
|
const inlineInputRef = ref(null);
|
|
3631
3890
|
const lastInputRef = ref(null);
|
|
3632
|
-
const collapsedInputRef = ref(null);
|
|
3633
3891
|
const isFocused = ref(false);
|
|
3634
|
-
const showDropdown = ref(false);
|
|
3635
3892
|
const activeTagIndex = ref(-1);
|
|
3636
3893
|
const sortableInstance = ref(null);
|
|
3637
3894
|
const visibleUsers = ref([]);
|
|
3638
3895
|
const hiddenCount = ref(0);
|
|
3639
|
-
const
|
|
3640
|
-
|
|
3896
|
+
const selectedUsers = ref([]);
|
|
3897
|
+
const showDropdown = computed(() => {
|
|
3898
|
+
return isFocused.value && (props.userGroup.length > 0 || searchQuery.value.trim() !== "");
|
|
3641
3899
|
});
|
|
3642
|
-
const
|
|
3643
|
-
|
|
3644
|
-
|
|
3645
|
-
|
|
3646
|
-
|
|
3647
|
-
|
|
3648
|
-
|
|
3649
|
-
|
|
3650
|
-
|
|
3900
|
+
const modelValueIds = computed(() => {
|
|
3901
|
+
if (props.multiple) {
|
|
3902
|
+
return Array.isArray(props.modelValue) ? props.modelValue : [];
|
|
3903
|
+
}
|
|
3904
|
+
return props.modelValue ? [props.modelValue] : [];
|
|
3905
|
+
});
|
|
3906
|
+
const computedPlaceholder = computed(() => props.placeholder || t("请输入人员名称搜索"));
|
|
3907
|
+
const computedUserGroupName = computed(() => props.userGroupName || t("用户群组"));
|
|
3908
|
+
const computedEmptyText = computed(() => props.emptyText || t("无匹配人员"));
|
|
3909
|
+
const selectedUserIds = computed(() => selectedUsers.value.map((user) => user.id));
|
|
3910
|
+
const isMaxCountReached = computed(() => {
|
|
3911
|
+
if (!props.maxCount || props.maxCount <= 0) return false;
|
|
3912
|
+
return selectedUsers.value.length >= props.maxCount;
|
|
3913
|
+
});
|
|
3914
|
+
const isMeTagDisabled = computed(
|
|
3915
|
+
() => isMaxCountReached.value || !!props.currentUserId && selectedUsers.value.some((user) => user[props.exactSearchKey] === props.currentUserId)
|
|
3916
|
+
);
|
|
3917
|
+
const userTagCommonProps = computed(() => ({
|
|
3918
|
+
avatarBaseUrl: props.avatarBaseUrl,
|
|
3919
|
+
currentTenantId: props.tenantId,
|
|
3920
|
+
hasAvatar: props.hasAvatar,
|
|
3921
|
+
renderTag: props.renderTag,
|
|
3922
|
+
tenants
|
|
3923
|
+
}));
|
|
3924
|
+
const { filteredUserGroup, filterOptions, createCustomUser } = useUserSelection({
|
|
3925
|
+
selectedUserIds,
|
|
3926
|
+
excludeUserIds: toRef(props, "excludeUserIds"),
|
|
3927
|
+
userGroup: toRef(props, "userGroup"),
|
|
3928
|
+
searchQuery
|
|
3929
|
+
});
|
|
3930
|
+
const { handlePaste } = useInputHandler({
|
|
3931
|
+
apiBaseUrl: props.apiBaseUrl,
|
|
3932
|
+
tenantId: props.tenantId,
|
|
3933
|
+
searchQuery,
|
|
3934
|
+
selectedUsers,
|
|
3935
|
+
allowCreate: props.allowCreate,
|
|
3936
|
+
freePaste: props.freePaste,
|
|
3937
|
+
enableMultiTenantMode: props.enableMultiTenantMode,
|
|
3938
|
+
maxCount: props.maxCount,
|
|
3939
|
+
onAddUser: addUser,
|
|
3940
|
+
onBatchAddUsers: props.multiple ? updateSelectedUsers : void 0
|
|
3941
|
+
});
|
|
3942
|
+
const displayOptions = computed(() => filterOptions(searchResults.value));
|
|
3943
|
+
const inputWidth = computed(() => {
|
|
3944
|
+
const query = searchQuery.value;
|
|
3945
|
+
if (!query) return "20px";
|
|
3946
|
+
const charWidth = query.split("").reduce((acc, char) => {
|
|
3947
|
+
return acc + (/[\u4e00-\u9fa5]/.test(char) ? 12 : 8);
|
|
3948
|
+
}, 0);
|
|
3949
|
+
return `${Math.max(20, charWidth + 4)}px`;
|
|
3651
3950
|
});
|
|
3951
|
+
const initSelectedUsers = async () => {
|
|
3952
|
+
const ids = modelValueIds.value;
|
|
3953
|
+
if (ids.length === 0) {
|
|
3954
|
+
selectedUsers.value = [];
|
|
3955
|
+
return;
|
|
3956
|
+
}
|
|
3957
|
+
let userGroupSelected = [];
|
|
3958
|
+
if (props.userGroup.length > 0) {
|
|
3959
|
+
const result = props.userGroup.filter((group) => ids.includes(group.id));
|
|
3960
|
+
userGroupSelected = result.map((group) => ({
|
|
3961
|
+
...group,
|
|
3962
|
+
tenantId: "",
|
|
3963
|
+
type: USER_TYPE.USER_GROUP
|
|
3964
|
+
}));
|
|
3965
|
+
}
|
|
3966
|
+
try {
|
|
3967
|
+
const result = await lookupUsers({
|
|
3968
|
+
apiBaseUrl: props.apiBaseUrl,
|
|
3969
|
+
tenantId: props.tenantId,
|
|
3970
|
+
exactSearchKey: "bk_username",
|
|
3971
|
+
usersList: ids,
|
|
3972
|
+
enableMultiTenantMode: props.enableMultiTenantMode
|
|
3973
|
+
});
|
|
3974
|
+
const selectedList = [...userGroupSelected, ...formatUsers(result, props.enableMultiTenantMode)];
|
|
3975
|
+
if (props.allowCreate) {
|
|
3976
|
+
selectedList.push(
|
|
3977
|
+
...ids.filter((id) => !selectedList.some((user) => user.id === id)).map((id) => ({ id, name: id, type: USER_TYPE.CUSTOM, tenantId: "" }))
|
|
3978
|
+
);
|
|
3979
|
+
}
|
|
3980
|
+
selectedUsers.value = ids.map((id) => selectedList.find((user) => user.id === id)).filter(Boolean);
|
|
3981
|
+
} catch (error) {
|
|
3982
|
+
console.error("获取选中用户信息失败:", error);
|
|
3983
|
+
selectedUsers.value = [];
|
|
3984
|
+
}
|
|
3985
|
+
};
|
|
3986
|
+
function updateSelectedUsers(users) {
|
|
3987
|
+
selectedUsers.value = users;
|
|
3988
|
+
if (props.multiple) {
|
|
3989
|
+
const ids = users.map((user) => user.id);
|
|
3990
|
+
emit("update:modelValue", ids);
|
|
3991
|
+
emit("change", users);
|
|
3992
|
+
} else {
|
|
3993
|
+
const user = users.length > 0 ? users[0] : null;
|
|
3994
|
+
const id = user ? user.id : "";
|
|
3995
|
+
emit("update:modelValue", id);
|
|
3996
|
+
emit("change", user);
|
|
3997
|
+
}
|
|
3998
|
+
}
|
|
3652
3999
|
const initSortable = () => {
|
|
3653
|
-
if (!props.draggable || !sortableContainerRef.value) return;
|
|
4000
|
+
if (!props.draggable || !props.multiple || !sortableContainerRef.value) return;
|
|
3654
4001
|
if (sortableInstance.value) {
|
|
3655
4002
|
sortableInstance.value.destroy();
|
|
3656
4003
|
}
|
|
@@ -3663,276 +4010,206 @@ const _sfc_main$2 = /* @__PURE__ */ defineComponent({
|
|
|
3663
4010
|
onEnd: (evt) => {
|
|
3664
4011
|
const { oldIndex, newIndex } = evt;
|
|
3665
4012
|
if (oldIndex === newIndex || oldIndex === void 0 || newIndex === void 0) return;
|
|
3666
|
-
const updatedUsers = [...
|
|
4013
|
+
const updatedUsers = [...selectedUsers.value];
|
|
3667
4014
|
const [movedUser] = updatedUsers.splice(oldIndex, 1);
|
|
3668
4015
|
updatedUsers.splice(newIndex, 0, movedUser);
|
|
3669
|
-
|
|
4016
|
+
updateSelectedUsers(updatedUsers);
|
|
3670
4017
|
emit("dragEnd", evt);
|
|
3671
4018
|
}
|
|
3672
4019
|
});
|
|
3673
4020
|
};
|
|
3674
4021
|
const calculateVisibleUsers = () => {
|
|
3675
|
-
if (!
|
|
4022
|
+
if (!selectedUsers.value.length) {
|
|
3676
4023
|
visibleUsers.value = [];
|
|
3677
4024
|
hiddenCount.value = 0;
|
|
3678
4025
|
return;
|
|
3679
4026
|
}
|
|
4027
|
+
if (!collapsedContainerRef.value) {
|
|
4028
|
+
visibleUsers.value = [...selectedUsers.value];
|
|
4029
|
+
hiddenCount.value = 0;
|
|
4030
|
+
return;
|
|
4031
|
+
}
|
|
3680
4032
|
const containerWidth = collapsedContainerRef.value.offsetWidth;
|
|
3681
4033
|
const tagElements = collapsedContainerRef.value.querySelectorAll(".user-tag");
|
|
4034
|
+
if (tagElements.length !== selectedUsers.value.length) {
|
|
4035
|
+
visibleUsers.value = [...selectedUsers.value];
|
|
4036
|
+
hiddenCount.value = 0;
|
|
4037
|
+
nextTick(calculateVisibleUsers);
|
|
4038
|
+
return;
|
|
4039
|
+
}
|
|
3682
4040
|
const visibleCount = calculateVisibleTags(
|
|
3683
4041
|
collapsedContainerRef.value,
|
|
3684
4042
|
tagElements,
|
|
3685
|
-
containerWidth -
|
|
3686
|
-
// 为输入框和更多标签预留空间
|
|
4043
|
+
containerWidth - RESERVED_SPACE_FOR_INPUT
|
|
3687
4044
|
);
|
|
3688
|
-
visibleUsers.value =
|
|
3689
|
-
hiddenCount.value = Math.max(0,
|
|
4045
|
+
visibleUsers.value = selectedUsers.value.slice(0, visibleCount);
|
|
4046
|
+
hiddenCount.value = Math.max(0, selectedUsers.value.length - visibleCount);
|
|
3690
4047
|
};
|
|
3691
4048
|
const handleFocus = () => {
|
|
3692
4049
|
isFocused.value = true;
|
|
3693
|
-
if (props.userGroup.length > 0) {
|
|
3694
|
-
showDropdown.value = true;
|
|
3695
|
-
} else {
|
|
3696
|
-
showDropdown.value = false;
|
|
3697
|
-
}
|
|
3698
4050
|
activeTagIndex.value = -1;
|
|
3699
4051
|
nextTick(() => {
|
|
3700
|
-
|
|
3701
|
-
|
|
3702
|
-
}
|
|
4052
|
+
var _a;
|
|
4053
|
+
return (_a = lastInputRef.value) == null ? void 0 : _a.focus();
|
|
3703
4054
|
});
|
|
3704
4055
|
};
|
|
4056
|
+
const scheduleVisibleUsersCalculation = () => {
|
|
4057
|
+
if (!isFocused.value) {
|
|
4058
|
+
nextTick(calculateVisibleUsers);
|
|
4059
|
+
}
|
|
4060
|
+
};
|
|
3705
4061
|
const handleClickOutside = (event) => {
|
|
3706
4062
|
const target = event.target;
|
|
3707
4063
|
const container = containerRef.value;
|
|
3708
|
-
if ((container == null ? void 0 : container.contains(target)) || container === target)
|
|
3709
|
-
|
|
3710
|
-
}
|
|
3711
|
-
if (isFocused.value) {
|
|
3712
|
-
emit("blur");
|
|
3713
|
-
}
|
|
4064
|
+
if ((container == null ? void 0 : container.contains(target)) || container === target) return;
|
|
4065
|
+
if (isFocused.value) emit("blur");
|
|
3714
4066
|
isFocused.value = false;
|
|
3715
|
-
showDropdown.value = false;
|
|
3716
4067
|
activeTagIndex.value = -1;
|
|
3717
|
-
|
|
3718
|
-
|
|
3719
|
-
calculateVisibleUsers();
|
|
3720
|
-
});
|
|
4068
|
+
clearSearch();
|
|
4069
|
+
scheduleVisibleUsersCalculation();
|
|
3721
4070
|
};
|
|
3722
4071
|
const handleContainerClick = () => {
|
|
3723
4072
|
activeTagIndex.value = -1;
|
|
3724
4073
|
nextTick(() => {
|
|
3725
|
-
|
|
3726
|
-
|
|
3727
|
-
}
|
|
4074
|
+
var _a;
|
|
4075
|
+
return (_a = lastInputRef.value) == null ? void 0 : _a.focus();
|
|
3728
4076
|
});
|
|
3729
4077
|
};
|
|
3730
4078
|
const handleTagClick = (index) => {
|
|
3731
4079
|
activeTagIndex.value = index;
|
|
3732
4080
|
nextTick(() => {
|
|
3733
4081
|
var _a;
|
|
3734
|
-
|
|
3735
|
-
|
|
3736
|
-
|
|
3737
|
-
}
|
|
3738
|
-
} else if ((_a = inlineInputRef.value) == null ? void 0 : _a[0]) {
|
|
3739
|
-
inlineInputRef.value[0].focus();
|
|
3740
|
-
}
|
|
4082
|
+
const isLastTag = index === selectedUsers.value.length - 1;
|
|
4083
|
+
const targetInput = isLastTag ? lastInputRef.value : (_a = inlineInputRef.value) == null ? void 0 : _a[0];
|
|
4084
|
+
targetInput == null ? void 0 : targetInput.focus();
|
|
3741
4085
|
});
|
|
3742
4086
|
};
|
|
3743
4087
|
const handleInputFocus = () => {
|
|
3744
4088
|
emit("focus");
|
|
3745
|
-
|
|
3746
|
-
isFocused.value = true;
|
|
3747
|
-
}
|
|
3748
|
-
if (searchQuery.value.length >= 1) {
|
|
3749
|
-
showDropdown.value = true;
|
|
3750
|
-
}
|
|
4089
|
+
isFocused.value = true;
|
|
3751
4090
|
};
|
|
3752
4091
|
const handleInput = () => {
|
|
3753
4092
|
handleSearchInput(searchQuery.value);
|
|
3754
|
-
if (searchQuery.value.length >= 1) {
|
|
3755
|
-
showDropdown.value = true;
|
|
3756
|
-
} else {
|
|
3757
|
-
showDropdown.value = false;
|
|
3758
|
-
}
|
|
3759
4093
|
};
|
|
3760
4094
|
const addCurrentUser = async () => {
|
|
3761
|
-
if (!props.currentUserId ||
|
|
3762
|
-
|
|
3763
|
-
|
|
3764
|
-
|
|
3765
|
-
tenantId: props.tenantId,
|
|
3766
|
-
exactSearchKey: props.exactSearchKey,
|
|
3767
|
-
usersList: [props.currentUserId],
|
|
3768
|
-
enableMultiTenantMode: props.enableMultiTenantMode
|
|
3769
|
-
});
|
|
3770
|
-
const formattedUsers = formatUsers(result, props.enableMultiTenantMode);
|
|
3771
|
-
if (formattedUsers.length > 0) {
|
|
3772
|
-
if (!props.selectedUsers.some((item) => item.id === formattedUsers[0].id)) {
|
|
3773
|
-
emit("update:selectedUsers", [...props.selectedUsers, formattedUsers[0]]);
|
|
3774
|
-
emit("add-user", formattedUsers[0]);
|
|
3775
|
-
}
|
|
3776
|
-
searchQuery.value = "";
|
|
3777
|
-
showDropdown.value = false;
|
|
3778
|
-
}
|
|
3779
|
-
} catch (error) {
|
|
3780
|
-
console.error("获取当前用户信息失败:", error);
|
|
4095
|
+
if (!props.currentUserId || selectedUsers.value.some((user) => user[props.exactSearchKey] === props.currentUserId))
|
|
4096
|
+
return;
|
|
4097
|
+
if (props.multiple && isMaxCountReached.value) {
|
|
4098
|
+
return;
|
|
3781
4099
|
}
|
|
3782
|
-
|
|
3783
|
-
|
|
3784
|
-
|
|
3785
|
-
|
|
3786
|
-
|
|
3787
|
-
|
|
3788
|
-
try {
|
|
3789
|
-
const usersList = pastedText.trim().split(/[,,;\n\s]+/).filter(Boolean);
|
|
3790
|
-
const users = usersList.map((user) => user.trim().replace(/\s*\(.*?\)\s*/, "")).filter((user) => user);
|
|
3791
|
-
const result = await lookupUsers({
|
|
3792
|
-
apiBaseUrl: props.apiBaseUrl,
|
|
3793
|
-
tenantId: props.tenantId,
|
|
3794
|
-
exactSearchKey: "login_name",
|
|
3795
|
-
usersList: users,
|
|
3796
|
-
enableMultiTenantMode: props.enableMultiTenantMode
|
|
3797
|
-
});
|
|
3798
|
-
const formattedUsers = formatUsers(result, props.enableMultiTenantMode);
|
|
3799
|
-
if (formattedUsers.length > 0) {
|
|
3800
|
-
const userMap = /* @__PURE__ */ new Map();
|
|
3801
|
-
[...props.selectedUsers, ...formattedUsers].forEach((user) => {
|
|
3802
|
-
if (!userMap.has(user.id)) {
|
|
3803
|
-
userMap.set(user.id, user);
|
|
3804
|
-
}
|
|
3805
|
-
});
|
|
3806
|
-
const updatedUsers = Array.from(userMap.values());
|
|
3807
|
-
if (props.freePaste) {
|
|
3808
|
-
const pastedUsers = usersList.map((user) => ({
|
|
3809
|
-
id: user,
|
|
3810
|
-
name: user,
|
|
3811
|
-
type: "custom",
|
|
3812
|
-
tenantId: "",
|
|
3813
|
-
login_name: user
|
|
3814
|
-
}));
|
|
3815
|
-
pastedUsers.forEach((user) => {
|
|
3816
|
-
if (!updatedUsers.some((item) => item.login_name === user.login_name)) {
|
|
3817
|
-
addUser(user);
|
|
3818
|
-
}
|
|
3819
|
-
});
|
|
3820
|
-
} else {
|
|
3821
|
-
emit("update:selectedUsers", updatedUsers);
|
|
3822
|
-
}
|
|
3823
|
-
} else {
|
|
3824
|
-
if (props.freePaste) {
|
|
3825
|
-
const pastedUsers = usersList.map((user) => ({
|
|
3826
|
-
id: user,
|
|
3827
|
-
name: user,
|
|
3828
|
-
type: "custom",
|
|
3829
|
-
tenantId: "",
|
|
3830
|
-
login_name: user
|
|
3831
|
-
}));
|
|
3832
|
-
pastedUsers.forEach((user) => {
|
|
3833
|
-
if (!props.selectedUsers.some((item) => item.login_name === user.login_name)) {
|
|
3834
|
-
addUser(user);
|
|
3835
|
-
}
|
|
3836
|
-
});
|
|
3837
|
-
}
|
|
3838
|
-
}
|
|
3839
|
-
} catch (error) {
|
|
3840
|
-
console.error("精准查找用户失败:", error);
|
|
4100
|
+
const currentUser = await fetchCurrentUser();
|
|
4101
|
+
if (currentUser) {
|
|
4102
|
+
if (!props.multiple) {
|
|
4103
|
+
updateSelectedUsers([currentUser]);
|
|
4104
|
+
} else if (!selectedUsers.value.some((item) => item.id === currentUser.id)) {
|
|
4105
|
+
updateSelectedUsers([...selectedUsers.value, currentUser]);
|
|
3841
4106
|
}
|
|
4107
|
+
clearSearch();
|
|
4108
|
+
isFocused.value = true;
|
|
4109
|
+
nextTick(() => {
|
|
4110
|
+
var _a;
|
|
4111
|
+
return (_a = lastInputRef.value) == null ? void 0 : _a.focus();
|
|
4112
|
+
});
|
|
3842
4113
|
}
|
|
3843
4114
|
};
|
|
4115
|
+
const onPaste = (event) => {
|
|
4116
|
+
handlePaste(event);
|
|
4117
|
+
};
|
|
3844
4118
|
const handleKeyDown = (event) => {
|
|
3845
|
-
if (event.key === "Backspace" && !searchQuery.value &&
|
|
4119
|
+
if (event.key === "Backspace" && !searchQuery.value && selectedUsers.value.length > 0) {
|
|
3846
4120
|
if (activeTagIndex.value >= 0) {
|
|
3847
|
-
const userToRemove =
|
|
4121
|
+
const userToRemove = selectedUsers.value[activeTagIndex.value];
|
|
3848
4122
|
removeUser(userToRemove);
|
|
3849
|
-
|
|
3850
|
-
activeTagIndex.value = activeTagIndex.value - 1;
|
|
3851
|
-
} else {
|
|
3852
|
-
activeTagIndex.value = -1;
|
|
3853
|
-
}
|
|
4123
|
+
activeTagIndex.value = activeTagIndex.value > 0 ? activeTagIndex.value - 1 : -1;
|
|
3854
4124
|
} else {
|
|
3855
|
-
const lastUser =
|
|
4125
|
+
const lastUser = selectedUsers.value[selectedUsers.value.length - 1];
|
|
3856
4126
|
removeUser(lastUser);
|
|
3857
4127
|
}
|
|
3858
|
-
} else if (event.key === "Enter" && props.allowCreate) {
|
|
3859
|
-
addUser(
|
|
3860
|
-
id: searchQuery.value,
|
|
3861
|
-
name: searchQuery.value,
|
|
3862
|
-
type: "custom",
|
|
3863
|
-
tenantId: "",
|
|
3864
|
-
login_name: searchQuery.value
|
|
3865
|
-
});
|
|
4128
|
+
} else if (event.key === "Enter" && props.allowCreate && searchQuery.value) {
|
|
4129
|
+
addUser(createCustomUser(searchQuery.value));
|
|
3866
4130
|
}
|
|
3867
4131
|
};
|
|
3868
|
-
|
|
4132
|
+
function addUser(user) {
|
|
3869
4133
|
if (!(user == null ? void 0 : user.id)) return;
|
|
3870
|
-
if (
|
|
4134
|
+
if (props.multiple && isMaxCountReached.value) {
|
|
4135
|
+
clearSearch();
|
|
4136
|
+
return;
|
|
4137
|
+
}
|
|
4138
|
+
if (!props.multiple) {
|
|
4139
|
+
updateSelectedUsers([user]);
|
|
4140
|
+
} else if (!selectedUsers.value.some((item) => item.id === user.id)) {
|
|
4141
|
+
const updatedUsers = activeTagIndex.value !== -1 ? [
|
|
4142
|
+
...selectedUsers.value.slice(0, activeTagIndex.value + 1),
|
|
4143
|
+
user,
|
|
4144
|
+
...selectedUsers.value.slice(activeTagIndex.value + 1)
|
|
4145
|
+
] : [...selectedUsers.value, user];
|
|
4146
|
+
updateSelectedUsers(updatedUsers);
|
|
4147
|
+
}
|
|
4148
|
+
if (activeTagIndex.value !== -1) {
|
|
4149
|
+
activeTagIndex.value = activeTagIndex.value + 1;
|
|
4150
|
+
}
|
|
4151
|
+
clearSearch();
|
|
4152
|
+
isFocused.value = true;
|
|
4153
|
+
nextTick(() => {
|
|
4154
|
+
var _a, _b, _c;
|
|
3871
4155
|
if (activeTagIndex.value !== -1) {
|
|
3872
|
-
|
|
3873
|
-
...props.selectedUsers.slice(0, activeTagIndex.value + 1),
|
|
3874
|
-
user,
|
|
3875
|
-
...props.selectedUsers.slice(activeTagIndex.value + 1)
|
|
3876
|
-
];
|
|
3877
|
-
emit("update:selectedUsers", updatedUsers);
|
|
4156
|
+
(_b = (_a = inlineInputRef.value) == null ? void 0 : _a[0]) == null ? void 0 : _b.focus();
|
|
3878
4157
|
} else {
|
|
3879
|
-
|
|
4158
|
+
(_c = lastInputRef.value) == null ? void 0 : _c.focus();
|
|
3880
4159
|
}
|
|
3881
|
-
emit("add-user", user);
|
|
3882
|
-
}
|
|
3883
|
-
searchQuery.value = "";
|
|
3884
|
-
showDropdown.value = false;
|
|
3885
|
-
nextTick(() => {
|
|
3886
|
-
var _a;
|
|
3887
|
-
(_a = lastInputRef.value) == null ? void 0 : _a.focus();
|
|
3888
4160
|
});
|
|
3889
|
-
}
|
|
4161
|
+
}
|
|
3890
4162
|
const removeUser = (user) => {
|
|
3891
4163
|
if (!(user == null ? void 0 : user.id)) return;
|
|
3892
|
-
const updatedUsers =
|
|
3893
|
-
|
|
3894
|
-
emit("remove-user", user);
|
|
4164
|
+
const updatedUsers = selectedUsers.value.filter((item) => item.id !== user.id);
|
|
4165
|
+
updateSelectedUsers(updatedUsers);
|
|
3895
4166
|
if (activeTagIndex.value >= updatedUsers.length) {
|
|
3896
|
-
activeTagIndex.value = updatedUsers.length - 1;
|
|
3897
|
-
}
|
|
3898
|
-
if (!isFocused.value) {
|
|
3899
|
-
nextTick(() => {
|
|
3900
|
-
calculateVisibleUsers();
|
|
3901
|
-
});
|
|
4167
|
+
activeTagIndex.value = updatedUsers.length - 1;
|
|
3902
4168
|
}
|
|
4169
|
+
scheduleVisibleUsersCalculation();
|
|
3903
4170
|
};
|
|
3904
|
-
const crossAxisOffset = ref(0);
|
|
3905
4171
|
watch(
|
|
3906
|
-
|
|
4172
|
+
selectedUsers,
|
|
3907
4173
|
() => {
|
|
3908
|
-
|
|
3909
|
-
if (!isFocused.value) {
|
|
3910
|
-
nextTick(() => {
|
|
3911
|
-
calculateVisibleUsers();
|
|
3912
|
-
});
|
|
3913
|
-
}
|
|
4174
|
+
scheduleVisibleUsersCalculation();
|
|
3914
4175
|
},
|
|
3915
4176
|
{ deep: true }
|
|
3916
4177
|
);
|
|
3917
4178
|
watch(isFocused, (newVal) => {
|
|
3918
4179
|
if (newVal) {
|
|
3919
|
-
nextTick(() =>
|
|
3920
|
-
initSortable();
|
|
3921
|
-
});
|
|
4180
|
+
nextTick(() => initSortable());
|
|
3922
4181
|
}
|
|
3923
4182
|
});
|
|
3924
|
-
|
|
3925
|
-
|
|
3926
|
-
|
|
4183
|
+
watch(
|
|
4184
|
+
() => props.userGroup,
|
|
4185
|
+
() => {
|
|
4186
|
+
initSelectedUsers();
|
|
3927
4187
|
}
|
|
3928
|
-
|
|
4188
|
+
);
|
|
4189
|
+
watch(
|
|
4190
|
+
() => props.modelValue,
|
|
4191
|
+
() => {
|
|
4192
|
+
const currentIds = selectedUsers.value.map((u) => u.id);
|
|
4193
|
+
const newIds = modelValueIds.value;
|
|
4194
|
+
if (currentIds.length !== newIds.length || !currentIds.every((id, index) => id === newIds[index])) {
|
|
4195
|
+
initSelectedUsers();
|
|
4196
|
+
}
|
|
4197
|
+
},
|
|
4198
|
+
{ deep: true }
|
|
4199
|
+
);
|
|
4200
|
+
useResizeObserver(containerRef, () => {
|
|
4201
|
+
scheduleVisibleUsersCalculation();
|
|
4202
|
+
});
|
|
4203
|
+
onBeforeMount(() => {
|
|
4204
|
+
initSelectedUsers();
|
|
4205
|
+
});
|
|
3929
4206
|
onMounted(() => {
|
|
3930
4207
|
initSortable();
|
|
3931
|
-
calculateVisibleUsers
|
|
3932
|
-
|
|
3933
|
-
|
|
3934
|
-
|
|
3935
|
-
|
|
4208
|
+
nextTick(calculateVisibleUsers);
|
|
4209
|
+
});
|
|
4210
|
+
onUnmounted(() => {
|
|
4211
|
+
var _a;
|
|
4212
|
+
(_a = sortableInstance.value) == null ? void 0 : _a.destroy();
|
|
3936
4213
|
});
|
|
3937
4214
|
return (_ctx, _cache) => {
|
|
3938
4215
|
return openBlock(), createElementBlock(
|
|
@@ -3940,34 +4217,32 @@ const _sfc_main$2 = /* @__PURE__ */ defineComponent({
|
|
|
3940
4217
|
{
|
|
3941
4218
|
ref_key: "containerRef",
|
|
3942
4219
|
ref: containerRef,
|
|
3943
|
-
class: normalizeClass(["
|
|
4220
|
+
class: normalizeClass(["bk-user-selector", { "is-disabled": _ctx.disabled }])
|
|
3944
4221
|
},
|
|
3945
4222
|
[
|
|
3946
4223
|
createCommentVNode(" 下拉选项列表 "),
|
|
3947
4224
|
createVNode(SelectionPopover, {
|
|
4225
|
+
"avatar-base-url": _ctx.avatarBaseUrl,
|
|
3948
4226
|
"container-width": containerRef.value ? containerRef.value.offsetWidth : "auto",
|
|
3949
|
-
"
|
|
3950
|
-
"
|
|
4227
|
+
"empty-text": computedEmptyText.value,
|
|
4228
|
+
"has-avatar": _ctx.hasAvatar,
|
|
3951
4229
|
"is-show": showDropdown.value,
|
|
3952
4230
|
loading: unref(searchLoading),
|
|
3953
|
-
options:
|
|
4231
|
+
options: displayOptions.value,
|
|
3954
4232
|
"render-list-item": _ctx.renderListItem,
|
|
3955
4233
|
"search-query": unref(searchQuery),
|
|
3956
4234
|
"tenant-id": _ctx.tenantId,
|
|
3957
|
-
tenants:
|
|
3958
|
-
"user-group":
|
|
3959
|
-
"user-group-name":
|
|
4235
|
+
tenants: unref(tenants),
|
|
4236
|
+
"user-group": unref(filteredUserGroup),
|
|
4237
|
+
"user-group-name": computedUserGroupName.value,
|
|
3960
4238
|
onClickOutside: handleClickOutside,
|
|
3961
4239
|
onSelectUser: addUser
|
|
3962
4240
|
}, {
|
|
3963
4241
|
default: withCtx(() => [
|
|
3964
4242
|
createCommentVNode(" 聚焦状态 - 可编辑模式 "),
|
|
3965
|
-
|
|
4243
|
+
withDirectives(createElementVNode(
|
|
3966
4244
|
"div",
|
|
3967
4245
|
{
|
|
3968
|
-
key: 0,
|
|
3969
|
-
ref_key: "tagsContainerRef",
|
|
3970
|
-
ref: tagsContainerRef,
|
|
3971
4246
|
class: "tags-container focused",
|
|
3972
4247
|
onClick: withModifiers(handleContainerClick, ["stop"])
|
|
3973
4248
|
},
|
|
@@ -3984,24 +4259,20 @@ const _sfc_main$2 = /* @__PURE__ */ defineComponent({
|
|
|
3984
4259
|
(openBlock(true), createElementBlock(
|
|
3985
4260
|
Fragment,
|
|
3986
4261
|
null,
|
|
3987
|
-
renderList(
|
|
4262
|
+
renderList(selectedUsers.value, (user, index) => {
|
|
3988
4263
|
return openBlock(), createElementBlock("div", {
|
|
3989
4264
|
key: user.id,
|
|
3990
|
-
class: "tag-wrapper"
|
|
3991
|
-
onClick: withModifiers(($event) => handleTagClick(index), ["stop"])
|
|
4265
|
+
class: "tag-wrapper"
|
|
3992
4266
|
}, [
|
|
3993
|
-
createVNode(UserTag, {
|
|
4267
|
+
createVNode(UserTag, mergeProps({ ref_for: true }, userTagCommonProps.value, {
|
|
3994
4268
|
active: index === activeTagIndex.value,
|
|
3995
|
-
|
|
3996
|
-
draggable: _ctx.draggable,
|
|
3997
|
-
"render-tag": _ctx.renderTag,
|
|
3998
|
-
tenants: _ctx.tenants,
|
|
4269
|
+
draggable: _ctx.draggable && _ctx.multiple,
|
|
3999
4270
|
user,
|
|
4000
4271
|
onClick: ($event) => handleTagClick(index),
|
|
4001
4272
|
onClose: ($event) => removeUser(user)
|
|
4002
|
-
}, null,
|
|
4273
|
+
}), null, 16, ["active", "draggable", "user", "onClick", "onClose"]),
|
|
4003
4274
|
createCommentVNode(" 在当前激活标签后插入输入框 "),
|
|
4004
|
-
index === activeTagIndex.value && activeTagIndex.value !==
|
|
4275
|
+
index === activeTagIndex.value && activeTagIndex.value !== selectedUsers.value.length - 1 ? withDirectives((openBlock(), createElementBlock(
|
|
4005
4276
|
"input",
|
|
4006
4277
|
{
|
|
4007
4278
|
key: 0,
|
|
@@ -4009,42 +4280,45 @@ const _sfc_main$2 = /* @__PURE__ */ defineComponent({
|
|
|
4009
4280
|
ref_key: "inlineInputRef",
|
|
4010
4281
|
ref: inlineInputRef,
|
|
4011
4282
|
"onUpdate:modelValue": _cache[0] || (_cache[0] = ($event) => isRef(searchQuery) ? searchQuery.value = $event : null),
|
|
4012
|
-
|
|
4283
|
+
autofocus: "",
|
|
4284
|
+
class: "search-input input-inline",
|
|
4285
|
+
style: normalizeStyle({ width: inputWidth.value }),
|
|
4013
4286
|
onFocus: handleInputFocus,
|
|
4014
4287
|
onInput: handleInput,
|
|
4015
4288
|
onKeydown: handleKeyDown,
|
|
4016
|
-
onPaste
|
|
4289
|
+
onPaste
|
|
4017
4290
|
},
|
|
4018
4291
|
null,
|
|
4019
|
-
|
|
4020
|
-
/*
|
|
4292
|
+
36
|
|
4293
|
+
/* STYLE, NEED_HYDRATION */
|
|
4021
4294
|
)), [
|
|
4022
4295
|
[vModelText, unref(searchQuery)]
|
|
4023
4296
|
]) : createCommentVNode("v-if", true)
|
|
4024
|
-
]
|
|
4297
|
+
]);
|
|
4025
4298
|
}),
|
|
4026
4299
|
128
|
|
4027
4300
|
/* KEYED_FRAGMENT */
|
|
4028
4301
|
)),
|
|
4029
4302
|
createCommentVNode(" 最后一个输入框 "),
|
|
4030
|
-
activeTagIndex.value === -1 || activeTagIndex.value ===
|
|
4303
|
+
activeTagIndex.value === -1 || activeTagIndex.value === selectedUsers.value.length - 1 ? withDirectives((openBlock(), createElementBlock("input", {
|
|
4031
4304
|
key: 0,
|
|
4032
4305
|
ref_key: "lastInputRef",
|
|
4033
4306
|
ref: lastInputRef,
|
|
4034
4307
|
"onUpdate:modelValue": _cache[1] || (_cache[1] = ($event) => isRef(searchQuery) ? searchQuery.value = $event : null),
|
|
4035
|
-
|
|
4036
|
-
|
|
4308
|
+
autofocus: "",
|
|
4309
|
+
class: "search-input input-last",
|
|
4310
|
+
placeholder: !selectedUsers.value.length ? computedPlaceholder.value : "",
|
|
4037
4311
|
onFocus: handleInputFocus,
|
|
4038
4312
|
onInput: handleInput,
|
|
4039
4313
|
onKeydown: handleKeyDown,
|
|
4040
|
-
onPaste
|
|
4041
|
-
}, null, 40,
|
|
4314
|
+
onPaste
|
|
4315
|
+
}, null, 40, _hoisted_1)), [
|
|
4042
4316
|
[vModelText, unref(searchQuery)]
|
|
4043
4317
|
]) : createCommentVNode("v-if", true),
|
|
4044
4318
|
createCommentVNode(' "我"标签 '),
|
|
4045
4319
|
createVNode(MeTag, {
|
|
4046
4320
|
"current-user-id": _ctx.currentUserId,
|
|
4047
|
-
"is-disabled":
|
|
4321
|
+
"is-disabled": isMeTagDisabled.value,
|
|
4048
4322
|
onClick: addCurrentUser
|
|
4049
4323
|
}, null, 8, ["current-user-id", "is-disabled"])
|
|
4050
4324
|
],
|
|
@@ -4054,580 +4328,102 @@ const _sfc_main$2 = /* @__PURE__ */ defineComponent({
|
|
|
4054
4328
|
],
|
|
4055
4329
|
512
|
|
4056
4330
|
/* NEED_PATCH */
|
|
4057
|
-
)
|
|
4058
|
-
|
|
4059
|
-
|
|
4331
|
+
), [
|
|
4332
|
+
[vShow, isFocused.value]
|
|
4333
|
+
]),
|
|
4334
|
+
createCommentVNode(" 未聚焦状态 - 只读展示模式 "),
|
|
4335
|
+
withDirectives(createElementVNode(
|
|
4336
|
+
"div",
|
|
4337
|
+
{
|
|
4338
|
+
ref_key: "collapsedContainerRef",
|
|
4339
|
+
ref: collapsedContainerRef,
|
|
4340
|
+
class: "tags-container tags-container-collapsed",
|
|
4341
|
+
onClick: withModifiers(handleFocus, ["stop"])
|
|
4342
|
+
},
|
|
4060
4343
|
[
|
|
4061
|
-
|
|
4062
|
-
|
|
4063
|
-
|
|
4064
|
-
{
|
|
4065
|
-
|
|
4066
|
-
|
|
4067
|
-
|
|
4068
|
-
|
|
4069
|
-
|
|
4070
|
-
|
|
4071
|
-
|
|
4072
|
-
|
|
4073
|
-
|
|
4074
|
-
|
|
4075
|
-
|
|
4076
|
-
|
|
4077
|
-
|
|
4078
|
-
|
|
4079
|
-
|
|
4080
|
-
|
|
4081
|
-
|
|
4082
|
-
|
|
4083
|
-
|
|
4084
|
-
|
|
4085
|
-
|
|
4086
|
-
|
|
4087
|
-
|
|
4088
|
-
|
|
4089
|
-
|
|
4090
|
-
|
|
4091
|
-
|
|
4092
|
-
|
|
4093
|
-
|
|
4094
|
-
|
|
4095
|
-
|
|
4096
|
-
|
|
4097
|
-
|
|
4098
|
-
|
|
4099
|
-
|
|
4100
|
-
|
|
4101
|
-
|
|
4102
|
-
|
|
4103
|
-
|
|
4104
|
-
|
|
4105
|
-
}, null, 8, ["tenant-id", "tenants", "user"]);
|
|
4106
|
-
}),
|
|
4107
|
-
128
|
|
4108
|
-
/* KEYED_FRAGMENT */
|
|
4109
|
-
))
|
|
4110
|
-
])
|
|
4111
|
-
]),
|
|
4344
|
+
(openBlock(true), createElementBlock(
|
|
4345
|
+
Fragment,
|
|
4346
|
+
null,
|
|
4347
|
+
renderList(visibleUsers.value, (user) => {
|
|
4348
|
+
return openBlock(), createBlock(UserTag, mergeProps({
|
|
4349
|
+
key: user.id,
|
|
4350
|
+
ref_for: true
|
|
4351
|
+
}, userTagCommonProps.value, {
|
|
4352
|
+
"show-tenant": true,
|
|
4353
|
+
user,
|
|
4354
|
+
onClick: handleFocus,
|
|
4355
|
+
onClose: ($event) => removeUser(user)
|
|
4356
|
+
}), null, 16, ["user", "onClose"]);
|
|
4357
|
+
}),
|
|
4358
|
+
128
|
|
4359
|
+
/* KEYED_FRAGMENT */
|
|
4360
|
+
)),
|
|
4361
|
+
createCommentVNode(" 显示折叠标签数量 "),
|
|
4362
|
+
hiddenCount.value > 0 ? (openBlock(), createBlock(unref(Popover), {
|
|
4363
|
+
key: 0,
|
|
4364
|
+
placement: "top"
|
|
4365
|
+
}, {
|
|
4366
|
+
content: withCtx(() => [
|
|
4367
|
+
createElementVNode("div", _hoisted_2, [
|
|
4368
|
+
(openBlock(true), createElementBlock(
|
|
4369
|
+
Fragment,
|
|
4370
|
+
null,
|
|
4371
|
+
renderList(selectedUsers.value.slice(visibleUsers.value.length), (user) => {
|
|
4372
|
+
return openBlock(), createBlock(unref(UserRender), {
|
|
4373
|
+
key: user.id,
|
|
4374
|
+
"avatar-base-url": _ctx.avatarBaseUrl,
|
|
4375
|
+
"has-avatar": _ctx.hasAvatar,
|
|
4376
|
+
"tenant-id": _ctx.tenantId,
|
|
4377
|
+
tenants: unref(tenants),
|
|
4378
|
+
user
|
|
4379
|
+
}, null, 8, ["avatar-base-url", "has-avatar", "tenant-id", "tenants", "user"]);
|
|
4380
|
+
}),
|
|
4381
|
+
128
|
|
4382
|
+
/* KEYED_FRAGMENT */
|
|
4383
|
+
))
|
|
4384
|
+
])
|
|
4385
|
+
]),
|
|
4386
|
+
default: withCtx(() => [
|
|
4387
|
+
createVNode(unref(Tag), null, {
|
|
4112
4388
|
default: withCtx(() => [
|
|
4113
|
-
|
|
4114
|
-
|
|
4115
|
-
|
|
4116
|
-
|
|
4117
|
-
|
|
4118
|
-
/* TEXT */
|
|
4119
|
-
)
|
|
4120
|
-
]),
|
|
4121
|
-
_: 1
|
|
4122
|
-
/* STABLE */
|
|
4123
|
-
})
|
|
4389
|
+
createTextVNode(
|
|
4390
|
+
" +" + toDisplayString(hiddenCount.value),
|
|
4391
|
+
1
|
|
4392
|
+
/* TEXT */
|
|
4393
|
+
)
|
|
4124
4394
|
]),
|
|
4125
4395
|
_: 1
|
|
4126
4396
|
/* STABLE */
|
|
4127
|
-
})
|
|
4128
|
-
|
|
4129
|
-
|
|
4130
|
-
|
|
4131
|
-
|
|
4132
|
-
|
|
4133
|
-
|
|
4134
|
-
|
|
4135
|
-
|
|
4136
|
-
|
|
4137
|
-
|
|
4138
|
-
|
|
4139
|
-
|
|
4140
|
-
|
|
4141
|
-
|
|
4142
|
-
|
|
4143
|
-
|
|
4144
|
-
|
|
4145
|
-
|
|
4146
|
-
|
|
4147
|
-
/* NEED_PATCH */
|
|
4148
|
-
)
|
|
4397
|
+
})
|
|
4398
|
+
]),
|
|
4399
|
+
_: 1
|
|
4400
|
+
/* STABLE */
|
|
4401
|
+
})) : createCommentVNode("v-if", true),
|
|
4402
|
+
createCommentVNode(" 搜索输入框 "),
|
|
4403
|
+
withDirectives(createElementVNode("input", {
|
|
4404
|
+
"onUpdate:modelValue": _cache[2] || (_cache[2] = ($event) => isRef(searchQuery) ? searchQuery.value = $event : null),
|
|
4405
|
+
class: "search-input search-input-collapsed",
|
|
4406
|
+
placeholder: !selectedUsers.value.length ? computedPlaceholder.value : "",
|
|
4407
|
+
onFocus: handleFocus
|
|
4408
|
+
}, null, 40, _hoisted_3), [
|
|
4409
|
+
[vModelText, unref(searchQuery)]
|
|
4410
|
+
]),
|
|
4411
|
+
createCommentVNode(' 未聚焦状态下的"我"标签 '),
|
|
4412
|
+
createVNode(MeTag, {
|
|
4413
|
+
"current-user-id": _ctx.currentUserId,
|
|
4414
|
+
"is-disabled": isMeTagDisabled.value,
|
|
4415
|
+
onClick: addCurrentUser
|
|
4416
|
+
}, null, 8, ["current-user-id", "is-disabled"])
|
|
4149
4417
|
],
|
|
4150
|
-
|
|
4151
|
-
/*
|
|
4152
|
-
)
|
|
4153
|
-
|
|
4154
|
-
_: 1
|
|
4155
|
-
/* STABLE */
|
|
4156
|
-
}, 8, ["container-width", "cross-axis-offset", "empty-text", "is-show", "loading", "options", "render-list-item", "search-query", "tenant-id", "tenants", "user-group", "user-group-name"])
|
|
4157
|
-
],
|
|
4158
|
-
2
|
|
4159
|
-
/* CLASS */
|
|
4160
|
-
);
|
|
4161
|
-
};
|
|
4162
|
-
}
|
|
4163
|
-
});
|
|
4164
|
-
const MultipleSelector = /* @__PURE__ */ _export_sfc(_sfc_main$2, [["__scopeId", "data-v-2a532f24"]]);
|
|
4165
|
-
const _hoisted_1 = { class: "input-container" };
|
|
4166
|
-
const _hoisted_2 = ["placeholder"];
|
|
4167
|
-
const _sfc_main$1 = /* @__PURE__ */ defineComponent({
|
|
4168
|
-
...{
|
|
4169
|
-
name: "BkUserSelectorSingle"
|
|
4170
|
-
},
|
|
4171
|
-
__name: "single-selector",
|
|
4172
|
-
props: {
|
|
4173
|
-
modelValue: { default: "" },
|
|
4174
|
-
tenants: {},
|
|
4175
|
-
allowCreate: { type: Boolean },
|
|
4176
|
-
apiBaseUrl: { default: "" },
|
|
4177
|
-
currentUserId: { default: "" },
|
|
4178
|
-
disabled: { type: Boolean },
|
|
4179
|
-
emptyText: { default: "" },
|
|
4180
|
-
enableMultiTenantMode: { type: Boolean },
|
|
4181
|
-
exactSearchKey: { default: "bk_username" },
|
|
4182
|
-
excludeUserIds: { default: () => [] },
|
|
4183
|
-
freePaste: { type: Boolean },
|
|
4184
|
-
placeholder: { default: "" },
|
|
4185
|
-
tenantId: { default: "" },
|
|
4186
|
-
userGroupName: { default: "" },
|
|
4187
|
-
renderListItem: {},
|
|
4188
|
-
renderTag: {},
|
|
4189
|
-
userGroup: { default: () => [] }
|
|
4190
|
-
},
|
|
4191
|
-
emits: ["update:modelValue", "change", "focus", "blur"],
|
|
4192
|
-
setup(__props, { emit: __emit }) {
|
|
4193
|
-
const props = __props;
|
|
4194
|
-
const emit = __emit;
|
|
4195
|
-
const containerRef = ref(null);
|
|
4196
|
-
const inputRef = ref(null);
|
|
4197
|
-
const options = ref([]);
|
|
4198
|
-
const isLoading = ref(false);
|
|
4199
|
-
const selectedUser = ref(props.modelValue || "");
|
|
4200
|
-
const searchQuery = ref("");
|
|
4201
|
-
const showDropdown = ref(false);
|
|
4202
|
-
const userGroupFilter = computed(() => {
|
|
4203
|
-
return props.userGroup.filter((group) => {
|
|
4204
|
-
var _a, _b;
|
|
4205
|
-
const filtered = group.id !== selectedUser.value && !group.hidden;
|
|
4206
|
-
if (filtered) {
|
|
4207
|
-
return ((_a = group.id) == null ? void 0 : _a.includes(searchQuery.value)) || ((_b = group.name) == null ? void 0 : _b.includes(searchQuery.value));
|
|
4208
|
-
}
|
|
4209
|
-
return false;
|
|
4210
|
-
});
|
|
4211
|
-
});
|
|
4212
|
-
const selectedUserInfo = computed(() => {
|
|
4213
|
-
const userGroup = (props.userGroup || []).map((group) => ({
|
|
4214
|
-
...group,
|
|
4215
|
-
tenantId: "",
|
|
4216
|
-
type: "userGroup"
|
|
4217
|
-
}));
|
|
4218
|
-
const list = [...options.value, ...userGroup];
|
|
4219
|
-
const selectedUserInfo2 = list.find((user) => user.id === selectedUser.value);
|
|
4220
|
-
emit("change", selectedUserInfo2 || null);
|
|
4221
|
-
return selectedUserInfo2;
|
|
4222
|
-
});
|
|
4223
|
-
const initSelectedUser = async () => {
|
|
4224
|
-
if (typeof props.modelValue === "string" && props.modelValue) {
|
|
4225
|
-
try {
|
|
4226
|
-
isLoading.value = true;
|
|
4227
|
-
const result = await lookupUsers({
|
|
4228
|
-
apiBaseUrl: props.apiBaseUrl,
|
|
4229
|
-
tenantId: props.tenantId,
|
|
4230
|
-
exactSearchKey: props.exactSearchKey,
|
|
4231
|
-
usersList: [props.modelValue],
|
|
4232
|
-
enableMultiTenantMode: props.enableMultiTenantMode
|
|
4233
|
-
});
|
|
4234
|
-
options.value = formatUsers(result, props.enableMultiTenantMode).filter(
|
|
4235
|
-
(user) => !props.excludeUserIds.includes(user.id)
|
|
4236
|
-
);
|
|
4237
|
-
if (props.userGroup.length > 0) {
|
|
4238
|
-
const groupResult = props.userGroup.filter((group) => group.id == props.modelValue);
|
|
4239
|
-
options.value = groupResult.map((group) => ({
|
|
4240
|
-
...group,
|
|
4241
|
-
tenantId: "",
|
|
4242
|
-
type: "userGroup"
|
|
4243
|
-
}));
|
|
4244
|
-
}
|
|
4245
|
-
if (props.allowCreate && options.value.length === 0) {
|
|
4246
|
-
options.value.push({
|
|
4247
|
-
id: props.modelValue,
|
|
4248
|
-
name: props.modelValue,
|
|
4249
|
-
type: "custom",
|
|
4250
|
-
tenantId: ""
|
|
4251
|
-
});
|
|
4252
|
-
}
|
|
4253
|
-
} catch (error) {
|
|
4254
|
-
console.error("获取用户信息失败:", error);
|
|
4255
|
-
} finally {
|
|
4256
|
-
isLoading.value = false;
|
|
4257
|
-
}
|
|
4258
|
-
} else {
|
|
4259
|
-
options.value = [];
|
|
4260
|
-
}
|
|
4261
|
-
};
|
|
4262
|
-
onBeforeMount(async () => {
|
|
4263
|
-
initSelectedUser();
|
|
4264
|
-
});
|
|
4265
|
-
const addCurrentUser = async () => {
|
|
4266
|
-
if (!props.currentUserId || selectedUser.value === props.currentUserId) return;
|
|
4267
|
-
try {
|
|
4268
|
-
const result = await lookupUsers({
|
|
4269
|
-
apiBaseUrl: props.apiBaseUrl,
|
|
4270
|
-
tenantId: props.tenantId,
|
|
4271
|
-
exactSearchKey: props.exactSearchKey,
|
|
4272
|
-
usersList: [props.currentUserId],
|
|
4273
|
-
enableMultiTenantMode: props.enableMultiTenantMode
|
|
4274
|
-
});
|
|
4275
|
-
const formattedResults = formatUsers(result, props.enableMultiTenantMode);
|
|
4276
|
-
if (formattedResults.length > 0) {
|
|
4277
|
-
options.value = formattedResults.filter((user) => !props.excludeUserIds.includes(user.id));
|
|
4278
|
-
addUser(formattedResults[0]);
|
|
4279
|
-
}
|
|
4280
|
-
} catch (error) {
|
|
4281
|
-
console.error("获取当前用户信息失败:", error);
|
|
4282
|
-
}
|
|
4283
|
-
};
|
|
4284
|
-
const fetchUsers = async (keyword = "") => {
|
|
4285
|
-
if (!(keyword == null ? void 0 : keyword.length)) {
|
|
4286
|
-
options.value = [];
|
|
4287
|
-
isLoading.value = false;
|
|
4288
|
-
return;
|
|
4289
|
-
}
|
|
4290
|
-
isLoading.value = true;
|
|
4291
|
-
try {
|
|
4292
|
-
const result = await searchUsers({
|
|
4293
|
-
apiBaseUrl: props.apiBaseUrl,
|
|
4294
|
-
tenantId: props.tenantId,
|
|
4295
|
-
keyword,
|
|
4296
|
-
enableMultiTenantMode: props.enableMultiTenantMode
|
|
4297
|
-
});
|
|
4298
|
-
options.value = formatUsers(result, props.enableMultiTenantMode).filter((user) => !selectedUser.value || user.id !== selectedUser.value).filter((user) => !props.excludeUserIds.includes(user.id));
|
|
4299
|
-
} catch (error) {
|
|
4300
|
-
console.error("获取用户列表失败:", error);
|
|
4301
|
-
options.value = [];
|
|
4302
|
-
} finally {
|
|
4303
|
-
isLoading.value = false;
|
|
4304
|
-
}
|
|
4305
|
-
};
|
|
4306
|
-
const handleKeyDown = (event) => {
|
|
4307
|
-
if (event.key === "Enter") {
|
|
4308
|
-
if (props.allowCreate) {
|
|
4309
|
-
const customUser = {
|
|
4310
|
-
id: searchQuery.value,
|
|
4311
|
-
name: searchQuery.value,
|
|
4312
|
-
tenantId: "",
|
|
4313
|
-
type: "custom"
|
|
4314
|
-
};
|
|
4315
|
-
options.value.push(customUser);
|
|
4316
|
-
addUser(customUser);
|
|
4317
|
-
}
|
|
4318
|
-
}
|
|
4319
|
-
};
|
|
4320
|
-
const handlePaste = (event) => {
|
|
4321
|
-
var _a;
|
|
4322
|
-
event.preventDefault();
|
|
4323
|
-
const pastedText = ((_a = event.clipboardData) == null ? void 0 : _a.getData("text").trim()) || "";
|
|
4324
|
-
if (props.freePaste) {
|
|
4325
|
-
const customUser = { id: pastedText, name: pastedText, type: "custom", tenantId: "", login_name: pastedText };
|
|
4326
|
-
if (!options.value.some((item) => item.login_name === customUser.login_name)) {
|
|
4327
|
-
options.value.push(customUser);
|
|
4328
|
-
}
|
|
4329
|
-
addUser(customUser);
|
|
4330
|
-
}
|
|
4331
|
-
};
|
|
4332
|
-
const addUser = (user) => {
|
|
4333
|
-
selectedUser.value = user.id;
|
|
4334
|
-
searchQuery.value = "";
|
|
4335
|
-
showDropdown.value = false;
|
|
4336
|
-
};
|
|
4337
|
-
const removeSelectedUser = () => {
|
|
4338
|
-
selectedUser.value = "";
|
|
4339
|
-
searchQuery.value = "";
|
|
4340
|
-
};
|
|
4341
|
-
const handleInputFocus = () => {
|
|
4342
|
-
if (searchQuery.value.length >= 1 || Array.isArray(props.userGroup) && props.userGroup.length > 0) {
|
|
4343
|
-
showDropdown.value = true;
|
|
4344
|
-
}
|
|
4345
|
-
emit("focus");
|
|
4346
|
-
};
|
|
4347
|
-
let timer = null;
|
|
4348
|
-
const handleInput = () => {
|
|
4349
|
-
showDropdown.value = searchQuery.value.length >= 1;
|
|
4350
|
-
isLoading.value = true;
|
|
4351
|
-
clearTimeout(timer);
|
|
4352
|
-
timer = setTimeout(() => {
|
|
4353
|
-
fetchUsers(searchQuery.value);
|
|
4354
|
-
}, 300);
|
|
4355
|
-
};
|
|
4356
|
-
const handleClickOutside = () => {
|
|
4357
|
-
setTimeout(() => {
|
|
4358
|
-
showDropdown.value = false;
|
|
4359
|
-
}, 0);
|
|
4360
|
-
};
|
|
4361
|
-
watch(
|
|
4362
|
-
() => props.modelValue,
|
|
4363
|
-
(newVal) => {
|
|
4364
|
-
selectedUser.value = newVal;
|
|
4365
|
-
}
|
|
4366
|
-
);
|
|
4367
|
-
watch(selectedUser, (newVal) => {
|
|
4368
|
-
emit("update:modelValue", newVal);
|
|
4369
|
-
});
|
|
4370
|
-
return (_ctx, _cache) => {
|
|
4371
|
-
return withDirectives((openBlock(), createElementBlock(
|
|
4372
|
-
"div",
|
|
4373
|
-
{
|
|
4374
|
-
ref_key: "containerRef",
|
|
4375
|
-
ref: containerRef,
|
|
4376
|
-
class: normalizeClass(["single-selector", { "is-disabled": _ctx.disabled }])
|
|
4377
|
-
},
|
|
4378
|
-
[
|
|
4379
|
-
createCommentVNode(" 使用新的公共下拉选项组件 "),
|
|
4380
|
-
createVNode(SelectionPopover, {
|
|
4381
|
-
"container-width": containerRef.value ? containerRef.value.offsetWidth : "auto",
|
|
4382
|
-
"empty-text": _ctx.emptyText,
|
|
4383
|
-
"is-show": showDropdown.value,
|
|
4384
|
-
loading: isLoading.value,
|
|
4385
|
-
options: options.value,
|
|
4386
|
-
"render-list-item": _ctx.renderListItem,
|
|
4387
|
-
"search-query": searchQuery.value,
|
|
4388
|
-
"tenant-id": _ctx.tenantId,
|
|
4389
|
-
tenants: _ctx.tenants,
|
|
4390
|
-
"user-group": userGroupFilter.value,
|
|
4391
|
-
"user-group-name": _ctx.userGroupName,
|
|
4392
|
-
onSelectUser: addUser
|
|
4393
|
-
}, {
|
|
4394
|
-
default: withCtx(() => [
|
|
4395
|
-
createCommentVNode(" 输入框 "),
|
|
4396
|
-
createElementVNode("div", _hoisted_1, [
|
|
4397
|
-
createCommentVNode(" 用户标签显示 "),
|
|
4398
|
-
selectedUserInfo.value ? (openBlock(), createElementBlock("div", {
|
|
4399
|
-
key: 0,
|
|
4400
|
-
onClick: withModifiers(removeSelectedUser, ["stop"])
|
|
4401
|
-
}, [
|
|
4402
|
-
createVNode(UserTag, {
|
|
4403
|
-
"current-tenant-id": _ctx.tenantId,
|
|
4404
|
-
"render-tag": _ctx.renderTag,
|
|
4405
|
-
tenants: _ctx.tenants,
|
|
4406
|
-
user: selectedUserInfo.value,
|
|
4407
|
-
onClose: removeSelectedUser
|
|
4408
|
-
}, null, 8, ["current-tenant-id", "render-tag", "tenants", "user"])
|
|
4409
|
-
])) : createCommentVNode("v-if", true),
|
|
4410
|
-
withDirectives(createElementVNode("input", {
|
|
4411
|
-
ref_key: "inputRef",
|
|
4412
|
-
ref: inputRef,
|
|
4413
|
-
"onUpdate:modelValue": _cache[0] || (_cache[0] = ($event) => searchQuery.value = $event),
|
|
4414
|
-
class: "search-input",
|
|
4415
|
-
placeholder: selectedUserInfo.value ? "" : _ctx.placeholder,
|
|
4416
|
-
onBlur: _cache[1] || (_cache[1] = ($event) => emit("blur")),
|
|
4417
|
-
onFocus: handleInputFocus,
|
|
4418
|
-
onInput: handleInput,
|
|
4419
|
-
onKeydown: handleKeyDown,
|
|
4420
|
-
onPaste: handlePaste
|
|
4421
|
-
}, null, 40, _hoisted_2), [
|
|
4422
|
-
[vModelText, searchQuery.value]
|
|
4423
|
-
]),
|
|
4424
|
-
createCommentVNode(' "我"标签 '),
|
|
4425
|
-
createVNode(MeTag, {
|
|
4426
|
-
"current-user-id": _ctx.currentUserId,
|
|
4427
|
-
"is-disabled": !!_ctx.currentUserId && !!selectedUserInfo.value && selectedUserInfo.value[_ctx.exactSearchKey] === _ctx.currentUserId,
|
|
4428
|
-
onClick: addCurrentUser
|
|
4429
|
-
}, null, 8, ["current-user-id", "is-disabled"])
|
|
4418
|
+
512
|
|
4419
|
+
/* NEED_PATCH */
|
|
4420
|
+
), [
|
|
4421
|
+
[vShow, !isFocused.value]
|
|
4430
4422
|
])
|
|
4431
4423
|
]),
|
|
4432
4424
|
_: 1
|
|
4433
4425
|
/* STABLE */
|
|
4434
|
-
}, 8, ["container-width", "empty-text", "is-show", "loading", "options", "render-list-item", "search-query", "tenant-id", "tenants", "user-group", "user-group-name"])
|
|
4435
|
-
],
|
|
4436
|
-
2
|
|
4437
|
-
/* CLASS */
|
|
4438
|
-
)), [
|
|
4439
|
-
[unref(clickoutside), handleClickOutside]
|
|
4440
|
-
]);
|
|
4441
|
-
};
|
|
4442
|
-
}
|
|
4443
|
-
});
|
|
4444
|
-
const SingleSelector = /* @__PURE__ */ _export_sfc(_sfc_main$1, [["__scopeId", "data-v-cbe352a6"]]);
|
|
4445
|
-
const _sfc_main = /* @__PURE__ */ defineComponent({
|
|
4446
|
-
...{
|
|
4447
|
-
name: "BkUserSelector"
|
|
4448
|
-
},
|
|
4449
|
-
__name: "user-selector",
|
|
4450
|
-
props: {
|
|
4451
|
-
draggable: { type: Boolean, default: false },
|
|
4452
|
-
modelValue: { default: "" },
|
|
4453
|
-
multiple: { type: Boolean, default: false },
|
|
4454
|
-
allowCreate: { type: Boolean, default: false },
|
|
4455
|
-
apiBaseUrl: { default: "" },
|
|
4456
|
-
currentUserId: { default: "" },
|
|
4457
|
-
disabled: { type: Boolean, default: false },
|
|
4458
|
-
emptyText: { default: "" },
|
|
4459
|
-
enableMultiTenantMode: { type: Boolean, default: true },
|
|
4460
|
-
exactSearchKey: { default: "bk_username" },
|
|
4461
|
-
excludeUserIds: { default: () => [] },
|
|
4462
|
-
freePaste: { type: Boolean, default: false },
|
|
4463
|
-
placeholder: { default: "" },
|
|
4464
|
-
tenantId: { default: "" },
|
|
4465
|
-
userGroupName: { default: "" },
|
|
4466
|
-
renderListItem: {},
|
|
4467
|
-
renderTag: {},
|
|
4468
|
-
userGroup: { default: () => [] }
|
|
4469
|
-
},
|
|
4470
|
-
emits: ["update:modelValue", "change", "dragStart", "dragEnd", "focus", "blur"],
|
|
4471
|
-
setup(__props, { emit: __emit }) {
|
|
4472
|
-
const { t } = useI18n();
|
|
4473
|
-
provideGlobalConfig({
|
|
4474
|
-
prefix: "bk"
|
|
4475
|
-
});
|
|
4476
|
-
const props = __props;
|
|
4477
|
-
const emit = __emit;
|
|
4478
|
-
const { tenants = {} } = useTenantData(props.apiBaseUrl, props.tenantId, props.enableMultiTenantMode);
|
|
4479
|
-
const selectedUsers = ref([]);
|
|
4480
|
-
const selectedUser = ref(props.multiple ? "" : props.modelValue);
|
|
4481
|
-
const selectedUserIds = computed(() => {
|
|
4482
|
-
return props.multiple ? selectedUsers.value.map((user) => user.id) : [];
|
|
4483
|
-
});
|
|
4484
|
-
const placeholder = computed(() => props.placeholder || t("请输入人员名称搜索"));
|
|
4485
|
-
const userGroupName = computed(() => props.userGroupName || t("用户群组"));
|
|
4486
|
-
const emptyText = computed(() => props.emptyText || t("无匹配人员"));
|
|
4487
|
-
const initSelectedUsers = async () => {
|
|
4488
|
-
if (props.multiple) {
|
|
4489
|
-
const ids = Array.isArray(props.modelValue) ? props.modelValue : [];
|
|
4490
|
-
let userGroupSelected = [];
|
|
4491
|
-
if (props.userGroup.length > 0) {
|
|
4492
|
-
const result = props.userGroup.filter((group) => ids.includes(group.id));
|
|
4493
|
-
userGroupSelected = result.map((group) => ({
|
|
4494
|
-
...group,
|
|
4495
|
-
tenantId: "",
|
|
4496
|
-
type: "userGroup"
|
|
4497
|
-
}));
|
|
4498
|
-
}
|
|
4499
|
-
if (ids.length > 0) {
|
|
4500
|
-
try {
|
|
4501
|
-
const result = await lookupUsers({
|
|
4502
|
-
apiBaseUrl: props.apiBaseUrl,
|
|
4503
|
-
tenantId: props.tenantId,
|
|
4504
|
-
exactSearchKey: "bk_username",
|
|
4505
|
-
usersList: ids,
|
|
4506
|
-
enableMultiTenantMode: props.enableMultiTenantMode
|
|
4507
|
-
});
|
|
4508
|
-
const selectedList = [...userGroupSelected, ...formatUsers(result, props.enableMultiTenantMode)];
|
|
4509
|
-
if (props.allowCreate) {
|
|
4510
|
-
selectedList.push(
|
|
4511
|
-
...ids.filter((id) => !selectedList.some((user) => user.id === id)).map((id) => ({ id, name: id, type: "custom", tenantId: "" }))
|
|
4512
|
-
);
|
|
4513
|
-
}
|
|
4514
|
-
selectedUsers.value = ids.map((id) => selectedList.find((user) => user.id === id)).filter(Boolean);
|
|
4515
|
-
} catch (error) {
|
|
4516
|
-
console.error("获取选中用户信息失败:", error);
|
|
4517
|
-
}
|
|
4518
|
-
} else {
|
|
4519
|
-
selectedUsers.value = [];
|
|
4520
|
-
}
|
|
4521
|
-
} else {
|
|
4522
|
-
selectedUser.value = props.modelValue;
|
|
4523
|
-
}
|
|
4524
|
-
};
|
|
4525
|
-
const handleUpdateUser = (user) => {
|
|
4526
|
-
emit("change", user);
|
|
4527
|
-
};
|
|
4528
|
-
const handleUpdateSelectedUsers = (users) => {
|
|
4529
|
-
selectedUsers.value = users;
|
|
4530
|
-
emit(
|
|
4531
|
-
"update:modelValue",
|
|
4532
|
-
users.map((user) => user.id)
|
|
4533
|
-
);
|
|
4534
|
-
emit("change", users);
|
|
4535
|
-
};
|
|
4536
|
-
const handleFocus = () => {
|
|
4537
|
-
emit("focus");
|
|
4538
|
-
};
|
|
4539
|
-
const handleBlur = () => {
|
|
4540
|
-
emit("blur");
|
|
4541
|
-
};
|
|
4542
|
-
watch(selectedUser, (newVal) => {
|
|
4543
|
-
if (!props.multiple) {
|
|
4544
|
-
emit("update:modelValue", newVal);
|
|
4545
|
-
}
|
|
4546
|
-
});
|
|
4547
|
-
watch(
|
|
4548
|
-
() => props.userGroup,
|
|
4549
|
-
() => {
|
|
4550
|
-
initSelectedUsers();
|
|
4551
|
-
}
|
|
4552
|
-
);
|
|
4553
|
-
watch(
|
|
4554
|
-
() => props.modelValue,
|
|
4555
|
-
() => {
|
|
4556
|
-
initSelectedUsers();
|
|
4557
|
-
},
|
|
4558
|
-
{ deep: true }
|
|
4559
|
-
);
|
|
4560
|
-
onBeforeMount(() => {
|
|
4561
|
-
initSelectedUsers();
|
|
4562
|
-
});
|
|
4563
|
-
return (_ctx, _cache) => {
|
|
4564
|
-
return openBlock(), createElementBlock(
|
|
4565
|
-
"section",
|
|
4566
|
-
{
|
|
4567
|
-
ref: "containerRef",
|
|
4568
|
-
class: normalizeClass(["bk-user-selector", { "is-disabled": _ctx.disabled }])
|
|
4569
|
-
},
|
|
4570
|
-
[
|
|
4571
|
-
createCommentVNode(" 单选模式 "),
|
|
4572
|
-
!_ctx.multiple ? (openBlock(), createBlock(SingleSelector, {
|
|
4573
|
-
key: 0,
|
|
4574
|
-
modelValue: selectedUser.value,
|
|
4575
|
-
"onUpdate:modelValue": _cache[0] || (_cache[0] = ($event) => selectedUser.value = $event),
|
|
4576
|
-
"allow-create": _ctx.allowCreate,
|
|
4577
|
-
"api-base-url": _ctx.apiBaseUrl,
|
|
4578
|
-
"current-user-id": _ctx.currentUserId,
|
|
4579
|
-
disabled: _ctx.disabled,
|
|
4580
|
-
"empty-text": emptyText.value,
|
|
4581
|
-
"enable-multi-tenant-mode": _ctx.enableMultiTenantMode,
|
|
4582
|
-
"exact-search-key": _ctx.exactSearchKey,
|
|
4583
|
-
"exclude-user-ids": _ctx.excludeUserIds,
|
|
4584
|
-
placeholder: placeholder.value,
|
|
4585
|
-
"render-list-item": _ctx.renderListItem,
|
|
4586
|
-
"render-tag": _ctx.renderTag,
|
|
4587
|
-
"tenant-id": _ctx.tenantId,
|
|
4588
|
-
tenants: unref(tenants),
|
|
4589
|
-
"user-group": _ctx.userGroup,
|
|
4590
|
-
"user-group-name": userGroupName.value,
|
|
4591
|
-
"free-paste": _ctx.freePaste,
|
|
4592
|
-
onBlur: handleBlur,
|
|
4593
|
-
onChange: handleUpdateUser,
|
|
4594
|
-
onFocus: handleFocus
|
|
4595
|
-
}, null, 8, ["modelValue", "allow-create", "api-base-url", "current-user-id", "disabled", "empty-text", "enable-multi-tenant-mode", "exact-search-key", "exclude-user-ids", "placeholder", "render-list-item", "render-tag", "tenant-id", "tenants", "user-group", "user-group-name", "free-paste"])) : (openBlock(), createElementBlock(
|
|
4596
|
-
Fragment,
|
|
4597
|
-
{ key: 1 },
|
|
4598
|
-
[
|
|
4599
|
-
createCommentVNode(" 多选模式 "),
|
|
4600
|
-
createVNode(MultipleSelector, {
|
|
4601
|
-
modelValue: selectedUserIds.value,
|
|
4602
|
-
"onUpdate:modelValue": _cache[1] || (_cache[1] = ($event) => selectedUserIds.value = $event),
|
|
4603
|
-
"allow-create": _ctx.allowCreate,
|
|
4604
|
-
"api-base-url": _ctx.apiBaseUrl,
|
|
4605
|
-
"current-user-id": _ctx.currentUserId,
|
|
4606
|
-
disabled: _ctx.disabled,
|
|
4607
|
-
draggable: _ctx.draggable,
|
|
4608
|
-
"empty-text": emptyText.value,
|
|
4609
|
-
"enable-multi-tenant-mode": _ctx.enableMultiTenantMode,
|
|
4610
|
-
"exact-search-key": _ctx.exactSearchKey,
|
|
4611
|
-
"exclude-user-ids": _ctx.excludeUserIds,
|
|
4612
|
-
placeholder: placeholder.value,
|
|
4613
|
-
"render-list-item": _ctx.renderListItem,
|
|
4614
|
-
"render-tag": _ctx.renderTag,
|
|
4615
|
-
"selected-users": selectedUsers.value,
|
|
4616
|
-
"tenant-id": _ctx.tenantId,
|
|
4617
|
-
tenants: unref(tenants),
|
|
4618
|
-
"user-group": _ctx.userGroup,
|
|
4619
|
-
"user-group-name": userGroupName.value,
|
|
4620
|
-
"free-paste": _ctx.freePaste,
|
|
4621
|
-
onBlur: handleBlur,
|
|
4622
|
-
onDragEnd: _cache[2] || (_cache[2] = ($event) => _ctx.$emit("dragEnd", $event)),
|
|
4623
|
-
onDragStart: _cache[3] || (_cache[3] = ($event) => _ctx.$emit("dragStart", $event)),
|
|
4624
|
-
onFocus: handleFocus,
|
|
4625
|
-
"onUpdate:selectedUsers": handleUpdateSelectedUsers
|
|
4626
|
-
}, null, 8, ["modelValue", "allow-create", "api-base-url", "current-user-id", "disabled", "draggable", "empty-text", "enable-multi-tenant-mode", "exact-search-key", "exclude-user-ids", "placeholder", "render-list-item", "render-tag", "selected-users", "tenant-id", "tenants", "user-group", "user-group-name", "free-paste"])
|
|
4627
|
-
],
|
|
4628
|
-
2112
|
|
4629
|
-
/* STABLE_FRAGMENT, DEV_ROOT_FRAGMENT */
|
|
4630
|
-
))
|
|
4426
|
+
}, 8, ["avatar-base-url", "container-width", "empty-text", "has-avatar", "is-show", "loading", "options", "render-list-item", "search-query", "tenant-id", "tenants", "user-group", "user-group-name"])
|
|
4631
4427
|
],
|
|
4632
4428
|
2
|
|
4633
4429
|
/* CLASS */
|
|
@@ -4635,7 +4431,7 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
|
|
|
4635
4431
|
};
|
|
4636
4432
|
}
|
|
4637
4433
|
});
|
|
4638
|
-
const BkUserSelector = /* @__PURE__ */ _export_sfc(_sfc_main, [["__scopeId", "data-v-
|
|
4434
|
+
const BkUserSelector = /* @__PURE__ */ _export_sfc(_sfc_main, [["__scopeId", "data-v-9975c7e1"]]);
|
|
4639
4435
|
export {
|
|
4640
4436
|
BkUserSelector,
|
|
4641
4437
|
BkUserSelector as default
|