需测试[0.2.7.3][ci]
This commit is contained in:
@@ -134,6 +134,13 @@
|
||||
border-radius: 6px;
|
||||
}
|
||||
|
||||
.search-container select {
|
||||
padding: 8px 12px;
|
||||
border: 1px solid #d1d5db;
|
||||
border-radius: 6px;
|
||||
background: #fff;
|
||||
}
|
||||
|
||||
.search-container button {
|
||||
padding: 8px 15px;
|
||||
background: #4f46e5;
|
||||
@@ -262,8 +269,10 @@
|
||||
|
||||
<div class="search-container">
|
||||
<input type="text" id="searchInput" placeholder="搜索用户名...">
|
||||
<select id="keyFilter"></select>
|
||||
<button id="searchBtn">搜索</button>
|
||||
<button id="resetBtn">重置</button>
|
||||
<button id="clearKeyBtn">清空Key</button>
|
||||
</div>
|
||||
|
||||
<div class="table-container">
|
||||
@@ -272,6 +281,7 @@
|
||||
<tr>
|
||||
<th>用户ID</th>
|
||||
<th>用户名</th>
|
||||
<th>Key</th>
|
||||
<th>权限</th>
|
||||
<th>操作</th>
|
||||
</tr>
|
||||
@@ -364,11 +374,12 @@
|
||||
}
|
||||
|
||||
// 获取所有用户
|
||||
async function loadUsers(searchTerm = '') {
|
||||
async function loadUsers(searchTerm = '', key = '') {
|
||||
try {
|
||||
const url = searchTerm ?
|
||||
`/elastic/users/?search=${encodeURIComponent(searchTerm)}` :
|
||||
'/elastic/users/';
|
||||
const params = new URLSearchParams();
|
||||
if ((searchTerm || '').trim()) params.set('search', (searchTerm || '').trim());
|
||||
if ((key || '').trim()) params.set('key', (key || '').trim());
|
||||
const url = params.toString() ? `/elastic/users/?${params.toString()}` : '/elastic/users/';
|
||||
|
||||
const response = await fetch(url);
|
||||
const result = await response.json();
|
||||
@@ -385,10 +396,13 @@
|
||||
|
||||
// 根据权限值显示权限名称
|
||||
const permissionText = Number(user.permission) === 0 ? '管理员' : '普通用户';
|
||||
const keys = Array.isArray(user.key) ? user.key : (user.key ? [user.key] : []);
|
||||
const keysText = keys.map(k => String(k || '').trim()).filter(Boolean).join('、') || '-';
|
||||
|
||||
row.innerHTML = `
|
||||
<td>${user.user_id}</td>
|
||||
<td>${user.username}</td>
|
||||
<td>${keysText}</td>
|
||||
<td>${permissionText}</td>
|
||||
<td class="action-buttons">
|
||||
<button class="btn btn-success edit-btn" data-user='${JSON.stringify(user)}'>编辑</button>
|
||||
@@ -407,6 +421,29 @@
|
||||
}
|
||||
}
|
||||
|
||||
async function initKeyFilter() {
|
||||
const select = document.getElementById('keyFilter');
|
||||
if (!select) return;
|
||||
select.innerHTML = '<option value="">全部Key</option>';
|
||||
try {
|
||||
const resp = await fetch('/elastic/keys-for-filter/', { credentials: 'same-origin' });
|
||||
const data = await resp.json();
|
||||
if (data.status !== 'success') return;
|
||||
const keys = data.data || [];
|
||||
keys.forEach(k => {
|
||||
const opt = document.createElement('option');
|
||||
opt.value = String(k || '').trim();
|
||||
opt.textContent = String(k || '').trim();
|
||||
if (opt.value) select.appendChild(opt);
|
||||
});
|
||||
} catch (e) {
|
||||
}
|
||||
select.addEventListener('change', () => {
|
||||
const searchTerm = document.getElementById('searchInput').value;
|
||||
loadUsers(searchTerm, select.value);
|
||||
});
|
||||
}
|
||||
|
||||
// 打开添加用户模态框
|
||||
function openAddModal() {
|
||||
document.getElementById('modalTitle').textContent = '添加用户';
|
||||
@@ -558,7 +595,8 @@
|
||||
if (searchBtn) {
|
||||
searchBtn.addEventListener('click', function() {
|
||||
const searchTerm = document.getElementById('searchInput').value;
|
||||
loadUsers(searchTerm);
|
||||
const key = (document.getElementById('keyFilter') || {}).value || '';
|
||||
loadUsers(searchTerm, key);
|
||||
});
|
||||
}
|
||||
|
||||
@@ -566,7 +604,19 @@
|
||||
if (resetBtn) {
|
||||
resetBtn.addEventListener('click', function() {
|
||||
document.getElementById('searchInput').value = '';
|
||||
loadUsers();
|
||||
const select = document.getElementById('keyFilter');
|
||||
if (select) select.value = '';
|
||||
loadUsers('', '');
|
||||
});
|
||||
}
|
||||
|
||||
const clearKeyBtn = document.getElementById('clearKeyBtn');
|
||||
if (clearKeyBtn) {
|
||||
clearKeyBtn.addEventListener('click', function() {
|
||||
const select = document.getElementById('keyFilter');
|
||||
if (select) select.value = '';
|
||||
const searchTerm = document.getElementById('searchInput').value;
|
||||
loadUsers(searchTerm, '');
|
||||
});
|
||||
}
|
||||
|
||||
@@ -609,6 +659,7 @@
|
||||
|
||||
// 页面加载时获取用户列表
|
||||
document.addEventListener('DOMContentLoaded', function() {
|
||||
initKeyFilter();
|
||||
const selfForm = document.getElementById('selfPwdForm');
|
||||
if (selfForm) {
|
||||
selfForm.addEventListener('submit', async (e) => {
|
||||
@@ -635,7 +686,8 @@
|
||||
}
|
||||
const tbody = document.getElementById('usersTableBody');
|
||||
if (tbody) {
|
||||
loadUsers();
|
||||
const select = document.getElementById('keyFilter');
|
||||
loadUsers('', select ? select.value : '');
|
||||
}
|
||||
});
|
||||
|
||||
@@ -654,4 +706,4 @@
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
</html>
|
||||
|
||||
@@ -444,6 +444,7 @@ def get_users(request):
|
||||
is_admin = int(request.session.get("permission", 1)) == 0
|
||||
requester = get_user_by_id(uid) or {}
|
||||
mgr_keys = set(requester.get("manage_key") or [])
|
||||
key_q = (request.GET.get("key") or "").strip()
|
||||
q = (request.GET.get("search") or "").strip()
|
||||
users = get_all_users()
|
||||
if is_admin:
|
||||
@@ -455,6 +456,15 @@ def get_users(request):
|
||||
filtered = [u for u in users if match_manage(u)]
|
||||
else:
|
||||
filtered = [u for u in users if str(u.get("user_id")) == str(uid)]
|
||||
if key_q:
|
||||
k = str(key_q).strip()
|
||||
def match_key(user):
|
||||
try:
|
||||
ukeys = {str(x).strip() for x in (user.get("key") or []) if str(x).strip()}
|
||||
except Exception:
|
||||
ukeys = set()
|
||||
return k in ukeys
|
||||
filtered = [u for u in filtered if match_key(u)]
|
||||
if q:
|
||||
filtered = [u for u in filtered if q in str(u.get("username", ""))]
|
||||
return JsonResponse({"status": "success", "data": filtered})
|
||||
|
||||
Reference in New Issue
Block a user