diff --git a/client/html/pages/games/games.html b/client/html/pages/games/games.html index 8728818..9f6125a 100644 --- a/client/html/pages/games/games.html +++ b/client/html/pages/games/games.html @@ -43,15 +43,6 @@

Games

-
- - Upload Game - -
diff --git a/client/html/pages/profile/user-profile.html b/client/html/pages/profile/user-profile.html index 7fb7831..10b133f 100644 --- a/client/html/pages/profile/user-profile.html +++ b/client/html/pages/profile/user-profile.html @@ -54,7 +54,7 @@ diff --git a/client/js/avatar.js b/client/js/avatar.js index 061dcad..ff9633b 100644 --- a/client/js/avatar.js +++ b/client/js/avatar.js @@ -1,6 +1,7 @@ $(document).ready(function () { initializeAvatarEditor(); loadUserAvatar(); + setupItemSelection(); }); function initializeAvatarEditor() { @@ -209,8 +210,9 @@ function wearItem(type, itemId) { updateAvatarDisplay(type, response.avatar[type]); updateCurrentlyWearing(type, response.avatar[type]); updateWearButton(type, itemId, true); - showAlert('success', `Wore your ${type} successfully.`); - saveAvatarSelection(type, itemId); + saveRender(); + showAlert('success', `${type.charAt(0).toUpperCase() + type.slice(1)} equipped successfully`); + // saveAvatarSelection(type, itemId); $('.wear-item').removeClass('btn-success').addClass('btn-primary').text('Wear'); $(`.wear-item[data-id="${itemId}"]`).removeClass('btn-primary').addClass('btn-success').text('Wearing'); @@ -229,6 +231,33 @@ function wearItem(type, itemId) { }); } +function saveRender() { + const avatarDisplay = $('#avatar-display'); + const renderData = { + shirt: $('#avatar-shirt').attr('src'), + // Add other avatar elements here when implemented + }; + + const token = localStorage.getItem('token'); + + $.ajax({ + url: '/api/avatar/render', + method: 'POST', + headers: { + Authorization: `Bearer ${token}`, + 'Content-Type': 'application/json' + }, + data: JSON.stringify(renderData), + success: function (response) { + console.log('Render saved successfully:', response); + }, + error: function (xhr, status, error) { + console.error('Error saving render:', error); + showAlert('danger', 'Error saving avatar render. Please try again later.'); + } + }); +} + function removeItem(type) { const token = localStorage.getItem('token'); @@ -245,8 +274,9 @@ function removeItem(type) { $(`#avatar-${type}`).attr('src', ''); $(`#currently-wearing [data-type="${type}"]`).remove(); updateWearButton(type, null, false); + saveRender(); showAlert('info', `Unwore your ${type}.`); - saveAvatarSelection(type, null); + // saveAvatarSelection(type, null); $('.wear-item').removeClass('btn-success').addClass('btn-primary').text('Wear'); }, @@ -258,17 +288,24 @@ function removeItem(type) { } function updateAvatarDisplay(type, item) { + const avatarContainer = $('#avatar-display'); + switch (type) { case 'shirt': if (item && item.ThumbnailLocation) { - $('#avatar-shirt').attr('src', item.ThumbnailLocation); + $('#avatar-shirt').attr('src', item.ThumbnailLocation) + .removeClass('hidden') + .css({ + 'max-width': '100%', + 'height': 'auto', + 'display': 'block', + 'margin': '0 auto' + }); } else { - $('#avatar-shirt').attr('src', ''); + $('#avatar-shirt').attr('src', '/images/default-shirt.png') + .addClass('hidden'); } break; - // Add cases for 'pants' and 'hat' when i makethem - default: - break; } } @@ -279,22 +316,28 @@ function updateCurrentlyWearing(type, item) { container.find(`[data-type="${type}"]`).remove(); if (item && item.ThumbnailLocation && item.Name) { - const itemHtml = ` -
-
-
-

${type.charAt(0).toUpperCase() + type.slice(1)}

-
-
- ${item.Name} -
${item.Name}
- + const itemHtml = ` +
+
+
+

${type.charAt(0).toUpperCase() + type.slice(1)}

+
+
+ ${item.Name} +
${item.Name}
+ +
-
- `; - - container.append(itemHtml); + `; + container.append(itemHtml); } } @@ -310,62 +353,136 @@ function updateWearButton(type, itemId, isWearing) { function loadUserAvatar() { const token = localStorage.getItem('token'); - console.log("hahaahsha"); + if (!token) { + console.error('No token found'); + return; + } + $.ajax({ url: '/api/avatar', method: 'GET', headers: { Authorization: `Bearer ${token}`, + 'Cache-Control': 'no-cache' }, - success: function (avatar) { - if (avatar.shirt && avatar.shirt._id) { - wearItem('shirt', avatar.shirtId); - } + success: function (response) { + console.log('Avatar data received:', response); + if (response && response.avatar) { + // Update the avatar display + updateAvatarDisplay('shirt', response.avatar.shirt); + updateCurrentlyWearing('shirt', response.avatar.shirt); + + if (response.avatar.shirt) { + updateWearButton('shirt', response.avatar.shirt._id, true); + // Store the current state in localStorage + localStorage.setItem('currentAvatar', JSON.stringify(response.avatar)); + } + } + + // Load and display the rendered avatar + if (response.avatarRender && response.avatarRender.shirt) { + $('#avatar-display').attr('src', response.avatarRender.shirt) + .removeClass('hidden') + .css({ + 'max-width': '100%', + 'height': 'auto', + 'display': 'block', + 'margin': '0 auto' + }); + localStorage.setItem('avatarRender', JSON.stringify(response.avatarRender)); + } }, error: function (xhr, status, error) { - console.error('Error loading avatar:', error); - $('#avatar-display').html('
Error loading avatar. Please try again later.
'); - }, + console.error('Error loading avatar:', { + error: error, + status: status, + response: xhr.responseText + }); + showAlert('danger', 'Error loading avatar. Please try again later.'); + } }); } function saveAvatarSelection(type, itemId) { const token = localStorage.getItem('token'); const avatarData = { type, itemId }; - console.log(`Saving avatar selection: ${type}, ID: ${itemId}`); + console.log('Saving avatar selection:', avatarData); $.ajax({ url: '/api/avatar', method: 'PUT', - contentType: 'application/json', headers: { Authorization: `Bearer ${token}`, - 'Content-Type': 'application/json', + 'Content-Type': 'application/json' }, data: JSON.stringify(avatarData), success: function (response) { - console.log('Avatar updated successfully:', response); - if (itemId) { - updateAvatarDisplay(type, response.avatar[type]); - updateCurrentlyWearing(type, response.avatar[type]); - updateWearButton(type, itemId, true); - showAlert('success', `Wore your ${type} successfully.`); - } else { - $(`#avatar-${type}`).attr('src', ''); - $(`#currently-wearing [data-type="${type}"]`).remove(); - updateWearButton(type, null, false); - showAlert('info', `Unwore your ${type}.`); + console.log('Avatar update response:', response); + + if (response.avatar && response.avatarRender) { + // Store the updated state + localStorage.setItem('currentAvatar', JSON.stringify(response.avatar)); + localStorage.setItem('avatarRender', JSON.stringify(response.avatarRender)); + + if (itemId) { + updateAvatarDisplay(type, response.avatar[type]); + updateCurrentlyWearing(type, response.avatar[type]); + updateWearButton(type, itemId, true); + + // Update the rendered avatar display + if (response.avatarRender.shirt) { + $('#avatar-display').attr('src', response.avatarRender.shirt) + .removeClass('hidden'); + } + showAlert('success', `Wore your ${type} successfully.`); + } else { + $(`#avatar-${type}`).attr('src', ''); + $(`#currently-wearing [data-type="${type}"]`).remove(); + updateWearButton(type, null, false); + $('#avatar-display').addClass('hidden'); + showAlert('info', `Unwore your ${type}.`); + } } }, error: function (xhr, status, error) { - console.error('Error updating avatar:', error); - console.error('Status:', status); - console.error('Response:', xhr.responseText); + console.error('Error updating avatar:', { + error: error, + status: status, + response: xhr.responseText + }); showAlert('danger', `Error ${itemId ? 'wearing' : 'unwearing'} ${type}. Please try again later.`); - }, + } }); } +function restoreAvatarState() { + const savedAvatar = localStorage.getItem('currentAvatar'); + const savedRender = localStorage.getItem('avatarRender'); + + if (savedAvatar) { + const avatar = JSON.parse(savedAvatar); + if (avatar.shirt) { + updateAvatarDisplay('shirt', avatar.shirt); + updateCurrentlyWearing('shirt', avatar.shirt); + updateWearButton('shirt', avatar.shirt._id, true); + } + } + + if (savedRender) { + const render = JSON.parse(savedRender); + if (render.shirt) { + $('#avatar-display').attr('src', render.shirt) + .removeClass('hidden') + .css({ + 'max-width': '100%', + 'height': 'auto', + 'display': 'block', + 'margin': '0 auto' + }); + } + } +} + // basic body colors set up for seven function setupBodyColors() { const bodyParts = ['head', 'torso', 'leftArm', 'rightArm', 'leftLeg', 'rightLeg']; @@ -409,3 +526,41 @@ function showAlert(type, message) { } +function loadRenderedAvatar() { + const token = localStorage.getItem('token'); + + $.ajax({ + url: '/api/avatar/render', + method: 'GET', + headers: { + Authorization: `Bearer ${token}`, + 'Cache-Control': 'no-cache' + }, + success: function(response) { + if (response && response.avatarRender) { + if (response.avatarRender.shirt) { + $('#avatar-shirt').attr('src', response.avatarRender.shirt) + .removeClass('hidden') + .css({ + 'max-width': '100%', + 'height': 'auto', + 'display': 'block', + 'margin': '0 auto' + }); + } + } + }, + error: function(xhr, status, error) { + console.error('Error loading rendered avatar:', error); + } + }); +} + +// Update the document ready function +$(document).ready(function () { + initializeAvatarEditor(); + loadUserAvatar(); + loadRenderedAvatar(); + setupItemSelection(); + restoreAvatarState(); +}); \ No newline at end of file diff --git a/client/js/home.js b/client/js/home.js index bef2db0..be88f7a 100644 --- a/client/js/home.js +++ b/client/js/home.js @@ -204,7 +204,7 @@ $(document).ready(function () {

Discord

Join our Discord server and talk to people in our community!

- Join Discord + Join Discord
@@ -222,7 +222,7 @@ $(document).ready(function () {

Twitter

We tweet whenever we post a video, and may even hint at some upcoming events on our Twitter.

- Follow Us + Follow Us
diff --git a/client/js/user-profile.js b/client/js/user-profile.js index 7f921e8..6efce05 100644 --- a/client/js/user-profile.js +++ b/client/js/user-profile.js @@ -15,43 +15,34 @@ $(document).ready(function () { function fetchUserProfile(username) { const token = localStorage.getItem('token'); if (!token) { - console.error('No token found in localStorage'); - $('#user-profile').html( - '

You are not logged in. Please login to view profiles.

' - ); - return; + console.error('No token found in localStorage'); + $('#user-profile').html('

You are not logged in. Please login to view profiles.

'); + return; } $.ajax({ - url: `/api/user/${username}`, - method: 'GET', - headers: { - Authorization: `Bearer ${token}`, - }, - success: function (user) { - currentUser = user; - fetchUserStatus(username).then((isOnline) => { - user.isOnline = isOnline; - - fetchForumPostCount(user._id).then((postCount) => { - user.forumPostCount = postCount; - - displayUserProfile(user); - }); - }); - document.getElementById( - 'profile-title' - ).textContent = `${user.username}'s Profile - Valkyrie`; - }, - error: function (xhr, status, error) { - console.error('Error fetching user profile:', xhr.responseText); - console.error('Status:', status); - console.error('Error:', error); - $('#user-profile').html( - '

Error fetching user profile. Please try again. If the problem persists, please login again.

' - ); - }, + url: `/api/user/${username}`, + method: 'GET', + headers: { + Authorization: `Bearer ${token}`, + }, + success: function (user) { + console.log('User profile data received:', user); // Add this line + currentUser = user; + fetchUserStatus(username).then((isOnline) => { + user.isOnline = isOnline; + fetchForumPostCount(user._id).then((postCount) => { + user.forumPostCount = postCount; + displayUserProfile(user); + }); + }); + document.getElementById('profile-title').textContent = `${user.username}'s Profile - Valkyrie`; + }, + error: function (xhr, status, error) { + console.error('Error fetching user profile:', xhr.responseText); + $('#user-profile').html('

Error fetching user profile. Please try again.

'); + }, }); - } +} function fetchUserStatus(username) { return new Promise((resolve, reject) => { @@ -86,6 +77,11 @@ $(document).ready(function () { } function displayUserProfile(user) { + console.log('Displaying profile for user:', { + userId: user.userId, + hasAvatarRender: !!user.avatarRender, + avatarRenderDetails: user.avatarRender + }); const isOwnProfile = user.username === localStorage.getItem('username'); let actionButton = ''; let onlineStatus = user.isOnline @@ -119,40 +115,31 @@ $(document).ready(function () {

${onlineStatus}

-

https://www.valk.fun/user-profile?username=${encodeURIComponent( - user.username - )}

- ${escapeHtml(user.username)} -
-
-
-

${ - user.blurb - ? escapeHtml(user.blurb).replace( - /\n/g, - '
' - ) - : 'No blurb set.' - }

-
-
- ${ - isOwnProfile - ? '' - : '' - } -
-
${actionButton}
- -
+

https://www.valk.fun/user-profile?username=${encodeURIComponent(user.username)}

+
+
- `; +
+
+
+

${user.blurb ? escapeHtml(user.blurb).replace(/\n/g, '
') : 'No blurb set.'}

+
+
+ ${isOwnProfile ? '' : ''} +
+
${actionButton}
+ + + `; $('#user-info').html(userInfoHtml); + + if (user.userId) { + loadUserAvatar(user.userId); + } else { + console.error('No userId found in user object:', user); + $('#profile-avatar').html('
Unable to load avatar: Missing user ID
'); + } const statisticsHtml = `
@@ -575,6 +562,49 @@ $(document).ready(function () { }); } + + + + function loadUserAvatar(userId) { + if (!userId) { + console.error('No userId provided to loadUserAvatar'); + return; + } + + const token = localStorage.getItem('token'); + $.ajax({ + url: `/api/avatar/render/${userId}`, + method: 'GET', + headers: { + Authorization: `Bearer ${token}` + }, + success: function(response) { + console.log('Avatar response:', response); + if (response && response.avatarRender && response.avatarRender.shirt) { + $('#profile-avatar').html(` + User Avatar + `); + } else { + console.warn('No avatar render data found'); + $('#profile-avatar').html('
No avatar available
'); + } + }, + error: function(xhr, status, error) { + console.error('Error loading user avatar:', { + status: status, + error: error, + response: xhr.responseText, + userId: userId + }); + $('#profile-avatar').html('
Error loading avatar
'); + } + }); +} + function displayUserShirts(shirts, userId) { const shirtsContainer = $('#user-shirts'); shirtsContainer.empty(); diff --git a/server/functions/api/models/User.js b/server/functions/api/models/User.js index a056dd1..3ee2adc 100644 --- a/server/functions/api/models/User.js +++ b/server/functions/api/models/User.js @@ -161,6 +161,18 @@ const userSchema = new mongoose.Schema({ ref: 'Asset', }, ], + + avatarRender: { + shirt: { + type: String, + default: null + }, + lastUpdated: { + type: Date, + default: Date.now + } + } + }); userSchema.pre('save', async function (next) { diff --git a/server/functions/api/routes/avatar.js b/server/functions/api/routes/avatar.js index 75e9698..7c32fd4 100644 --- a/server/functions/api/routes/avatar.js +++ b/server/functions/api/routes/avatar.js @@ -11,91 +11,212 @@ router.get('/', authenticateToken, async (req, res) => { res.set('Pragma', 'no-cache'); res.set('Expires', '0'); try { - console.log('Fetching avatar for userId:', req.user.userId); - const user = await User.findOne({ userId: req.user.userId }).select('avatar'); + console.log('Fetching avatar and render data for userId:', req.user.userId); + const user = await User.findOne({ userId: req.user.userId }) + .select('avatar avatarRender') + .populate('avatar.shirt'); if (!user) { - console.error('User not found for userId:', req.user.userId); + console.error('User not found:', { userId: req.user.userId }); return res.status(404).json({ error: 'User not found' }); } - console.log('Avatar fetched successfully:', user.avatar); - res.json(user.avatar); + console.log('Avatar data fetched:', { + userId: req.user.userId, + hasAvatar: !!user.avatar, + avatarDetails: user.avatar, + hasAvatarRender: !!user.avatarRender, + renderDetails: user.avatarRender + }); + + res.json({ + avatar: user.avatar, + avatarRender: user.avatarRender + }); } catch (error) { - console.error('Error fetching avatar:', error); + console.error('Error fetching avatar data:', { + error: error.message, + stack: error.stack, + userId: req.user.userId + }); res.status(500).json({ error: 'Internal server error', details: error.message }); } }); -// Update avatar -router.put('/', authenticateToken, async (req, res) => { +router.get('/render/:userId', async (req, res) => { try { - const { type, itemId } = req.body; - console.log('Updating avatar:', { userId: req.user.userId, type, itemId }); - - if (!type || !['shirt', 'pants', 'hat'].includes(type)) { - console.error('Invalid or missing item type:', type); - return res.status(400).json({ error: 'Invalid or missing item type' }); + const user = await User.findOne({ userId: parseInt(req.params.userId) }); + + if (!user) { + console.log('User not found for avatar render:', req.params.userId); + return res.status(404).json({ error: 'User not found' }); } - const user = await User.findOne({ userId: req.user.userId }).populate('inventory'); + // Return both the shirt URL and display URL + res.json({ + avatarRender: { + ...user.avatarRender, + displayUrl: user.avatarRender?.displayUrl || user.avatarRender?.shirt + } + }); + } catch (error) { + console.error('Error fetching avatar render:', { + error: error.message, + stack: error.stack, + userId: req.params.userId + }); + res.status(500).json({ + error: 'Internal server error', + details: error.message + }); + } +}); + + + +router.post('/render', authenticateToken, async (req, res) => { + try { + const { shirt, displayUrl } = req.body; + const user = await User.findOne({ userId: req.user.userId }); if (!user) { - console.error('User not found for userId:', req.user.userId); + console.log('User not found:', req.user.userId); return res.status(404).json({ error: 'User not found' }); } - if (!user.avatar) { - user.avatar = {}; + if (!user.avatarRender) { + user.avatarRender = {}; } - console.log('User inventory:', user.inventory.map(item => ({ id: item._id.toString(), type: item.AssetType }))); + // Update the render data with both the shirt URL and display URL + user.avatarRender = { + ...user.avatarRender, + shirt, + displayUrl: displayUrl || shirt, // Use displayUrl if provided, otherwise use shirt URL + lastUpdated: new Date() + }; + await user.save(); + console.log('Avatar render saved:', user.avatarRender); - switch (type) { - case 'shirt': - if (itemId) { - if (!mongoose.Types.ObjectId.isValid(itemId)) { - console.error('Invalid shirt ID:', itemId); - return res.status(400).json({ error: 'Invalid shirt ID' }); - } + res.json({ + message: 'Avatar render saved successfully', + avatarRender: user.avatarRender + }); + } catch (error) { + console.error('Error saving avatar render:', { + error: error.message, + stack: error.stack, + userId: req.user.userId + }); + res.status(500).json({ + error: 'Internal server error', + details: error.message + }); + } +}); + +// Update avatar +router.put('/', authenticateToken, async (req, res) => { + try { + const { type, itemId } = req.body; + console.log('Updating avatar:', { + userId: req.user.userId, + type, + itemId, + timestamp: new Date().toISOString() + }); - console.log('Checking inventory for shirt:', itemId); + const user = await User.findOne({ userId: req.user.userId }) + .populate('inventory') + .populate('avatar.shirt'); + + if (!user) { + console.error('User not found:', { userId: req.user.userId }); + return res.status(404).json({ error: 'User not found' }); + } - const inventoryItem = user.inventory.find(item => - item._id.toString() === itemId && item.AssetType === 'Shirt' - ); + if (!user.avatar) user.avatar = {}; + if (!user.avatarRender) user.avatarRender = {}; - const createdShirt = await Asset.findOne({ + switch (type) { + case 'shirt': + if (itemId) { + const shirtAsset = await Asset.findOne({ _id: itemId, - creator: user._id, - AssetType: 'Shirt' - }).populate('creator', 'username'); + AssetType: 'Shirt', + $or: [ + { _id: { $in: user.inventory } }, + { creator: user._id } + ] + }); - if (!inventoryItem && !createdShirt) { - console.error('Shirt not in user inventory or not created by user:', itemId); - return res.status(400).json({ error: 'Shirt not in user inventory or not created by u' }); + if (!shirtAsset) { + console.error('Shirt not accessible:', { + userId: req.user.userId, + shirtId: itemId + }); + return res.status(400).json({ + error: 'Shirt not in inventory or not created by user' + }); } - console.log('Setting shirt:', itemId); - user.avatar.shirt = createdShirt || inventoryItem; + console.log('Wearing shirt:', { + userId: req.user.userId, + shirtId: itemId, + shirtDetails: { + name: shirtAsset.Name, + imageUrl: shirtAsset.imageUrl + } + }); + + user.avatar.shirt = shirtAsset; + user.avatarRender = { + ...user.avatarRender, + shirt: shirtAsset.imageUrl, + displayUrl: shirtAsset.imageUrl, + lastUpdated: new Date() + }; } else { - console.log('Unwearing shirt'); + console.log('Removing shirt from avatar:', { + userId: req.user.userId, + previousShirt: user.avatar.shirt + }); user.avatar.shirt = null; + user.avatarRender = { + ...user.avatarRender, + shirt: null, + displayUrl: null, + lastUpdated: new Date() + }; } break; - // cases for pants and hats can be added here later - default: - console.error('Unsupported item type:', type); - return res.status(400).json({ error: 'Unsupported item type' }); } await user.save(); - console.log('Avatar updated successfully for userId:', req.user.userId, 'New avatar:', user.avatar); - res.json({ message: 'Avatar updated successfully', avatar: user.avatar }); + console.log('Avatar update successful:', { + userId: req.user.userId, + newAvatarState: user.avatar, + newRenderState: user.avatarRender, + timestamp: new Date().toISOString() + }); + + res.json({ + message: 'Avatar updated successfully', + avatar: user.avatar, + avatarRender: user.avatarRender + }); } catch (error) { - console.error('Error updating avatar:', error); - res.status(500).json({ error: 'Internal server error', details: error.message, stack: error.stack }); + console.error('Avatar update failed:', { + error: error.message, + stack: error.stack, + userId: req.user.userId, + requestBody: req.body + }); + res.status(500).json({ + error: 'Internal server error', + details: error.message + }); } }); diff --git a/server/functions/api/routes/user.js b/server/functions/api/routes/user.js index 208f99b..07f9efd 100644 --- a/server/functions/api/routes/user.js +++ b/server/functions/api/routes/user.js @@ -7,33 +7,62 @@ const User = require('../models/User'); router.get('/user/:username', authenticateToken, async (req, res) => { try { const { username } = req.params; + console.log('Fetching profile for username:', username); + const currentUser = await User.findOne({ userId: req.user.userId }); - const user = await User.findOne({ username }).select( - 'username userId signupDate lastLoggedIn blurb friendRequests friends sentFriendRequests' - ); + if (!currentUser) { + console.error('Current user not found:', req.user.userId); + return res.status(404).json({ error: 'Current user not found' }); + } + + const user = await User.findOne({ username }) + .select('username userId signupDate lastLoggedIn blurb friendRequests friends sentFriendRequests avatarRender') + .lean(); if (!user) { + console.error('Target user not found:', username); return res.status(404).json({ error: 'User not found' }); } + console.log('User found:', { + userId: user.userId, + hasAvatarRender: !!user.avatarRender, + avatarRenderDetails: user.avatarRender + }); + const isFriend = currentUser.friends.includes(user.userId); const friendRequestSent = user.friendRequests.includes(currentUser.userId); const friendRequestReceived = currentUser.friendRequests.includes(user.userId); - const userObject = user.toObject(); - delete userObject.friendRequests; - delete userObject.friends; - delete userObject.sentFriendRequests; + delete user.friendRequests; + delete user.friends; + delete user.sentFriendRequests; - res.json({ - ...userObject, + const responseData = { + ...user, isFriend, friendRequestSent, friendRequestReceived, + }; + + console.log('Sending profile response:', { + userId: responseData.userId, + hasAvatarRender: !!responseData.avatarRender, + avatarRenderDetails: responseData.avatarRender }); + + res.json(responseData); } catch (error) { - console.error('User profile error:', error); - res.status(500).json({ error: 'Error fetching user profile' }); + console.error('User profile error:', { + error: error.message, + stack: error.stack, + username: req.params.username, + userId: req.user.userId + }); + res.status(500).json({ + error: 'Error fetching user profile', + details: error.message + }); } }); @@ -107,4 +136,36 @@ router.get('/user-info', authenticateToken, async (req, res) => { } }); +router.get('/:userId/avatar', async (req, res) => { + try { + console.log('Fetching avatar for userId:', req.params.userId); + + const user = await User.findOne({ userId: req.params.userId }); + if (!user) { + console.error('User not found for avatar request:', req.params.userId); + return res.status(404).json({ error: 'User not found' }); + } + + console.log('Avatar data found:', { + userId: user.userId, + hasAvatarRender: !!user.avatarRender, + avatarRenderDetails: user.avatarRender + }); + + res.json({ + avatarRender: user.avatarRender + }); + } catch (error) { + console.error('Error fetching user avatar render:', { + error: error.message, + stack: error.stack, + userId: req.params.userId + }); + res.status(500).json({ + error: 'Internal server error', + details: error.message + }); + } +}); + module.exports = router;