mirror of
https://github.com/laurent22/joplin.git
synced 2025-01-11 18:24:43 +02:00
Desktop: Fixes #8305: Ensure that notes that contain invalid links can still be exported as HTML or PDF
This commit is contained in:
parent
329f5a0dda
commit
fb9974c76f
@ -33,8 +33,15 @@ const htmlentities = (s: string): string => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const dataUriEncode = (filePath: string): string => {
|
const dataUriEncode = (filePath: string): string => {
|
||||||
const result = Datauri(filePath);
|
try {
|
||||||
return result.content;
|
const result = Datauri(filePath);
|
||||||
|
return result.content;
|
||||||
|
} catch (error) {
|
||||||
|
// If the file path is invalid, the Datauri will throw an exception.
|
||||||
|
// Instead, since we can just ignore that particular file.
|
||||||
|
// Fixes https://github.com/laurent22/joplin/issues/8305
|
||||||
|
return '';
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
const attributesHtml = (attr: any) => {
|
const attributesHtml = (attr: any) => {
|
||||||
|
@ -7,6 +7,7 @@ import * as fs from 'fs-extra';
|
|||||||
import { tempFilePath } from '../../testing/test-utils';
|
import { tempFilePath } from '../../testing/test-utils';
|
||||||
import { ContentScriptType } from '../../services/plugins/api/types';
|
import { ContentScriptType } from '../../services/plugins/api/types';
|
||||||
import { FileSystemItem } from './types';
|
import { FileSystemItem } from './types';
|
||||||
|
import { readFile } from 'fs/promises';
|
||||||
|
|
||||||
async function recreateExportDir() {
|
async function recreateExportDir() {
|
||||||
const dir = exportDir();
|
const dir = exportDir();
|
||||||
@ -120,4 +121,22 @@ describe('interop/InteropService_Exporter_Html', () => {
|
|||||||
expect(readFenceContent).toBe(fenceContent);
|
expect(readFenceContent).toBe(fenceContent);
|
||||||
}));
|
}));
|
||||||
|
|
||||||
|
test('should not throw an error on invalid resource paths', (async () => {
|
||||||
|
const service = InteropService.instance();
|
||||||
|
const folder1 = await Folder.save({ title: 'folder1' });
|
||||||
|
await Note.save({ title: 'note1', parent_id: folder1.id, body: '[a link starts with slash](/)' });
|
||||||
|
|
||||||
|
const filePath = `${exportDir()}/test.html`;
|
||||||
|
|
||||||
|
await service.export({
|
||||||
|
path: filePath,
|
||||||
|
format: 'html',
|
||||||
|
packIntoSingleFile: true,
|
||||||
|
target: FileSystemItem.File,
|
||||||
|
});
|
||||||
|
|
||||||
|
const content = await readFile(filePath, 'utf-8');
|
||||||
|
expect(content).toContain('<a data-from-md="" title="/" href="" download="">a link starts with slash</a>');
|
||||||
|
}));
|
||||||
|
|
||||||
});
|
});
|
||||||
|
@ -6,7 +6,7 @@ import Folder from '../../models/Folder';
|
|||||||
import Note from '../../models/Note';
|
import Note from '../../models/Note';
|
||||||
import Setting from '../../models/Setting';
|
import Setting from '../../models/Setting';
|
||||||
import { MarkupToHtml } from '@joplin/renderer';
|
import { MarkupToHtml } from '@joplin/renderer';
|
||||||
import { ResourceEntity } from '../database/types';
|
import { NoteEntity, ResourceEntity } from '../database/types';
|
||||||
import { contentScriptsToRendererRules } from '../plugins/utils/loadContentScripts';
|
import { contentScriptsToRendererRules } from '../plugins/utils/loadContentScripts';
|
||||||
import { basename, friendlySafeFilename, rtrimSlashes, dirname } from '../../path-utils';
|
import { basename, friendlySafeFilename, rtrimSlashes, dirname } from '../../path-utils';
|
||||||
import htmlpack from '@joplin/htmlpack';
|
import htmlpack from '@joplin/htmlpack';
|
||||||
@ -48,7 +48,7 @@ export default class InteropService_Exporter_Html extends InteropService_Exporte
|
|||||||
this.style_ = themeStyle(Setting.THEME_LIGHT);
|
this.style_ = themeStyle(Setting.THEME_LIGHT);
|
||||||
}
|
}
|
||||||
|
|
||||||
private async makeDirPath_(item: any, pathPart: string = null) {
|
private async makeDirPath_(item: NoteEntity, pathPart: string = null) {
|
||||||
let output = '';
|
let output = '';
|
||||||
while (true) {
|
while (true) {
|
||||||
if (item.type_ === BaseModel.TYPE_FOLDER) {
|
if (item.type_ === BaseModel.TYPE_FOLDER) {
|
||||||
@ -64,7 +64,7 @@ export default class InteropService_Exporter_Html extends InteropService_Exporte
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private async processNoteResources_(item: any) {
|
private async processNoteResources_(item: NoteEntity) {
|
||||||
const target = this.metadata().target;
|
const target = this.metadata().target;
|
||||||
const linkedResourceIds = await Note.linkedResourceIds(item.body);
|
const linkedResourceIds = await Note.linkedResourceIds(item.body);
|
||||||
const relativePath = target === 'directory' ? rtrimSlashes(await this.makeDirPath_(item, '..')) : '';
|
const relativePath = target === 'directory' ? rtrimSlashes(await this.makeDirPath_(item, '..')) : '';
|
||||||
|
Loading…
Reference in New Issue
Block a user