From e5a6c641966583331e32014ca36ea6c676c6cf55 Mon Sep 17 00:00:00 2001 From: Pau Date: Sun, 25 May 2025 04:38:33 +0200 Subject: [PATCH] added changes to reports repository to implement intermediary table and multiple report_types --- .../usersHasPlacesRepository.js | 126 ++++++++++++------ 1 file changed, 84 insertions(+), 42 deletions(-) diff --git a/src/repositories/resource_types/usersHasPlacesRepository.js b/src/repositories/resource_types/usersHasPlacesRepository.js index 7f64842..521c346 100644 --- a/src/repositories/resource_types/usersHasPlacesRepository.js +++ b/src/repositories/resource_types/usersHasPlacesRepository.js @@ -4,64 +4,71 @@ const _userHasPlacesSelectQuery = (_pagination = '') => ({ count }) => ({ uuid, const uuidCondition = uuid ? 'AND up.uuid = :uuid ' : ''; const user_uuidCondition = user_uuid ? 'AND up.fk_user = (SELECT id FROM dbmaster.users WHERE uuid = :user_uuid)' : ''; const place_uuidCondition = place_uuid ? 'AND up.fk_place = (SELECT id FROM dbmaster.places WHERE uuid = :place_uuid)' : ''; - const report_type_uuidCondition = report_type_uuid ? 'AND up.fk_report_type = (SELECT id FROM dbmaster.report_types WHERE uuid = :report_type_uuid)' : ''; const ratingCondition = rating ? 'AND up.rating = :rating' : ''; const descriptionCondition = description ? `AND up.description LIKE CONCAT('%',:description,'%')` : ''; - - // Conditional fields and joins for the report type - const reportTypeFields = report_type_uuid ? `, rt.name AS report_type_name, - rt.uuid AS report_type_uuid` : ''; - - const reportTypeJoin = report_type_uuid ? 'LEFT JOIN dbmaster.report_types AS rt ON up.fk_report_type = rt.id' : ''; - - const reportTypeDeletedCondition = report_type_uuid ? 'AND rt.deleted IS NULL' : ''; - + + // For filter type, we do EXISTS with intermediate table + const reportTypeCondition = report_type_uuid ? ` + AND EXISTS ( + SELECT 1 FROM dbmaster.report_report_type rrt + WHERE rrt.report_uuid = up.uuid AND rrt.report_type_uuid = :report_type_uuid + ) + ` : ''; + return ` - SELECT ${count || - `up.*, + SELECT ${count || `up.*, u.username AS user_username, u.uuid AS user_uuid, p.name AS place_name, - p.uuid AS place_uuid${reportTypeFields}`} + p.uuid AS place_uuid, + GROUP_CONCAT(rt.uuid) AS report_type_uuids, + GROUP_CONCAT(rt.name) AS report_type_names` + } FROM dbmaster.users_has_places AS up LEFT JOIN dbmaster.users AS u ON up.fk_user = u.id LEFT JOIN dbmaster.places AS p ON up.fk_place = p.id - ${reportTypeJoin} + LEFT JOIN dbmaster.report_report_type AS rrt ON rrt.report_uuid = up.uuid + LEFT JOIN dbmaster.report_types AS rt ON rt.uuid = rrt.report_type_uuid WHERE up.created <= :now AND (up.deleted > :now OR up.deleted IS NULL) AND u.deleted IS NULL AND p.deleted IS NULL - ${reportTypeDeletedCondition} ${uuidCondition} ${user_uuidCondition} ${place_uuidCondition} - ${report_type_uuidCondition} + ${reportTypeCondition} ${ratingCondition} ${descriptionCondition} + GROUP BY up.uuid ${_pagination} `; } + const getUserHasPlacesListQuery = ({ limit, page, ...rest }) => _userHasPlacesSelectQuery(pagination({ limit, page }))({ count: false })(rest); const countUserHasPlacesListQuery = rest => _userHasPlacesSelectQuery()({ count: 'COUNT(DISTINCT(up.uuid)) AS count' })(rest); -const insertUserHasPlacesQuery = ({ user_uuid, place_uuid, description, createdBy, report_type_uuid, images}) => { - const user_uuidCondition = user_uuid ? '(SELECT id FROM dbmaster.users WHERE uuid = :user_uuid)' : null; - const place_uuidCondition = place_uuid ? '(SELECT id FROM dbmaster.places WHERE uuid = :place_uuid)' : null; - const createdByCondition = createdBy ? ':createdBy' : null; - const descriptionCondition = description ? ':description' : null; - const reportTypeCondition = report_type_uuid ? `(SELECT id FROM dbmaster.report_types WHERE uuid = :report_type_uuid)` : null; - const imagesCondition = images ? ':images' : null; - +const insertUserHasPlacesQuery = ({ user_uuid, place_uuid, description, createdBy, report_type_uuid, images }) => { + const report_type_uuidStatements = report_type_uuid && report_type_uuid.length > 0 + ? report_type_uuid.map(rt => + `INSERT INTO dbmaster.report_report_type (report_uuid, report_type_uuid) VALUES (:uuid, '${rt}');` + ).join('\n ') + : ''; + + const user_uuidCondition = user_uuid ? '(SELECT id FROM dbmaster.users WHERE uuid = :user_uuid)' : 'NULL'; + const place_uuidCondition = place_uuid ? '(SELECT id FROM dbmaster.places WHERE uuid = :place_uuid)' : 'NULL'; + const createdByCondition = createdBy ? ':createdBy' : 'NULL'; + const descriptionCondition = description ? ':description' : 'NULL'; + const imagesCondition = images ? ':images' : 'NULL'; + return ` INSERT INTO dbmaster.users_has_places ( uuid, fk_user, fk_place, - fk_report_type, rating, images, description, @@ -72,40 +79,75 @@ const insertUserHasPlacesQuery = ({ user_uuid, place_uuid, description, createdB :uuid, ${user_uuidCondition}, ${place_uuidCondition}, - ${reportTypeCondition}, :rating, ${imagesCondition}, ${descriptionCondition}, ${createdByCondition}, :now ); - SELECT * FROM dbmaster.users_has_places WHERE uuid = :uuid; - ` + + ${report_type_uuidStatements} + + SELECT + up.*, + u.username AS user_username, + u.uuid AS user_uuid, + p.name AS place_name, + p.uuid AS place_uuid, + GROUP_CONCAT(rt.uuid) AS report_type_uuids, + GROUP_CONCAT(rt.name) AS report_type_names + FROM dbmaster.users_has_places AS up + LEFT JOIN dbmaster.users AS u ON up.fk_user = u.id + LEFT JOIN dbmaster.places AS p ON up.fk_place = p.id + LEFT JOIN dbmaster.report_report_type AS rrt ON rrt.report_uuid = up.uuid + LEFT JOIN dbmaster.report_types AS rt ON rt.uuid = rrt.report_type_uuid + WHERE up.created <= :now + AND (up.deleted > :now OR up.deleted IS NULL) + AND u.deleted IS NULL + AND p.deleted IS NULL + GROUP BY up.uuid; + `; } const modifyUserHasPlacesQuery = ({user_uuid, place_uuid, report_type_uuid, rating, images, description}) => { - const user_uuidCondition = user_uuid ? 'fk_user = (SELECT id FROM dbmaster.users WHERE uuid = :user_uuid),' : ``; - const place_uuidCondition = place_uuid ? 'fk_place = (SELECT id FROM dbmaster.places WHERE uuid = :place_uuid),' : ``; - const report_type_uuidCondition = report_type_uuid ? 'fk_report_type = (SELECT id FROM dbmaster.report_types WHERE uuid = :report_type_uuid),' : ``; - const ratingCondition = rating ? 'rating = :rating,' : ``; - const imagesCondition = images ? `images = :images,` : ''; - const descriptionCondition = description ? `description = :description,` : ``; + const user_uuidCondition = user_uuid ? 'fk_user = (SELECT id FROM dbmaster.users WHERE uuid = :user_uuid),' : ''; + const place_uuidCondition = place_uuid ? 'fk_place = (SELECT id FROM dbmaster.places WHERE uuid = :place_uuid),' : ''; + const report_type_uuidCondition = report_type_uuid ? `DELETE FROM dbmaster.report_report_type WHERE report_uuid = :uuid; ${report_type_uuid.map(rt => `INSERT INTO dbmaster.report_report_type (report_uuid, report_type_uuid) VALUES (:uuid, '${rt}');`).join(' ')}` : ''; + const ratingCondition = rating ? 'rating = :rating,' : ''; + const imagesCondition = images ? 'images = :images,' : ''; + const descriptionCondition = description ? 'description = :description,' : ''; + return ` + ${report_type_uuidCondition} UPDATE dbmaster.users_has_places SET ${user_uuidCondition} ${place_uuidCondition} - ${report_type_uuidCondition} ${ratingCondition} ${imagesCondition} ${descriptionCondition} - uuid = :uuid - WHERE - users_has_places.uuid = :uuid - AND - users_has_places.deleted IS NULL; - SELECT * FROM dbmaster.users_has_places WHERE uuid = :uuid; - ` + modified = :now + WHERE uuid = :uuid AND deleted IS NULL; + + SELECT + up.*, + u.username AS user_username, + u.uuid AS user_uuid, + p.name AS place_name, + p.uuid AS place_uuid, + GROUP_CONCAT(rt.uuid) AS report_type_uuids, + GROUP_CONCAT(rt.name) AS report_type_names + FROM dbmaster.users_has_places AS up + LEFT JOIN dbmaster.users AS u ON up.fk_user = u.id + LEFT JOIN dbmaster.places AS p ON up.fk_place = p.id + LEFT JOIN dbmaster.report_report_type AS rrt ON rrt.report_uuid = up.uuid + LEFT JOIN dbmaster.report_types AS rt ON rt.uuid = rrt.report_type_uuid + WHERE up.uuid = :uuid + AND (up.deleted > :now OR up.deleted IS NULL) + AND u.deleted IS NULL + AND p.deleted IS NULL + GROUP BY up.uuid; + `; } const softDeleteUserHasPlacesQuery = () => {