addon
This commit is contained in:
@@ -100,27 +100,36 @@ function escapeHtml(text) {
|
||||
|
||||
// Copy text to clipboard
|
||||
async function copyToClipboard(text) {
|
||||
try {
|
||||
await navigator.clipboard.writeText(text);
|
||||
return true;
|
||||
} catch (err) {
|
||||
console.error('Failed to copy:', err);
|
||||
// Fallback for older browsers
|
||||
const textArea = document.createElement('textarea');
|
||||
textArea.value = text;
|
||||
textArea.style.position = 'fixed';
|
||||
textArea.style.left = '-999999px';
|
||||
document.body.appendChild(textArea);
|
||||
textArea.select();
|
||||
// Try modern clipboard API first
|
||||
if (navigator.clipboard && navigator.clipboard.writeText) {
|
||||
try {
|
||||
document.execCommand('copy');
|
||||
document.body.removeChild(textArea);
|
||||
await navigator.clipboard.writeText(text);
|
||||
return true;
|
||||
} catch (err) {
|
||||
document.body.removeChild(textArea);
|
||||
return false;
|
||||
console.error('Clipboard API failed:', err);
|
||||
// Fall through to fallback method
|
||||
}
|
||||
}
|
||||
|
||||
// Fallback for older browsers or non-HTTPS contexts
|
||||
const textArea = document.createElement('textarea');
|
||||
textArea.value = text;
|
||||
textArea.style.position = 'fixed';
|
||||
textArea.style.left = '-999999px';
|
||||
textArea.style.top = '0';
|
||||
document.body.appendChild(textArea);
|
||||
textArea.focus();
|
||||
textArea.select();
|
||||
|
||||
try {
|
||||
const successful = document.execCommand('copy');
|
||||
document.body.removeChild(textArea);
|
||||
return successful;
|
||||
} catch (err) {
|
||||
console.error('Fallback copy failed:', err);
|
||||
document.body.removeChild(textArea);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// Show toast notification
|
||||
@@ -432,6 +441,75 @@ function renderMarkdown(text) {
|
||||
return `<div class="markdown-block">${html}</div>`;
|
||||
}
|
||||
|
||||
// Additional utility functions for peripherals module
|
||||
function formatDateTime(dateString) {
|
||||
if (!dateString) return 'N/A';
|
||||
const date = new Date(dateString);
|
||||
return date.toLocaleString('fr-FR', {
|
||||
year: 'numeric',
|
||||
month: 'long',
|
||||
day: 'numeric',
|
||||
hour: '2-digit',
|
||||
minute: '2-digit'
|
||||
});
|
||||
}
|
||||
|
||||
function formatBytes(bytes) {
|
||||
return formatFileSize(bytes);
|
||||
}
|
||||
|
||||
function showSuccess(message) {
|
||||
showToast(message, 'success');
|
||||
}
|
||||
|
||||
function showInfo(message) {
|
||||
showToast(message, 'info');
|
||||
}
|
||||
|
||||
// API request helper
|
||||
async function apiRequest(endpoint, options = {}) {
|
||||
const config = window.CONFIG || { API_BASE_URL: 'http://localhost:8007/api' };
|
||||
const url = `${config.API_BASE_URL}${endpoint}`;
|
||||
|
||||
const defaultOptions = {
|
||||
headers: {}
|
||||
};
|
||||
|
||||
// Don't set Content-Type for FormData (browser will set it with boundary)
|
||||
if (options.body && !(options.body instanceof FormData)) {
|
||||
defaultOptions.headers['Content-Type'] = 'application/json';
|
||||
}
|
||||
|
||||
const response = await fetch(url, {
|
||||
...defaultOptions,
|
||||
...options,
|
||||
headers: {
|
||||
...defaultOptions.headers,
|
||||
...options.headers
|
||||
}
|
||||
});
|
||||
|
||||
if (!response.ok) {
|
||||
let message = `HTTP ${response.status}: ${response.statusText}`;
|
||||
try {
|
||||
const data = await response.json();
|
||||
if (data && typeof data === 'object') {
|
||||
message = data.detail || data.message || message;
|
||||
}
|
||||
} catch (error) {
|
||||
// Ignore JSON parse errors and keep default message.
|
||||
}
|
||||
throw new Error(message);
|
||||
}
|
||||
|
||||
// Handle 204 No Content
|
||||
if (response.status === 204) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return response.json();
|
||||
}
|
||||
|
||||
window.BenchUtils = {
|
||||
formatDate,
|
||||
formatRelativeTime,
|
||||
@@ -461,5 +539,10 @@ window.BenchUtils = {
|
||||
formatStorage,
|
||||
formatCache,
|
||||
formatTemperature,
|
||||
renderMarkdown
|
||||
renderMarkdown,
|
||||
formatDateTime,
|
||||
formatBytes,
|
||||
showSuccess,
|
||||
showInfo,
|
||||
apiRequest
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user