bizmatch-project/bizmatch-server/scripts/reproduce-favorites.ts

120 lines
5.1 KiB
TypeScript

import { Pool } from 'pg';
import { drizzle, NodePgDatabase } from 'drizzle-orm/node-postgres';
import { sql, eq, and } from 'drizzle-orm';
import * as schema from '../src/drizzle/schema';
import { users_json } from '../src/drizzle/schema';
// Mock JwtUser
interface JwtUser {
email: string;
}
// Logic from UserService.addFavorite
async function addFavorite(db: NodePgDatabase<typeof schema>, id: string, user: JwtUser) {
console.log(`[Action] Adding favorite. Target ID: ${id}, Favoriter Email: ${user.email}`);
await db
.update(schema.users_json)
.set({
data: sql`jsonb_set(${schema.users_json.data}, '{favoritesForUser}',
coalesce((${schema.users_json.data}->'favoritesForUser')::jsonb, '[]'::jsonb) || to_jsonb(${user.email}::text))`,
} as any)
.where(eq(schema.users_json.id, id));
}
// Logic from UserService.getFavoriteUsers
async function getFavoriteUsers(db: NodePgDatabase<typeof schema>, user: JwtUser) {
console.log(`[Action] Fetching favorites for ${user.email}`);
// Corrected query using `?` operator (matches array element check)
const data = await db
.select()
.from(schema.users_json)
.where(sql`${schema.users_json.data}->'favoritesForUser' ? ${user.email}`);
return data;
}
// Logic from UserService.deleteFavorite
async function deleteFavorite(db: NodePgDatabase<typeof schema>, id: string, user: JwtUser) {
console.log(`[Action] Removing favorite. Target ID: ${id}, Favoriter Email: ${user.email}`);
await db
.update(schema.users_json)
.set({
data: sql`jsonb_set(${schema.users_json.data}, '{favoritesForUser}',
(SELECT coalesce(jsonb_agg(elem), '[]'::jsonb)
FROM jsonb_array_elements(coalesce(${schema.users_json.data}->'favoritesForUser', '[]'::jsonb)) AS elem
WHERE elem::text != to_jsonb(${user.email}::text)::text))`,
} as any)
.where(eq(schema.users_json.id, id));
}
async function main() {
console.log('═══════════════════════════════════════════════════════');
console.log(' FAVORITES REPRODUCTION SCRIPT');
console.log('═══════════════════════════════════════════════════════\n');
const connectionString = process.env.DATABASE_URL || 'postgresql://postgres:postgres@localhost:5432/bizmatch';
const pool = new Pool({ connectionString });
const db = drizzle(pool, { schema });
try {
// 1. Find a "professional" user to be the TARGET listing
// filtering by customerType = 'professional' inside the jsonb data
const targets = await db.select().from(users_json).limit(1);
if (targets.length === 0) {
console.error("No users found in DB to test with.");
return;
}
const targetUser = targets[0];
console.log(`Found target user: ID=${targetUser.id}, Email=${targetUser.email}`);
// 2. Define a "favoriter" user (doesn't need to exist in DB for the logic to work, but better if it's realistic)
// We'll just use a dummy email or one from DB if available.
const favoriterEmail = 'test-repro-favoriter@example.com';
const favoriter: JwtUser = { email: favoriterEmail };
// 3. Clear any existing favorite for this pair first
await deleteFavorite(db, targetUser.id, favoriter);
// 4. Add Favorite
await addFavorite(db, targetUser.id, favoriter);
// 5. Verify it was added by checking the raw data
const updatedTarget = await db.select().from(users_json).where(eq(users_json.id, targetUser.id));
const favoritesData = (updatedTarget[0].data as any).favoritesForUser;
console.log(`\n[Check] Raw favoritesForUser data on target:`, favoritesData);
if (!favoritesData || !favoritesData.includes(favoriterEmail)) {
console.error("❌ Add Favorite FAILED. Email not found in favoritesForUser array.");
} else {
console.log("✅ Add Favorite SUCCESS. Email found in JSON.");
}
// 6. Test retrieval using the getFavoriteUsers query
const retrievedFavorites = await getFavoriteUsers(db, favoriter);
console.log(`\n[Check] retrievedFavorites count: ${retrievedFavorites.length}`);
const found = retrievedFavorites.find(u => u.id === targetUser.id);
if (found) {
console.log("✅ Get Favorites SUCCESS. Target user returned in query.");
} else {
console.log("❌ Get Favorites FAILED. Target user NOT returned by query.");
console.log("Query used: favoritesForUser @> [email]");
}
// 7. Cleanup
await deleteFavorite(db, targetUser.id, favoriter);
console.log("\n[Cleanup] Removed test favorite.");
} catch (error) {
console.error('❌ Script failed:', error);
} finally {
await pool.end();
}
}
main();