From 57371feeb0738ca507f50e7dfebb102bd7f07d93 Mon Sep 17 00:00:00 2001 From: Slawomir Koszewski Date: Sat, 31 Jan 2026 11:06:25 +0100 Subject: [PATCH] Release v1.3.1: Added PowerShell support and fixed theme issues --- bin/Upload-JMESPath.ps1 | 8 ++-- package.json | 4 +- src/App.css | 70 +++++++++++++++++++++++++--- src/App.jsx | 18 +++++++- src/components/ApiKeyPage.jsx | 86 ++++++++++++++++++++++++++++------- src/components/Header.jsx | 22 ++++----- src/index.css | 13 ------ vite.config.js | 4 +- 8 files changed, 168 insertions(+), 57 deletions(-) diff --git a/bin/Upload-JMESPath.ps1 b/bin/Upload-JMESPath.ps1 index 08aa4c0..9403eed 100755 --- a/bin/Upload-JMESPath.ps1 +++ b/bin/Upload-JMESPath.ps1 @@ -1,15 +1,15 @@ #!/usr/bin/env pwsh [CmdletBinding()] param( - [Parameter(Position=0, HelpMessage='API base URL')] + [Parameter(HelpMessage='Path to JSON file; default: read from stdin')] + [string]$JsonFile = '-', + + [Parameter(HelpMessage='API base URL')] [string]$ApiUrl, [Parameter(HelpMessage='API key for authentication')] [string]$ApiKey, - [Parameter(HelpMessage='Path to JSON file; default: read from stdin')] - [string]$JsonFile = '-', - [Parameter(HelpMessage='Show help')] [switch]$Help ) diff --git a/package.json b/package.json index c025fde..3f27430 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "jmespath-playground", - "version": "1.3.0", + "version": "1.3.1", "description": "A React-based web application for testing JMESPath expressions against JSON data", "main": "index.js", "scripts": { @@ -9,7 +9,7 @@ "build": "vite build", "preview": "vite preview", "test": "vitest", - "server": "node server.js", + "server": "node server.js --dev", "dev": "concurrently \"npm start\" \"npm run server\"", "build-image": "node scripts/build-image.js" }, diff --git a/src/App.css b/src/App.css index 45c90c3..cf32dd7 100644 --- a/src/App.css +++ b/src/App.css @@ -5,6 +5,22 @@ --font-mono: 'Monaco', 'Menlo', 'Ubuntu Mono', 'Consolas', monospace; --accent-color: #007bff; + /* Brand colors */ + --brand-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%); + --brand-white: #ffffff; + --brand-dark: #212529; + --brand-warning: #ffc107; + + /* Brand opacity levels */ + --brand-white-60: rgba(255, 255, 255, 0.6); + --brand-white-10: rgba(255, 255, 255, 0.1); + --brand-warning-50: rgba(255, 193, 7, 0.5); + --brand-warning-10: rgba(255, 193, 7, 0.1); + + /* Elevation and overlays */ + --shadow-light: rgba(0, 0, 0, 0.1); + --focus-ring: rgba(0, 123, 255, 0.25); + /* Button variants */ --btn-success: #28a745; --btn-info: #17a2b8; @@ -36,23 +52,57 @@ body { /* Header section styling - more compact */ .header-section { - /* Removed gradient background to fix text visibility */ + background: var(--brand-gradient); + color: var(--brand-white); + padding: 1.2rem 0; + margin-bottom: 1rem; transition: background-color 0.3s ease; } +.header-section h2 { + color: var(--brand-white); +} + +/* Ensure buttons in header are clearly visible against gradient */ +.header-section .btn-light.active { + background-color: var(--brand-white); + color: var(--brand-dark) !important; /* Deep dark text for selected states */ + border-color: var(--brand-white); +} + +.header-section .btn-outline-light { + color: var(--brand-white); + border-color: var(--brand-white-60); +} + +.header-section .btn-outline-light:hover { + background-color: var(--brand-white-10); + color: var(--brand-white); +} + +.header-section .btn-outline-warning { + color: var(--brand-warning); + border-color: var(--brand-warning-50); +} + +.header-section .btn-outline-warning:hover { + background-color: var(--brand-warning-10); + color: var(--brand-warning); +} + /* Custom card styling */ .card { border: none; - box-shadow: 0 2px 8px rgba(0,0,0,0.1); + box-shadow: 0 2px 8px var(--shadow-light); border-radius: 8px; transition: background-color 0.3s ease, box-shadow 0.3s ease; } .card-header { - background-color: #f8f9fa; - border-bottom: 2px solid #dee2e6; + background-color: var(--bg-secondary); + border-bottom: 2px solid var(--border); font-weight: 600; - color: #212529; + color: var(--text-primary); transition: background-color 0.3s ease, border-color 0.3s ease, color 0.3s ease; } @@ -224,7 +274,7 @@ footer a:hover { /* Focus states */ .jmespath-input:focus { border-color: var(--accent-color, #007bff); - box-shadow: 0 0 0 0.2rem rgba(0, 123, 255, 0.25); + box-shadow: 0 0 0 0.2rem var(--focus-ring); } .json-input:focus, @@ -232,7 +282,7 @@ footer a:hover { background-color: var(--bg-primary); border-color: var(--accent-color, #007bff); color: var(--text-secondary); - box-shadow: 0 0 0 0.2rem rgba(0, 123, 255, 0.25); + box-shadow: 0 0 0 0.2rem var(--focus-ring); } /* Placeholder colors */ @@ -249,6 +299,12 @@ footer a:hover { color: var(--error-text); } +.alert-success { + background-color: var(--success-bg); + border-color: var(--success-border); + color: var(--success-text); +} + /* Code block styles */ pre.bg-light { background-color: var(--bg-secondary) !important; diff --git a/src/App.jsx b/src/App.jsx index b2ea6a6..8a4bdff 100644 --- a/src/App.jsx +++ b/src/App.jsx @@ -31,6 +31,10 @@ function App() { // Load theme from localStorage or default to 'auto' return localStorage.getItem("theme") || "auto"; }); + const [shellType, setShellType] = useState(() => { + // Load shell type from localStorage or default to 'bash' + return localStorage.getItem("jmespath-shell-type") || "bash"; + }); const [showReloadButton, setShowReloadButton] = useState(false); const [currentStateGuid, setCurrentStateGuid] = useState(null); const [jmespathExpression, setJmespathExpression] = @@ -81,6 +85,11 @@ function App() { localStorage.setItem("theme", theme); }, [theme]); + // Shell type management + useEffect(() => { + localStorage.setItem("jmespath-shell-type", shellType); + }, [shellType]); + // Get headers for API requests const getApiHeaders = () => { return { @@ -163,7 +172,7 @@ function App() { }; return ( -
+
) : ( - + )}
diff --git a/src/components/ApiKeyPage.jsx b/src/components/ApiKeyPage.jsx index a9d6104..cb39247 100644 --- a/src/components/ApiKeyPage.jsx +++ b/src/components/ApiKeyPage.jsx @@ -1,6 +1,36 @@ import React, { useState } from 'react'; -function ApiKeyPage({ apiKey, onRegenerateApiKey }) { +function CodeBlock({ code }) { + const [copySuccess, setCopySuccess] = useState(false); + + const handleCopy = async () => { + try { + await navigator.clipboard.writeText(code); + setCopySuccess(true); + setTimeout(() => setCopySuccess(false), 2000); + } catch (err) { + console.error('Failed to copy to clipboard:', err); + } + }; + + return ( +
+
+        {code}
+      
+ +
+ ); +} + +function ApiKeyPage({ apiKey, onRegenerateApiKey, shellType, onShellTypeChange }) { const [copySuccess, setCopySuccess] = useState(false); const handleCopyToClipboard = async () => { @@ -60,28 +90,50 @@ function ApiKeyPage({ apiKey, onRegenerateApiKey }) {
-
📡 Remote Data Upload API
+
+
📡 Remote Data Upload API
+
+ onShellTypeChange('bash')} + /> + + onShellTypeChange('powershell')} + /> + +
+

External tools can upload sample data remotely using the REST API. The API key is required for authentication. Define two - environment variables in your .bashrc. + environment variables in your {shellType === 'bash' ? .bashrc : PowerShell profile}.

-
-              export JMESPATH_PLAYGROUND_API_URL={window.location.origin}
export JMESPATH_PLAYGROUND_API_KEY={apiKey}
-
-

Then, use the following curl command to upload your data:

-
-{`curl -s -X POST \\
-    -H "Content-Type: application/json" \\
-    -H "Accept: application/json" \\
-    -H "X-API-Key: $JMESPATH_PLAYGROUND_API_KEY" \\
-    --data @__JSON_FILE_NAME__ \\
-    "$\{JMESPATH_PLAYGROUND_API_URL}/api/v1/upload"`}
-              
+ +

Then, use the following {shellType === 'bash' ? curl : PowerShell} command to upload your data:

+
Replace {"__JSON_FILE_NAME__"} with the path to your - JSON file containing the sample data. or use - to - read from standard input. + JSON file containing the sample data. {shellType === 'bash' && or use - to read from standard input.}
diff --git a/src/components/Header.jsx b/src/components/Header.jsx index f26a9ae..5c4eba4 100644 --- a/src/components/Header.jsx +++ b/src/components/Header.jsx @@ -2,19 +2,19 @@ import React from 'react'; function Header({ theme, onThemeChange, currentPage, onPageChange }) { return ( -
-
-
+
+
+

JMESPath Testing Tool

{/* Right side controls - better positioning */} -
+
{/* API Key Management Button - more prominent */}