Added comprehensive debugging to identify why collection.id is undefined: - Log identifier analysis (slug vs ID detection) - Log which query path is taken (slug vs numeric ID) - Log collection result structure and content - Add validation for collection data before using collection.id - Better error messages for debugging This will help identify the root cause of the thumbnails API failure.
140 lines
No EOL
4.4 KiB
JavaScript
140 lines
No EOL
4.4 KiB
JavaScript
import { sql } from '@vercel/postgres';
|
|
import { getUserFromRequest } from '../../../../lib/permission-middleware';
|
|
import { isValidSlug } from '../../../../lib/slug-utils';
|
|
|
|
export default async function handler(req, res) {
|
|
// Set CORS headers
|
|
res.setHeader('Access-Control-Allow-Origin', '*');
|
|
res.setHeader('Access-Control-Allow-Methods', 'GET, OPTIONS');
|
|
res.setHeader('Access-Control-Allow-Headers', 'Content-Type, Authorization');
|
|
|
|
// Handle preflight requests
|
|
if (req.method === 'OPTIONS') {
|
|
res.status(200).end();
|
|
return;
|
|
}
|
|
|
|
if (req.method !== 'GET') {
|
|
return res.status(405).json({ error: 'Method not allowed' });
|
|
}
|
|
|
|
try {
|
|
const { identifier } = req.query;
|
|
|
|
// Get authenticated user
|
|
const user = await getUserFromRequest(req);
|
|
if (!user) {
|
|
return res.status(401).json({ error: 'Authentication required' });
|
|
}
|
|
|
|
if (!identifier) {
|
|
return res.status(400).json({ error: 'Collection identifier is required' });
|
|
}
|
|
|
|
// Determine if identifier is a slug or numeric ID
|
|
const isSlug = isValidSlug(identifier) || isNaN(parseInt(identifier));
|
|
|
|
console.log('🔍 Identifier analysis:', { identifier, isSlug, isValidSlug: isValidSlug(identifier), isNaN: isNaN(parseInt(identifier)) });
|
|
|
|
// Verify user has access to this collection
|
|
let collectionResult;
|
|
if (isSlug) {
|
|
console.log('🔍 Querying by slug:', identifier);
|
|
collectionResult = await sql`
|
|
SELECT c.*, cp.role as user_role
|
|
FROM collections c
|
|
LEFT JOIN collection_permissions cp ON c.id = cp.collection_id AND cp.user_id = ${user.userId} AND cp.status = 'active'
|
|
WHERE c.slug = ${identifier}
|
|
AND (
|
|
c.user_id = ${user.userId} OR
|
|
cp.id IS NOT NULL OR
|
|
c.is_public = true
|
|
)
|
|
`;
|
|
} else {
|
|
const numericId = parseInt(identifier);
|
|
console.log('🔍 Querying by ID:', numericId);
|
|
collectionResult = await sql`
|
|
SELECT c.*, cp.role as user_role
|
|
FROM collections c
|
|
LEFT JOIN collection_permissions cp ON c.id = cp.collection_id AND cp.user_id = ${user.userId} AND cp.status = 'active'
|
|
WHERE c.id = ${numericId}
|
|
AND (
|
|
c.user_id = ${user.userId} OR
|
|
cp.id IS NOT NULL OR
|
|
c.is_public = true
|
|
)
|
|
`;
|
|
}
|
|
|
|
if (collectionResult.length === 0) {
|
|
return res.status(404).json({ error: 'Collection not found or access denied' });
|
|
}
|
|
|
|
console.log('🔍 Collection result:', {
|
|
identifier,
|
|
isSlug,
|
|
resultLength: collectionResult.length,
|
|
collection: collectionResult[0]
|
|
});
|
|
|
|
const collection = collectionResult[0];
|
|
|
|
// Add debugging and validation
|
|
if (!collection || !collection.id) {
|
|
console.error('Collection data invalid:', { collection, identifier, isSlug });
|
|
return res.status(500).json({ error: 'Collection data invalid' });
|
|
}
|
|
|
|
// Get the top 5 rarest cards from the collection
|
|
const thumbnailsResult = await sql`
|
|
SELECT DISTINCT
|
|
cards.id,
|
|
cards.name,
|
|
cards.rarity,
|
|
cards.image_url,
|
|
cards.stock_image_url,
|
|
cards.market_price,
|
|
cards.game,
|
|
cards.set_name,
|
|
cc.quantity
|
|
FROM collection_cards cc
|
|
JOIN cards ON cc.card_id = cards.id
|
|
WHERE cc.collection_id = ${collection.id}
|
|
AND (cards.image_url IS NOT NULL OR cards.stock_image_url IS NOT NULL)
|
|
ORDER BY
|
|
CASE cards.rarity
|
|
WHEN 'mythic' THEN 8
|
|
WHEN 'legendary' THEN 7
|
|
WHEN 'rare' THEN 6
|
|
WHEN 'uncommon' THEN 5
|
|
WHEN 'common' THEN 4
|
|
WHEN 'special' THEN 3
|
|
WHEN 'promo' THEN 2
|
|
WHEN 'token' THEN 1
|
|
ELSE 0
|
|
END DESC,
|
|
cards.market_price DESC NULLS LAST,
|
|
cards.name ASC
|
|
LIMIT 5
|
|
`;
|
|
|
|
const thumbnails = thumbnailsResult.map(card => ({
|
|
id: card.id,
|
|
name: card.name,
|
|
rarity: card.rarity,
|
|
image_url: card.image_url,
|
|
stock_image_url: card.stock_image_url,
|
|
market_price: parseFloat(card.market_price) || 0,
|
|
game: card.game,
|
|
set_name: card.set_name,
|
|
quantity: parseInt(card.quantity) || 1
|
|
}));
|
|
|
|
res.status(200).json(thumbnails);
|
|
|
|
} catch (error) {
|
|
console.error('Error fetching collection thumbnails:', error);
|
|
res.status(500).json({ error: 'Internal server error' });
|
|
}
|
|
}
|