forked from HeyPuter/puter
-
Notifications
You must be signed in to change notification settings - Fork 150
fix: prevent TypeError when validating invalid social media image URLs #60
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Open
PrayagCodes
wants to merge
4
commits into
codepath:main
Choose a base branch
from
PrayagCodes:fix/social-media-image-validation-bug
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
fix: prevent TypeError when validating invalid social media image URLs #60
PrayagCodes
wants to merge
4
commits into
codepath:main
from
PrayagCodes:fix/social-media-image-validation-bug
Conversation
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
The PuterHomepageService was attempting to reassign a const variable (social_media_image) during validation, causing a runtime error that prevented the homepage from loading when invalid URLs were configured. Changes: - Replace const reassignment with mutable variable (validated_social_media_image) - Update URL validation logic to use mutable variable - Update extension validation logic to use mutable variable - Maintain fallback to default image when validation fails The fix ensures that: - Invalid URLs (malformed or non-absolute) are properly detected - URLs without valid image extensions are properly detected - Service gracefully falls back to default image on validation failure - Homepage loads successfully regardless of URL validity Fixes the TypeError: Assignment to constant variable error that occurred at lines 197 and 202 when validating social media image URLs.
Author
|
Unit tests script /**
* Test script to verify the fix for PuterHomepageService social media image validation bug
*
* This test verifies that:
* 1. No runtime errors occur when validating invalid URLs
* 2. Invalid URLs are properly detected and fallback to default image
* 3. Valid URLs are used correctly
* 4. Edge cases (null, undefined, empty) are handled
* 5. The homepage loads successfully regardless of URL validity
*/
const { PuterHomepageService } = require('./src/backend/src/services/PuterHomepageService');
// Create a minimal service instance with required properties
// We use Object.create to avoid calling the constructor which requires service resources
const service = Object.create(PuterHomepageService.prototype);
// Initialize minimal properties needed by generate_puter_page_html
service.service_scripts = [];
service.gui_params = {};
service.require = require; // Use Node's require function
// Helper function to extract social media image URL from HTML
function extractSocialMediaImageUrl(html, env = 'dev') {
const assetDir = env === 'dev' ? '/src' : '/dist';
const defaultImage = `${assetDir}/images/screenshot.png`;
// Check for og:image meta tag
const ogImageMatch = html.match(/<meta property="og:image" content="([^"]+)">/);
if (ogImageMatch) {
return ogImageMatch[1];
}
// Check for twitter:image meta tag
const twitterImageMatch = html.match(/<meta name="twitter:image" content="([^"]+)">/);
if (twitterImageMatch) {
return twitterImageMatch[1];
}
return null;
}
// Common test parameters
const baseParams = {
env: 'dev',
manifest: {},
gui_path: '/gui',
use_bundled_gui: false,
app_origin: 'https://example.com',
api_origin: 'https://api.example.com',
launch_options: {},
gui_params: {}
};
// Test cases
const testCases = [
// Invalid URLs - should fallback to default
{
name: "Invalid file extension (.txt)",
social_media_image: "https://example.com/image.txt",
shouldFallback: true,
description: "URL with invalid extension should fallback to default"
},
{
name: "Malformed URL",
social_media_image: "not-a-valid-url",
shouldFallback: true,
description: "Malformed URL should be rejected and fallback to default"
},
{
name: "Valid URL with invalid extension (.html)",
social_media_image: "https://example.com/image.html",
shouldFallback: true,
description: "Valid URL with invalid extension should fallback to default"
},
{
name: "Relative path",
social_media_image: "/images/test.png",
shouldFallback: true,
description: "Relative path should be rejected and fallback to default"
},
// Valid URLs - should be used as-is
{
name: "Valid URL with .png extension",
social_media_image: "https://example.com/image.png",
shouldFallback: false,
expectedUrl: "https://example.com/image.png",
description: "Valid URL with .png should be used"
},
{
name: "Valid URL with .jpg extension",
social_media_image: "https://example.com/image.jpg",
shouldFallback: false,
expectedUrl: "https://example.com/image.jpg",
description: "Valid URL with .jpg should be used"
},
{
name: "Valid URL with .jpeg extension",
social_media_image: "https://example.com/image.jpeg",
shouldFallback: false,
expectedUrl: "https://example.com/image.jpeg",
description: "Valid URL with .jpeg should be used"
},
{
name: "Valid URL with .gif extension",
social_media_image: "https://example.com/image.gif",
shouldFallback: false,
expectedUrl: "https://example.com/image.gif",
description: "Valid URL with .gif should be used"
},
{
name: "Valid URL with .webp extension",
social_media_image: "https://example.com/image.webp",
shouldFallback: false,
expectedUrl: "https://example.com/image.webp",
description: "Valid URL with .webp should be used"
},
{
name: "Valid URL with uppercase extension (.PNG)",
social_media_image: "https://example.com/image.PNG",
shouldFallback: false,
expectedUrl: "https://example.com/image.PNG",
description: "Valid URL with uppercase extension should be used (case-insensitive check)"
},
// Edge cases - should fallback to default
{
name: "null value",
social_media_image: null,
shouldFallback: true,
description: "null should fallback to default"
},
{
name: "undefined value",
social_media_image: undefined,
shouldFallback: true,
description: "undefined should fallback to default"
},
{
name: "Empty string",
social_media_image: "",
shouldFallback: true,
description: "Empty string should fallback to default"
}
];
console.log("=".repeat(70));
console.log("Testing PuterHomepageService Social Media Image Validation Fix");
console.log("=".repeat(70));
console.log("\nThis test verifies that:");
console.log("1. No runtime errors occur (no TypeError: Assignment to constant variable)");
console.log("2. Invalid URLs are detected and fallback to default image");
console.log("3. Valid URLs are used correctly in the HTML output");
console.log("4. Edge cases (null, undefined, empty) are handled gracefully");
console.log("5. Homepage loads successfully regardless of URL validity");
console.log("=".repeat(70));
console.log();
let testsPassed = 0;
let testsFailed = 0;
const failures = [];
// Run each test case
testCases.forEach((testCase, index) => {
console.log(`Test ${index + 1}: ${testCase.name}`);
console.log(` Description: ${testCase.description}`);
console.log(` Input: social_media_image = ${JSON.stringify(testCase.social_media_image)}`);
let testPassed = true;
let errorMessage = null;
try {
const meta = {
title: "Test App",
description: "Test description",
short_description: "Test short description",
company: "Test Company",
canonical_url: "https://example.com",
social_media_image: testCase.social_media_image
};
const html = service.generate_puter_page_html({
...baseParams,
meta: meta
});
// Verify no errors were thrown
if (!html || typeof html !== 'string') {
testPassed = false;
errorMessage = "HTML output is invalid";
} else {
// Extract the social media image URL from HTML
const imageUrl = extractSocialMediaImageUrl(html, baseParams.env);
const expectedDefaultUrl = `${baseParams.env === 'dev' ? '/src' : '/dist'}/images/screenshot.png`;
if (testCase.shouldFallback) {
// Should fallback to default
if (imageUrl !== expectedDefaultUrl) {
testPassed = false;
errorMessage = `Expected fallback to default image (${expectedDefaultUrl}), but got: ${imageUrl}`;
} else {
console.log(` ✅ Correctly fell back to default image: ${imageUrl}`);
}
} else {
// Should use the provided URL
if (imageUrl !== testCase.expectedUrl) {
testPassed = false;
errorMessage = `Expected URL (${testCase.expectedUrl}), but got: ${imageUrl}`;
} else {
console.log(` ✅ Correctly used provided URL: ${imageUrl}`);
}
}
}
if (testPassed) {
console.log(" ✅ PASSED: No errors, correct behavior");
testsPassed++;
} else {
console.log(` ❌ FAILED: ${errorMessage}`);
testsFailed++;
failures.push({
test: testCase.name,
error: errorMessage
});
}
} catch (error) {
testPassed = false;
const errorMsg = error.message || String(error);
console.log(` ❌ FAILED: Unexpected error thrown`);
console.log(` Error Type: ${error.constructor.name}`);
console.log(` Error Message: ${errorMsg}`);
// Check if it's the bug we're trying to fix
if (errorMsg.includes("Assignment to constant variable")) {
errorMessage = "BUG STILL EXISTS: TypeError: Assignment to constant variable";
} else {
errorMessage = `Unexpected error: ${errorMsg}`;
}
testsFailed++;
failures.push({
test: testCase.name,
error: errorMessage
});
}
console.log();
});
// Summary
console.log("=".repeat(70));
console.log("Test Summary");
console.log("=".repeat(70));
console.log(`Total Tests: ${testCases.length}`);
console.log(`✅ Passed: ${testsPassed}`);
console.log(`❌ Failed: ${testsFailed}`);
console.log();
if (testsFailed > 0) {
console.log("Failed Tests:");
failures.forEach((failure, index) => {
console.log(` ${index + 1}. ${failure.test}: ${failure.error}`);
});
console.log();
}
if (testsPassed === testCases.length) {
console.log("✅ ALL TESTS PASSED!");
console.log("\nThe fix is working correctly:");
console.log("✓ No runtime errors occur");
console.log("✓ Invalid URLs are properly detected and handled");
console.log("✓ Valid URLs are used correctly");
console.log("✓ Edge cases are handled gracefully");
console.log("✓ Homepage loads successfully regardless of URL validity");
console.log("\nAll acceptance criteria and expected behavior requirements are met!");
} else {
console.log("❌ Some tests failed. Please review the failures above.");
}
console.log("=".repeat(70)); |
israx
approved these changes
Dec 1, 2025
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Summary
Fixes a critical bug in
PuterHomepageServicewhere attempting to validate invalid social media image URLs caused a runtime error (TypeError: Assignment to constant variable), preventing the homepage from loading when invalid URLs were configured.Problem
The service was attempting to reassign a
constvariable (social_media_image) during validation checks. In JavaScript,constvariables cannot be reassigned after their initial declaration, causing a runtime error that prevented the homepage from loading.Root Cause
social_media_imagewas destructured as aconstvariable (line 175)nullon lines 197 and 202Impact
TypeError: Assignment to constant variableSolution
Replaced the const reassignment pattern with a mutable variable approach:
letvariable (validated_social_media_image) initialized with the original valueChanges Made
File:
src/backend/src/services/PuterHomepageService.jslet validated_social_media_image = social_media_image;(line 195)Validation Logic
The service now performs two validation checks:
URL Format Validation: Ensures the URL is a valid absolute URL using
is_valid_url()helperhttp://orhttps://File Extension Validation: Ensures the URL ends with a valid image extension
.png,.jpg,.jpeg,.gif,.webpIf either validation fails,
validated_social_media_imageis set tonull, which triggers the fallback to the default image (${asset_dir}/images/screenshot.png).Testing
Automated Tests
Created comprehensive test suite (
test-bug-reproduction.cjs) covering:.txt,.html)All 13 test cases pass successfully.
Manual Testing
Verified the following scenarios:
https://example.com/image.png- Uses provided URL correctlyhttps://example.com/image.txt- Falls back to default imagenot-a-valid-url- Falls back to default imageAll scenarios load successfully without runtime errors.
Acceptance Criteria
Related Files
src/backend/src/services/PuterHomepageService.js- Main fixtest-bug-reproduction.cjs- Test suite (not committed)Breaking Changes
None. This is a bug fix that maintains backward compatibility.
Checklist