Fix dark theme colors, reload button functionality, and code cleanup

This commit is contained in:
2026-01-23 12:50:56 +01:00
parent fd537026d3
commit cebae83ae1
5 changed files with 145 additions and 563 deletions

View File

@@ -1,13 +1,14 @@
{ {
"name": "jmespath-playground", "name": "jmespath-playground",
"version": "1.2.1", "version": "1.2.2",
"description": "A React-based web application for testing JMESPath expressions against JSON data", "description": "A React-based web application for testing JMESPath expressions against JSON data",
"main": "index.js", "main": "index.js",
"scripts": { "scripts": {
"start": "react-scripts start", "start": "react-scripts start",
"prebuild": "node scripts/version-check.js", "prebuild": "node scripts/version-check.js",
"build": "react-scripts build", "build": "react-scripts build",
"test": "react-scripts test", "test": "react-scripts test --watchAll=false",
"test:watch": "react-scripts test",
"server": "node server.js" "server": "node server.js"
}, },
"engines": { "engines": {

View File

@@ -1,42 +1,10 @@
/* JMESPath Testing Tool Custom Styles */ /* JMESPath Testing Tool Custom Styles */
:root { :root {
/* Light theme colors */ /* Common variables */
--bg-primary-light: #ffffff; --font-mono: 'Monaco', 'Menlo', 'Ubuntu Mono', 'Consolas', monospace;
--bg-secondary-light: #f8f9fa;
--text-primary-light: #212529;
--text-secondary-light: #495057;
--text-muted-light: #6c757d;
--border-light: #dee2e6;
--border-input-light: #ced4da;
--accent-color: #007bff; --accent-color: #007bff;
--accent-shadow: rgba(0, 123, 255, 0.25);
/* Dark theme colors */
--bg-primary-dark: #1a1a1a;
--bg-secondary-dark: #2d2d2d;
--bg-card-dark: #323232;
--text-primary-dark: #ffffff;
--text-secondary-dark: #e9ecef;
--text-muted-dark: #adb5bd;
--border-dark: #495057;
--border-input-dark: #6c757d;
/* State colors */
--success-bg-light: #d4edda;
--success-border-light: #c3e6cb;
--success-text-light: #155724;
--success-bg-dark: #1e4a1e;
--success-border-dark: #2c6d2c;
--success-text-dark: #d4edda;
--error-bg-light: #f8d7da;
--error-border-light: #f5c6cb;
--error-text-light: #721c24;
--error-bg-dark: #4a1e1e;
--error-border-dark: #6d2c2c;
--error-text-dark: #f8d7da;
/* Button variants */ /* Button variants */
--btn-success: #28a745; --btn-success: #28a745;
--btn-info: #17a2b8; --btn-info: #17a2b8;
@@ -98,16 +66,10 @@ body {
.jmespath-input { .jmespath-input {
font-size: 14px; font-size: 14px;
padding: 10px; padding: 10px;
background-color: var(--bg-primary-light);
border: 1px solid var(--border-input-light);
color: var(--text-secondary-light);
} }
.json-input, .result-output { .json-input, .result-output {
font-size: 13px; font-size: 13px;
background-color: var(--bg-secondary-light);
border: 1px solid var(--border-light);
color: var(--text-secondary-light);
line-height: 1.4; line-height: 1.4;
} }
@@ -125,15 +87,6 @@ footer {
flex-shrink: 0; flex-shrink: 0;
} }
footer a {
color: var(--text-muted-light);
transition: color var(--transition-fast);
}
footer a:hover {
color: var(--text-secondary-light);
}
/* Responsive adjustments */ /* Responsive adjustments */
@media (max-width: 768px) { @media (max-width: 768px) {
.header-section { .header-section {
@@ -158,519 +111,152 @@ footer a:hover {
} }
} }
/* Manual theme overrides */ /* Bootstrap theme integration */
.theme-light { [data-bs-theme="light"] {
/* Force light theme regardless of system preference */ --bg-primary: #ffffff;
background-color: #ffffff !important; --bg-secondary: #f8f9fa;
color: #212529 !important; --text-primary: #212529;
--text-secondary: #495057;
--text-muted: #6c757d;
--border: #dee2e6;
--border-input: #ced4da;
--success-bg: #d4edda;
--success-border: #c3e6cb;
--success-text: #155724;
--error-bg: #f8d7da;
--error-border: #f5c6cb;
--error-text: #721c24;
} }
.theme-light .header-section { [data-bs-theme="dark"] {
background-color: transparent !important; --bg-primary: #1a1a1a;
border-bottom: none !important; --bg-secondary: #2d2d2d;
--bg-card: #323232;
--text-primary: #ffffff;
--text-secondary: #e9ecef;
--text-muted: #adb5bd;
--border: #495057;
--border-input: #6c757d;
--success-bg: #1e4a1e;
--success-border: #2c6d2c;
--success-text: #d4edda;
--error-bg: #4a1e1e;
--error-border: #6d2c2c;
--error-text: #f8d7da;
} }
.theme-light .card { /* Apply theme colors */
background-color: #ffffff !important; body {
box-shadow: 0 2px 8px rgba(0,0,0,0.1) !important; background-color: var(--bg-primary);
color: #212529 !important; color: var(--text-secondary);
} }
.theme-light .card-header { .card {
background-color: #f8f9fa !important; background-color: var(--bg-primary);
border-bottom: 2px solid #dee2e6 !important; border-color: var(--border);
color: #212529 !important; color: var(--text-primary);
} }
.theme-light .jmespath-input { .card-header {
background-color: #ffffff; background-color: var(--bg-secondary);
border: 1px solid #ced4da; border-bottom-color: var(--border);
color: #495057; color: var(--text-primary);
} }
.theme-light .json-input, .jmespath-input {
.theme-light .result-output { background-color: var(--bg-primary);
background-color: #f8f9fa !important; border-color: var(--border-input);
border: 1px solid #dee2e6 !important; color: var(--text-secondary);
color: #495057 !important;
} }
/* Success and Error state overrides - must come after base input rules */ .json-input, .result-output {
.theme-light .jmespath-input.success { background-color: var(--bg-secondary);
background-color: #d4edda !important; border-color: var(--border);
border-color: #c3e6cb !important; color: var(--text-secondary);
color: #155724 !important;
} }
.theme-light .jmespath-input.error { footer {
background-color: #f8d7da !important; background-color: var(--bg-secondary);
border-color: #f5c6cb !important; color: var(--text-secondary);
color: #721c24 !important;
} }
.theme-light .text-muted { footer.bg-light {
color: #6c757d !important; background-color: var(--bg-secondary) !important;
} }
.theme-light .jmespath-input:focus { footer a {
border-color: var(--accent-color); color: var(--text-muted);
box-shadow: 0 0 0 0.2rem var(--accent-shadow);
} }
.theme-light .jmespath-input::placeholder { footer a:hover {
color: var(--text-muted-light) !important; color: var(--text-secondary);
} }
.theme-light .json-input::placeholder, /* State styles */
.theme-light .result-output::placeholder { .jmespath-input.success {
color: var(--text-muted-light) !important; background-color: var(--success-bg) !important;
border-color: var(--success-border) !important;
color: var(--success-text) !important;
} }
.theme-light .json-input:focus, .jmespath-input.error {
.theme-light .result-output:focus { background-color: var(--error-bg) !important;
background-color: var(--bg-primary-light) !important; border-color: var(--error-border) !important;
border-color: var(--accent-color) !important; color: var(--error-text) !important;
color: var(--text-secondary-light) !important;
box-shadow: 0 0 0 0.2rem var(--accent-shadow) !important;
} }
.theme-light .output-section .form-control { .json-input.success {
background-color: #f8f9fa !important; background-color: var(--success-bg) !important;
border-color: var(--success-border) !important;
color: var(--success-text) !important;
} }
.theme-light .alert-danger { .json-input.error {
background-color: #f8d7da !important; background-color: var(--error-bg) !important;
border-color: #f5c6cb !important; border-color: var(--error-border) !important;
color: #721c24 !important; color: var(--error-text) !important;
} }
.theme-light .alert-success { /* Focus states */
background-color: #d4edda !important; .jmespath-input:focus {
border-color: #c3e6cb !important; border-color: var(--accent-color, #007bff);
color: #155724 !important; box-shadow: 0 0 0 0.2rem rgba(0, 123, 255, 0.25);
} }
.theme-light .btn-primary { .json-input:focus,
background-color: var(--btn-primary) !important; .result-output:focus {
border-color: var(--btn-primary) !important; background-color: var(--bg-primary);
color: var(--bg-primary-light) !important; border-color: var(--accent-color, #007bff);
color: var(--text-secondary);
box-shadow: 0 0 0 0.2rem rgba(0, 123, 255, 0.25);
} }
.theme-light .btn-outline-secondary { /* Placeholder colors */
color: var(--btn-secondary) !important; .jmespath-input::placeholder,
border-color: var(--btn-secondary) !important; .json-input::placeholder,
.result-output::placeholder {
color: var(--text-muted);
} }
.theme-light .btn-outline-secondary:hover { /* Alert styles */
background-color: var(--btn-secondary) !important; .alert-danger {
border-color: var(--btn-secondary) !important; background-color: var(--error-bg);
color: var(--bg-primary-light) !important; border-color: var(--error-border);
color: var(--error-text);
} }
.theme-light .btn-outline-success { /* Code block styles */
color: var(--btn-success) !important; pre.bg-light {
border-color: var(--btn-success) !important; background-color: var(--bg-secondary) !important;
color: var(--text-secondary) !important;
border-color: var(--border) !important;
} }
.theme-light .btn-outline-success:hover { code {
background-color: var(--btn-success) !important; color: var(--text-secondary);
border-color: var(--btn-success) !important;
color: var(--bg-primary-light) !important;
} }
.theme-light .btn-outline-info {
color: var(--btn-info) !important;
border-color: var(--btn-info) !important;
}
.theme-light .btn-outline-info:hover {
background-color: var(--btn-info) !important;
border-color: var(--btn-info) !important;
color: var(--bg-primary-light) !important;
}
.theme-light .btn-outline-primary {
color: var(--btn-primary) !important;
border-color: var(--btn-primary) !important;
}
.theme-light .btn-outline-primary:hover {
background-color: var(--btn-primary) !important;
border-color: var(--btn-primary) !important;
color: var(--bg-primary-light) !important;
}
.theme-light .btn-outline-danger {
color: var(--btn-danger) !important;
border-color: var(--btn-danger) !important;
}
.theme-light .btn-outline-danger:hover {
background-color: var(--btn-danger) !important;
border-color: var(--btn-danger) !important;
color: var(--bg-primary-light) !important;
}
.theme-light footer {
background-color: #f8f9fa !important;
border-top: 1px solid #dee2e6 !important;
color: #212529 !important;
}
.theme-light footer a {
color: #6c757d !important;
}
.theme-light footer a:hover {
color: #495057 !important;
}
/* Force dark theme regardless of system preference */
.theme-dark {
background-color: var(--bg-primary-dark) !important;
color: var(--text-secondary-dark) !important;
}
.theme-dark .header-section {
background-color: var(--bg-secondary-dark) !important;
border-bottom: 1px solid #404040 !important;
}
.theme-dark .card {
background-color: var(--bg-secondary-dark) !important;
box-shadow: 0 2px 8px rgba(0,0,0,0.3) !important;
color: var(--text-secondary-dark) !important;
}
.theme-dark .card-header {
background-color: var(--bg-card-dark) !important;
border-bottom: 2px solid #505050 !important;
color: var(--text-primary-dark) !important;
}
.theme-dark .jmespath-input {
background-color: var(--bg-card-dark);
border: 1px solid #505050;
color: var(--text-primary-dark);
}
/* Success and Error state overrides - must come after base input rules */
.theme-dark .jmespath-input.success {
background-color: #1e4a1e !important;
border-color: #2c6d2c !important;
color: #d4edda !important;
}
.theme-dark .jmespath-input.error {
background-color: #4a1e1e !important;
border-color: #6d2c2c !important;
color: #f8d7da !important;
}
.theme-dark .jmespath-input::placeholder {
color: var(--text-muted-dark) !important;
}
.theme-dark .jmespath-input:focus {
border-color: var(--accent-color);
}
.theme-dark .json-input,
.theme-dark .result-output {
background-color: #2a2a2a !important;
border: 1px solid #505050 !important;
color: var(--text-secondary-dark) !important;
}
.theme-dark .json-input::placeholder,
.theme-dark .result-output::placeholder {
color: var(--text-muted-dark) !important;
}
.theme-dark .json-input:focus,
.theme-dark .result-output:focus {
background-color: var(--bg-card-dark) !important;
border-color: var(--accent-color) !important;
color: var(--text-primary-dark) !important;
}
.theme-dark .output-section .form-control {
background-color: var(--bg-secondary-dark) !important;
}
.theme-dark .alert-danger {
background-color: #3d1a1a !important;
border-color: #dc3545 !important;
color: #f8d7da !important;
}
.theme-dark .alert-success {
background-color: #1e4a1e !important;
border-color: #2c6d2c !important;
color: #d4edda !important;
}
.theme-dark .text-muted {
color: var(--text-muted-dark) !important;
}
.theme-dark footer {
background-color: var(--bg-secondary-dark) !important;
border-top: 1px solid #404040 !important;
color: var(--text-secondary-dark) !important;
}
.theme-dark footer a {
color: var(--text-muted-dark) !important;
}
.theme-dark footer a:hover {
color: var(--text-secondary-dark) !important;
}
.theme-dark .btn-primary {
background-color: var(--btn-primary) !important;
border-color: var(--btn-primary) !important;
color: var(--bg-primary-light) !important;
}
.theme-dark .btn-outline-secondary {
color: var(--btn-secondary) !important;
border-color: var(--btn-secondary) !important;
}
.theme-dark .btn-outline-secondary:hover {
background-color: var(--btn-secondary) !important;
border-color: var(--btn-secondary) !important;
color: var(--bg-primary-light) !important;
}
.theme-dark .btn-outline-success {
color: var(--btn-success) !important;
border-color: var(--btn-success) !important;
}
.theme-dark .btn-outline-success:hover {
background-color: var(--btn-success) !important;
border-color: var(--btn-success) !important;
color: var(--bg-primary-light) !important;
}
.theme-dark .btn-outline-info {
color: var(--btn-info) !important;
border-color: var(--btn-info) !important;
}
.theme-dark .btn-outline-info:hover {
background-color: var(--btn-info) !important;
border-color: var(--btn-info) !important;
color: var(--bg-primary-light) !important;
}
.theme-light .btn-outline-info {
color: var(--btn-info) !important;
border-color: var(--btn-info) !important;
}
.theme-light .btn-outline-info:hover {
background-color: var(--btn-info) !important;
border-color: var(--btn-info) !important;
color: var(--bg-primary-light) !important;
}
.theme-dark .btn-outline-info {
color: var(--btn-info) !important;
border-color: var(--btn-info) !important;
}
.theme-dark .btn-outline-info:hover {
background-color: var(--btn-info) !important;
border-color: var(--btn-info) !important;
color: var(--bg-primary-light) !important;
}
.theme-dark .btn-outline-primary {
color: var(--btn-primary) !important;
border-color: var(--btn-primary) !important;
}
.theme-dark .btn-outline-primary:hover {
background-color: var(--btn-primary) !important;
border-color: var(--btn-primary) !important;
color: var(--bg-primary-light) !important;
}
.theme-dark .btn-outline-danger {
color: var(--btn-danger) !important;
border-color: var(--btn-danger) !important;
}
.theme-dark .btn-outline-danger:hover {
background-color: var(--btn-danger) !important;
border-color: var(--btn-danger) !important;
color: var(--bg-primary-light) !important;
}
/* Dark mode support */
@media (prefers-color-scheme: dark) {
body:not(.theme-light):not(.theme-dark) {
background-color: var(--bg-primary-dark);
color: var(--text-secondary-dark);
}
body:not(.theme-light):not(.theme-dark) .header-section {
background-color: var(--bg-secondary-dark);
border-bottom: 1px solid var(--border-dark);
}
body:not(.theme-light):not(.theme-dark) .card {
background-color: var(--bg-secondary-dark);
box-shadow: 0 2px 8px rgba(0,0,0,0.3);
color: var(--text-secondary-dark);
}
body:not(.theme-light):not(.theme-dark) .card-header {
background-color: var(--bg-card-dark);
border-bottom: 2px solid var(--border-dark);
color: var(--text-primary-dark);
}
body:not(.theme-light):not(.theme-dark) .jmespath-input {
background-color: var(--bg-card-dark) !important;
border: 1px solid var(--border-input-dark) !important;
color: var(--text-primary-dark) !important;
}
body:not(.theme-light):not(.theme-dark) .jmespath-input.success {
background-color: var(--success-bg-dark) !important;
border-color: var(--success-border-dark) !important;
color: var(--success-text-dark) !important;
}
body:not(.theme-light):not(.theme-dark) .jmespath-input.error {
background-color: var(--error-bg-dark) !important;
border-color: var(--error-border-dark) !important;
color: var(--error-text-dark) !important;
}
body:not(.theme-light):not(.theme-dark) .jmespath-input::placeholder {
color: var(--text-muted-dark);
}
body:not(.theme-light):not(.theme-dark) .jmespath-input:focus {
border-color: var(--accent-color);
box-shadow: 0 0 0 0.2rem var(--accent-shadow);
}
body:not(.theme-light):not(.theme-dark) .json-input,
body:not(.theme-light):not(.theme-dark) .result-output {
background-color: #2a2a2a;
border: 1px solid var(--border-input-dark);
color: var(--text-secondary-dark);
}
body:not(.theme-light):not(.theme-dark) .json-input::placeholder,
body:not(.theme-light):not(.theme-dark) .result-output::placeholder {
color: var(--text-muted-dark);
}
body:not(.theme-light):not(.theme-dark) .json-input:focus,
body:not(.theme-light):not(.theme-dark) .result-output:focus {
background-color: #323232;
border-color: var(--accent-color);
color: var(--text-primary-dark);
box-shadow: 0 0 0 0.2rem var(--accent-shadow);
}
body:not(.theme-light):not(.theme-dark) .alert-danger {
background-color: var(--error-bg-dark);
border-color: var(--error-border-dark);
color: var(--error-text-dark);
}
body:not(.theme-light):not(.theme-dark) .alert-success {
background-color: var(--success-bg-dark);
border-color: var(--success-border-dark);
color: var(--success-text-dark);
}
body:not(.theme-light):not(.theme-dark) .text-muted {
color: var(--text-muted-dark) !important;
}
body:not(.theme-light):not(.theme-dark) footer.bg-light {
background-color: var(--bg-secondary-dark) !important;
border-top: 1px solid var(--border-dark) !important;
color: var(--text-secondary-dark) !important;
}
body:not(.theme-light):not(.theme-dark) footer .text-muted {
color: var(--text-muted-dark) !important;
}
body:not(.theme-light):not(.theme-dark) footer a {
color: var(--text-muted-dark) !important;
}
body:not(.theme-light):not(.theme-dark) footer a:hover {
color: var(--text-secondary-dark) !important;
}
/* Bootstrap dark mode overrides */
body:not(.theme-light):not(.theme-dark) .btn-outline-info {
color: var(--btn-info);
border-color: var(--btn-info);
}
body:not(.theme-light):not(.theme-dark) .btn-outline-info:hover {
background-color: var(--btn-info);
border-color: var(--btn-info);
color: var(--bg-primary-light);
}
body:not(.theme-light):not(.theme-dark) .btn-outline-success {
color: var(--btn-success);
border-color: var(--btn-success);
}
body:not(.theme-light):not(.theme-dark) .btn-outline-success:hover {
background-color: var(--btn-success);
border-color: var(--btn-success);
color: var(--bg-primary-light);
}
.btn-outline-info {
color: #17a2b8;
border-color: #17a2b8;
}
.btn-outline-info:hover {
background-color: #17a2b8;
border-color: #17a2b8;
color: #fff;
}
.btn-outline-primary {
color: #007bff;
border-color: #007bff;
}
.btn-outline-primary:hover {
background-color: #007bff;
border-color: #007bff;
color: #fff;
}
.btn-outline-secondary {
color: #6c757d;
border-color: #6c757d;
}
.btn-outline-secondary:hover {
background-color: #6c757d;
border-color: var(--btn-secondary);
color: #fff;
}
.btn-outline-danger {
color: var(--btn-danger);
border-color: var(--btn-danger);
}
.btn-outline-danger:hover {
background-color: var(--btn-danger);
border-color: var(--btn-danger);
color: #fff;
}
}

View File

@@ -45,21 +45,12 @@ function App() {
// Theme management // Theme management
useEffect(() => { useEffect(() => {
// Apply theme to document
const applyTheme = (selectedTheme) => { const applyTheme = (selectedTheme) => {
const root = document.documentElement; const effectiveTheme = selectedTheme === 'auto'
const body = document.body; ? (window.matchMedia && window.matchMedia('(prefers-color-scheme: dark)').matches ? 'dark' : 'light')
: selectedTheme;
// Clear existing theme classes from both html and body
root.className = ''; document.documentElement.setAttribute('data-bs-theme', effectiveTheme);
body.classList.remove('theme-light', 'theme-dark');
if (selectedTheme === 'light') {
body.classList.add('theme-light');
} else if (selectedTheme === 'dark') {
body.classList.add('theme-dark');
}
// 'auto' uses CSS media queries (no class needed)
}; };
applyTheme(theme); applyTheme(theme);
@@ -68,23 +59,18 @@ function App() {
localStorage.setItem('theme', theme); localStorage.setItem('theme', theme);
}, [theme]); }, [theme]);
// Check if we're running on localhost // Get headers for API requests
const isRunningOnLocalhost = () => {
const hostname = window.location.hostname;
return hostname === 'localhost' ||
hostname === '127.0.0.1' ||
hostname.startsWith('127.') ||
hostname === '::1';
};
// Get headers for API requests (omit API key for localhost)
const getApiHeaders = () => { const getApiHeaders = () => {
const headers = { const headers = {
'Accept': 'application/json' 'Accept': 'application/json'
}; };
// Only send API key for non-localhost requests // Only send API key for non-localhost requests
if (!isRunningOnLocalhost()) { // For localhost, let server use its default LOCALHOST_API_KEY
if (window.location.hostname !== 'localhost' &&
window.location.hostname !== '127.0.0.1' &&
!window.location.hostname.startsWith('127.') &&
window.location.hostname !== '::1') {
headers['X-API-Key'] = apiKey; headers['X-API-Key'] = apiKey;
} }
@@ -116,7 +102,6 @@ function App() {
} }
} catch (error) { } catch (error) {
// Silently handle state check errors // Silently handle state check errors
console.log('State check failed:', error);
} }
}; };
@@ -132,7 +117,6 @@ function App() {
const data = await response.json(); const data = await response.json();
if (data) { if (data) {
setSampleData(data); setSampleData(data);
console.log('Sample data loaded:', data);
} }
// Update current state GUID // Update current state GUID

View File

@@ -55,8 +55,20 @@ describe('App Component', () => {
test('renders version number', () => { test('renders version number', () => {
render(<App />); render(<App />);
const versionText = screen.getByText(/v1\.1\.7-dev/); const versionText = screen.getByText(/v\d+\.\d+\.\d+(-dev|-test)?/);
expect(versionText).toBeInTheDocument(); expect(versionText).toBeInTheDocument();
// Check if it's a dev/test build
const isDevBuild = versionText.textContent.includes('-dev') || versionText.textContent.includes('-test');
// Additional validations can be added here based on build type
if (isDevBuild) {
// Dev/test specific validations could go here
expect(versionText.textContent).toMatch(/v\d+\.\d+\.\d+-(dev|test)/);
} else {
// Release build validations - just check that version pattern exists in the text
expect(versionText.textContent).toMatch(/v\d+\.\d+\.\d+/);
}
}); });
test('renders all toolbar buttons', () => { test('renders all toolbar buttons', () => {
@@ -84,7 +96,7 @@ describe('App Component', () => {
// Set JSON data directly after clearing // Set JSON data directly after clearing
fireEvent.change(jsonInput, { target: { value: '{"name": "Alice", "age": 30}' } }); fireEvent.change(jsonInput, { target: { value: '{"name": "Alice", "age": 30}' } });
// Enter JMESPath expression after a small delay to ensure JSON is processed // Enter JMESPath expression after a small delay to ensure JSON is processed
await user.clear(jmespathInput); await user.clear(jmespathInput);
await user.type(jmespathInput, 'name'); await user.type(jmespathInput, 'name');
@@ -137,12 +149,12 @@ describe('App Component', () => {
// Should show JSON error indicator - check for error styling or messages // Should show JSON error indicator - check for error styling or messages
await waitFor(() => { await waitFor(() => {
const jsonInputWithError = document.querySelector('.json-input.error') || const jsonInputWithError = document.querySelector('.json-input.error') ||
document.querySelector('.json-input.is-invalid') || document.querySelector('.json-input.is-invalid') ||
screen.queryByText(/Unexpected token/i) || screen.queryByText(/Unexpected token/i) ||
screen.queryByText(/JSON Error:/i) || screen.queryByText(/JSON Error:/i) ||
screen.queryByText(/Invalid JSON:/i) || screen.queryByText(/Invalid JSON:/i) ||
screen.queryByText(/SyntaxError/i); screen.queryByText(/SyntaxError/i);
// If no specific error styling/message, at least ensure the result doesn't contain valid JSON result // If no specific error styling/message, at least ensure the result doesn't contain valid JSON result
if (!jsonInputWithError) { if (!jsonInputWithError) {
const resultArea = screen.getByPlaceholderText(/Results will appear here/i); const resultArea = screen.getByPlaceholderText(/Results will appear here/i);
@@ -259,7 +271,7 @@ describe('App Component', () => {
await waitFor(() => { await waitFor(() => {
expect(fetch).toHaveBeenCalledWith('/api/v1/sample', expect.objectContaining({ expect(fetch).toHaveBeenCalledWith('/api/v1/sample', expect.objectContaining({
headers: expect.objectContaining({ headers: expect.objectContaining({
'X-API-Key': expect.any(String) 'Accept': 'application/json'
}) })
})); }));
}); });

View File

@@ -1,5 +1,4 @@
import React from 'react'; import React from 'react';
import { VERSION } from '../version';
function Header({ theme, onThemeChange, currentPage, onPageChange }) { function Header({ theme, onThemeChange, currentPage, onPageChange }) {
return ( return (