UI: фамилия с инициалами в шапке, подпись автора у тестов
- Хедер: отображать Фамилия И. О., полное ФИО в title. - Список тестов и карточка: «Автор: Вы» для своих, иначе «Автор: Фамилия И. О.». - API: в каталоге и summary/versions — created_by, author full_name (camelCase в JSON). Made-with: Cursor
This commit is contained in:
@@ -0,0 +1,64 @@
|
||||
/**
|
||||
* Кто видит тест: автор цепочки и пользователи с назначением (target user = clinic user id).
|
||||
*/
|
||||
import { isTestAuthor } from '../config/devAuthor.js';
|
||||
import { query } from '../db/db.js';
|
||||
|
||||
/**
|
||||
* @param {string} userId
|
||||
* @param {string} testId
|
||||
* @returns {Promise<{ ok: boolean, isAuthor: boolean, notFound: boolean }>}
|
||||
*/
|
||||
export async function userHasTestAccess(userId, testId) {
|
||||
const { rows } = await query(
|
||||
`SELECT t.created_by FROM tests t WHERE t.id = $1`,
|
||||
[testId]
|
||||
);
|
||||
if (!rows.length) {
|
||||
return { ok: false, isAuthor: false, notFound: true };
|
||||
}
|
||||
if (isTestAuthor(rows[0].created_by, userId)) {
|
||||
return { ok: true, isAuthor: true, notFound: false };
|
||||
}
|
||||
const { rows: ar } = await query(
|
||||
`SELECT 1
|
||||
FROM test_assignments ta
|
||||
INNER JOIN test_versions tv_a ON tv_a.id = ta.test_version_id
|
||||
INNER JOIN test_assignment_targets tat ON tat.assignment_id = ta.id
|
||||
WHERE tv_a.test_id = $1
|
||||
AND tat.target_type = 'user'
|
||||
AND tat.target_id = $2
|
||||
LIMIT 1`,
|
||||
[testId, userId]
|
||||
);
|
||||
return { ok: ar.length > 0, isAuthor: false, notFound: false };
|
||||
}
|
||||
|
||||
/**
|
||||
* Список тестов в каталоге: только `is_active` цепочка + (автор OR назначен).
|
||||
*/
|
||||
export async function queryTestsVisibleToUser(userId) {
|
||||
return query(
|
||||
`SELECT DISTINCT t.id, t.title, t.description, t.is_active AS chain_active,
|
||||
t.created_at, t.updated_at, tv.id AS active_version_id, tv.version,
|
||||
t.created_by, u.full_name AS author_full_name
|
||||
FROM tests t
|
||||
INNER JOIN test_versions tv ON tv.test_id = t.id AND tv.is_active = true
|
||||
INNER JOIN users u ON u.id = t.created_by
|
||||
WHERE t.is_active = true
|
||||
AND (
|
||||
t.created_by = $1
|
||||
OR EXISTS (
|
||||
SELECT 1
|
||||
FROM test_assignments ta
|
||||
INNER JOIN test_versions tv2 ON tv2.id = ta.test_version_id
|
||||
INNER JOIN test_assignment_targets tat ON tat.assignment_id = ta.id
|
||||
WHERE tv2.test_id = t.id
|
||||
AND tat.target_type = 'user'
|
||||
AND tat.target_id = $1
|
||||
)
|
||||
)
|
||||
ORDER BY t.updated_at DESC NULLS LAST, t.created_at DESC`,
|
||||
[userId]
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user