136 lines
4.4 KiB
JavaScript
136 lines
4.4 KiB
JavaScript
(() => {
|
|
const API_BASE = '/api/gui/files';
|
|
const params = new URLSearchParams(window.location.search);
|
|
const path = params.get('path');
|
|
|
|
const editorArea = document.getElementById('editorArea');
|
|
const filePathEl = document.getElementById('filePath');
|
|
const statusInfo = document.getElementById('statusInfo');
|
|
const saveBtn = document.getElementById('btnSave');
|
|
const downloadBtn = document.getElementById('btnDownload');
|
|
const backBtn = document.getElementById('btnBack');
|
|
const fontIncreaseBtn = document.getElementById('btnIncreaseFont');
|
|
const fontDecreaseBtn = document.getElementById('btnDecreaseFont');
|
|
|
|
let originalContent = '';
|
|
let dirty = false;
|
|
let fontSize = 14;
|
|
|
|
if (!path) {
|
|
editorArea.value = '缺少 path 参数,无法加载文件。';
|
|
editorArea.disabled = true;
|
|
saveBtn.disabled = true;
|
|
downloadBtn.disabled = true;
|
|
statusInfo.textContent = '缺少路径';
|
|
return;
|
|
}
|
|
|
|
filePathEl.textContent = path;
|
|
|
|
function setDirty(value) {
|
|
dirty = value;
|
|
statusInfo.textContent = dirty ? '有未保存的更改' : '已保存';
|
|
saveBtn.disabled = !dirty;
|
|
}
|
|
|
|
async function request(url, options = {}) {
|
|
const response = await fetch(url, options);
|
|
const data = await response.json().catch(() => ({}));
|
|
if (!response.ok || data.success === false) {
|
|
const message = data.error || data.message || `请求失败 (${response.status})`;
|
|
throw new Error(message);
|
|
}
|
|
return data;
|
|
}
|
|
|
|
async function loadFile() {
|
|
statusInfo.textContent = '加载中...';
|
|
try {
|
|
const result = await request(`${API_BASE}/text?path=${encodeURIComponent(path)}`);
|
|
originalContent = result.content || '';
|
|
editorArea.value = originalContent;
|
|
setDirty(false);
|
|
statusInfo.textContent = `最后修改时间:${result.modified_at}`;
|
|
} catch (err) {
|
|
editorArea.value = `文件加载失败:${err.message}`;
|
|
editorArea.disabled = true;
|
|
saveBtn.disabled = true;
|
|
statusInfo.textContent = '无法加载文件';
|
|
}
|
|
}
|
|
|
|
async function saveFile() {
|
|
statusInfo.textContent = '保存中...';
|
|
try {
|
|
await request(`${API_BASE}/text`, {
|
|
method: 'POST',
|
|
headers: { 'Content-Type': 'application/json' },
|
|
body: JSON.stringify({ path, content: editorArea.value }),
|
|
});
|
|
originalContent = editorArea.value;
|
|
setDirty(false);
|
|
statusInfo.textContent = '已保存';
|
|
} catch (err) {
|
|
statusInfo.textContent = `保存失败:${err.message}`;
|
|
}
|
|
}
|
|
|
|
editorArea.addEventListener('input', () => {
|
|
if (editorArea.disabled) return;
|
|
setDirty(editorArea.value !== originalContent);
|
|
});
|
|
|
|
saveBtn.addEventListener('click', () => {
|
|
if (!dirty) return;
|
|
saveFile();
|
|
});
|
|
|
|
downloadBtn.addEventListener('click', () => {
|
|
window.open(`${API_BASE}/download?path=${encodeURIComponent(path)}`, '_blank');
|
|
});
|
|
|
|
const getParentDirectory = () => {
|
|
const segments = path.split('/').filter(Boolean);
|
|
if (segments.length <= 1) {
|
|
return '';
|
|
}
|
|
segments.pop();
|
|
return segments.join('/');
|
|
};
|
|
|
|
const navigateToManager = () => {
|
|
const parentDir = getParentDirectory();
|
|
const target = parentDir ? `/file-manager?path=${encodeURIComponent(parentDir)}` : '/file-manager';
|
|
window.location.href = target;
|
|
};
|
|
|
|
backBtn.addEventListener('click', () => {
|
|
if (dirty) {
|
|
const confirmLeave = window.confirm('有未保存的更改,确认要离开吗?');
|
|
if (!confirmLeave) return;
|
|
}
|
|
navigateToManager();
|
|
});
|
|
|
|
fontIncreaseBtn.addEventListener('click', () => {
|
|
fontSize = Math.min(fontSize + 1, 28);
|
|
editorArea.style.fontSize = `${fontSize}px`;
|
|
});
|
|
|
|
fontDecreaseBtn.addEventListener('click', () => {
|
|
fontSize = Math.max(fontSize - 1, 10);
|
|
editorArea.style.fontSize = `${fontSize}px`;
|
|
});
|
|
|
|
window.addEventListener('beforeunload', (event) => {
|
|
if (!dirty) return;
|
|
event.preventDefault();
|
|
event.returnValue = '';
|
|
});
|
|
|
|
loadFile().catch((err) => {
|
|
console.error(err);
|
|
statusInfo.textContent = err.message;
|
|
});
|
|
})();
|