fix: open local uploaded resources

This commit is contained in:
lix-2026
2026-05-20 12:58:29 +08:00
parent cfc91320be
commit 322c7ffdce
4 changed files with 429 additions and 3 deletions
+39 -2
View File
@@ -2137,7 +2137,7 @@ const SIDEBAR_TREE_JS: &str = r##"
function localFilePathFromAssetId(assetId) {
var value = String(assetId || '').trim();
return value.indexOf('local-file:') === 0 ? value.slice('local-file:'.length) : '';
return value.indexOf('local-file:') === 0 ? value.slice('local-file:'.length) : value.indexOf('local:asset:') === 0 ? value.slice('local:asset:'.length) : '';
}
function buildLocalFileOpenUrl(relativePath, download) {
@@ -2350,6 +2350,16 @@ const SIDEBAR_TREE_JS: &str = r##"
return String(asset && (asset.asset_type || asset.assetType || asset.mime_type || '') || '').trim();
}
function fileTreeIconKindForFileName(fileName) {
var name = String(fileName || '').trim().toLowerCase();
var ext = name.indexOf('.') >= 0 ? name.split('.').pop() : '';
if (['doc', 'docx', 'odt', 'rtf', 'ppt', 'pptx', 'odp', 'xls', 'xlsx', 'ods', 'csv'].indexOf(ext) >= 0) return 'office';
if (ext === 'md' || ext === 'markdown') return 'markdown';
if (ext === 'pdf') return 'pdf';
if (['png', 'jpg', 'jpeg', 'gif', 'webp', 'svg', 'bmp'].indexOf(ext) >= 0) return 'image';
return '';
}
function isLocalUploadedAsset(asset) {
var id = String(asset && asset.id || '').trim();
return String(asset && asset.sourceKind || '').trim() === 'local_folder' || id.indexOf('local:asset:') === 0;
@@ -2688,7 +2698,7 @@ const SIDEBAR_TREE_JS: &str = r##"
};
li.setAttribute('data-node-id', 'asset:' + assetId);
var title = uploadedAssetTitle(asset);
var iconKind = uploadedAssetType(asset) || 'file';
var iconKind = fileTreeIconKindForFileName(title) || uploadedAssetType(asset) || 'file';
if (objectKind === 'mindmap') iconKind = 'mindmap';
li.innerHTML =
'<div class="tree-row" role="treeitem" aria-level="' + (parentRow ? '2' : '1') + '" aria-expanded="false" data-rust-rendered-row="filetree" data-testid="filetree-asset-row" data-row-id="' + escapeHtml('asset:' + assetId) + '" data-row-kind="asset" data-node-id="' + escapeHtml('asset:' + assetId) + '" data-document-id="' + escapeHtml(targetDocumentId) + '" data-doc-id="' + escapeHtml(targetDocumentId) + '" data-asset-id="' + escapeHtml(assetId) + '" data-object-identity="' + escapeHtml(objectIdentityAttr(objectIdentity)) + '" data-object-kind="' + escapeHtml(objectKind || 'attachment') + '" data-shell-mode="filetree" data-selected="false" data-active="false" draggable="true">' +
@@ -7221,6 +7231,19 @@ const SIDEBAR_TREE_JS: &str = r##"
async function resolveEditorAttachmentUrl(detail) {
var assetId = String(detail && detail.assetId || '').trim();
var localFilePath = localFilePathFromAssetId(assetId);
if (localFilePath) {
var localUrl = buildLocalFileOpenUrl(localFilePath, false);
if (localUrl) {
return {
url: localUrl,
asset: {
file_name: String(detail && detail.fileName || '').trim(),
fileSize: String(detail && detail.fileSize || '').trim()
}
};
}
}
if (assetId) {
var response = await fetch('/api/media/sign?assetId=' + encodeURIComponent(assetId), {
method: 'GET',
@@ -7303,6 +7326,14 @@ const SIDEBAR_TREE_JS: &str = r##"
async function openEditorAttachmentDownload(detail) {
if (!detail) return;
var localFilePath = localFilePathFromAssetId(detail.assetId);
if (localFilePath) {
var localDownloadUrl = buildLocalFileOpenUrl(localFilePath, true);
if (localDownloadUrl) {
window.open(localDownloadUrl, '_blank', 'noopener,noreferrer');
return;
}
}
if (detail.assetId) {
try {
var response = await fetch('/api/media/sign?assetId=' + encodeURIComponent(detail.assetId), {
@@ -8740,6 +8771,8 @@ mod tests {
assert!(SIDEBAR_TREE_JS.contains("function localFilePathFromAssetId"));
assert!(SIDEBAR_TREE_JS.contains("/api/local-folder/files/open"));
assert!(SIDEBAR_TREE_JS.contains("local-file:"));
assert!(SIDEBAR_TREE_JS
.contains("value.indexOf('local:asset:') === 0 ? value.slice('local:asset:'.length)"));
assert!(SIDEBAR_TREE_JS.contains("fetchCurrentOnlyOfficeUserId"));
assert!(SIDEBAR_TREE_JS.contains("/api/auth/whoami"));
assert!(SIDEBAR_TREE_JS.contains("buildOnlyOfficeOpenUrl"));
@@ -8908,6 +8941,7 @@ mod tests {
assert!(SIDEBAR_TREE_JS.contains("isLocalUploadedAsset(asset)"));
assert!(SIDEBAR_TREE_JS.contains("buildLocalOnlyOfficeOpenUrl"));
assert!(SIDEBAR_TREE_JS.contains("localOfficeUrl"));
assert!(SIDEBAR_TREE_JS.contains("fileTreeIconKindForFileName(title)"));
assert!(SIDEBAR_TREE_JS.contains("refreshLocalFolderSidebarSnapshot"));
assert!(SIDEBAR_TREE_JS.contains("wolai:local-assets-changed"));
}
@@ -9051,6 +9085,9 @@ mod tests {
assert!(SIDEBAR_TREE_JS.contains("function openPdfEditorAttachment"));
assert!(SIDEBAR_TREE_JS.contains("function openCodeEditorAttachment"));
assert!(SIDEBAR_TREE_JS.contains("function resolveEditorAttachmentUrl"));
assert!(SIDEBAR_TREE_JS.contains("var localFilePath = localFilePathFromAssetId(assetId)"));
assert!(SIDEBAR_TREE_JS
.contains("var localDownloadUrl = buildLocalFileOpenUrl(localFilePath, true)"));
assert!(SIDEBAR_TREE_JS.contains("type: 'codeBlock'"));
assert!(SIDEBAR_TREE_JS.contains("attrs: { language: language }"));
assert!(SIDEBAR_TREE_JS.contains("inferCodeAttachmentLanguage"));
+41
View File
@@ -1819,6 +1819,34 @@ body {
text-decoration: none !important;
}
.document-shell .editor-surface .ProseMirror a.mnote-uploaded-attachment-row::before {
content: "" !important;
display: inline-block !important;
width: 18px !important;
height: 18px !important;
flex: 0 0 18px !important;
border-radius: 4px !important;
background: #6b7280;
box-shadow: inset 0 0 0 1px rgba(15, 23, 42, 0.12) !important;
}
.document-shell .editor-surface .ProseMirror a.mnote-uploaded-attachment-word::before {
background: #4f7df3;
}
.document-shell .editor-surface .ProseMirror a.mnote-uploaded-attachment-ppt::before,
.document-shell .editor-surface .ProseMirror a.mnote-uploaded-attachment-pdf::before {
background: #d94841;
}
.document-shell .editor-surface .ProseMirror a.mnote-uploaded-attachment-sheet::before {
background: #2f9e44;
}
.document-shell .editor-surface .ProseMirror a.mnote-uploaded-attachment-code::before {
background: #111111;
}
.document-shell .editor-surface .ProseMirror a.mnote-uploaded-attachment-row::after {
content: "" !important;
display: none !important;
@@ -4044,6 +4072,19 @@ mod tests {
assert!(MNOTE_CSS.contains("#mnote-mindmap-island"));
}
#[test]
fn uploaded_attachment_rows_use_colored_file_badges() {
assert!(MNOTE_CSS.contains("a.mnote-uploaded-attachment-row::before"));
assert!(MNOTE_CSS.contains("a.mnote-uploaded-attachment-word::before"));
assert!(MNOTE_CSS.contains("background: #4f7df3"));
assert!(MNOTE_CSS.contains("a.mnote-uploaded-attachment-ppt::before"));
assert!(MNOTE_CSS.contains("background: #d94841"));
assert!(MNOTE_CSS.contains("a.mnote-uploaded-attachment-sheet::before"));
assert!(MNOTE_CSS.contains("background: #2f9e44"));
assert!(MNOTE_CSS.contains("a.mnote-uploaded-attachment-code::before"));
assert!(MNOTE_CSS.contains("background: #111111"));
}
#[test]
fn mnote_css_contains_responsive_breakpoints() {
assert!(MNOTE_CSS.contains("@media (max-width: 768px)"));