-
-
Notifications
You must be signed in to change notification settings - Fork 3.7k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Code Block displays HTML entities #5901
Comments
Hi! Great to hear that you like this feature :) I'm not sure if we can consider it as a bug - it's a code block, so you want to display the code without executing it and HTML entities might be a part of the code. However, the current inconsistent behaviour between |
Imagine I'm writing a blog post about programming so it has both text and code blocks. I save a draft to the database (so call .getData()) and another day I want to continue editing the draft (so it's loaded from DB and set with .setData()), but it's not what I saw/edited yesterday with those mangled entities. Unless I'm missing something I can't fix this behavior in the host code in any reasonable way which makes me think this inconsistency is not just confusing, but a bug. |
Doh, try this:
And then:
And the second snippet will change the actual editor data (the thing that you can see in the editor). So this is definitely a bug. |
I would like to note that the impact of this bug is quite large for some use cases - some programming languages (e.g. Java, JavaScript, C++, PHP) use ampersand quite heavily and this bug makes it impossible to use code blocks for these ... |
Just to second @zadam, as I've mentioned in my report @ zadam/trilium#917, each save increases the text over time. So right now, in a particular bash snippet that started out containing |
Have you a change to gives us an approximate date when this issue will be fixed? |
Here is a partial fix: neongreen/ckeditor5-code-block@53d0541 Can be applied to |
Hm... cc @oleq, do you remember why you went this way? Was there a problem with the view structure or you just went for what was easier to code? |
It's been a while so it's hard to tell. It's probably related to the data processor we went with around here ckeditor5/packages/ckeditor5-code-block/src/converters.js Lines 186 to 188 in ec1de8c
It looks like |
I think we could remove the entire stringification part and then we wouldn't need the DP at all. |
Some notes from my talk with @oleq:
So, the quick fix is as proposed before – to de-encode The real solution is to not use the data processor here, but instead iterate over the view |
I checked and this should work: diff --git a/packages/ckeditor5-code-block/src/codeblockediting.js b/packages/ckeditor5-code-block/src/codeblockediting.js
index e819e08933..7e769d8824 100644
--- a/packages/ckeditor5-code-block/src/codeblockediting.js
+++ b/packages/ckeditor5-code-block/src/codeblockediting.js
@@ -128,7 +128,7 @@ export default class CodeBlockEditing extends Plugin {
editor.editing.downcastDispatcher.on( 'insert:codeBlock', modelToViewCodeBlockInsertion( model, normalizedLanguagesDefs, true ) );
editor.data.downcastDispatcher.on( 'insert:codeBlock', modelToViewCodeBlockInsertion( model, normalizedLanguagesDefs ) );
editor.data.downcastDispatcher.on( 'insert:softBreak', modelToDataViewSoftBreakInsertion( model ), { priority: 'high' } );
- editor.data.upcastDispatcher.on( 'element:pre', dataViewToModelCodeBlockInsertion( editor.data, normalizedLanguagesDefs ) );
+ editor.data.upcastDispatcher.on( 'element:pre', dataViewToModelCodeBlockInsertion( editor.data, editor.editing.view, normalizedLanguagesDefs ) );
// Intercept the clipboard input (paste) when the selection is anchored in the code block and force the clipboard
// data to be pasted as a single plain text. Otherwise, the code lines will split the code block and
diff --git a/packages/ckeditor5-code-block/src/converters.js b/packages/ckeditor5-code-block/src/converters.js
index 7ee4a6324f..2fdd5b7845 100644
--- a/packages/ckeditor5-code-block/src/converters.js
+++ b/packages/ckeditor5-code-block/src/converters.js
@@ -131,7 +131,7 @@ export function modelToDataViewSoftBreakInsertion( model ) {
* configuration passed to the feature.
* @returns {Function} Returns a conversion callback.
*/
-export function dataViewToModelCodeBlockInsertion( dataController, languageDefs ) {
+export function dataViewToModelCodeBlockInsertion( dataController, editingView, languageDefs ) {
// Language names associated with CSS classes:
//
// {
@@ -183,8 +183,11 @@ export function dataViewToModelCodeBlockInsertion( dataController, languageDefs
writer.setAttribute( 'language', defaultLanguageName, codeBlock );
}
- const stringifiedElement = dataController.processor.toData( viewChild );
- const textData = extractDataFromCodeElement( stringifiedElement );
+ const textData = [ ...editingView.createRangeIn( viewChild ) ]
+ .filter( current => current.type === 'text' )
+ .map( ( { item } ) => item.data )
+ .join( '' );
+
const fragment = rawSnippetTextToModelDocumentFragment( writer, textData );
writer.append( fragment, codeBlock );
@@ -234,14 +237,3 @@ export function dataViewToModelCodeBlockInsertion( dataController, languageDefs
}
};
}
-
-// Returns content of `<pre></pre>` with unescaped html inside.
-//
-// @param {String} stringifiedElement
-function extractDataFromCodeElement( stringifiedElement ) {
- const data = new RegExp( /^<code[^>]*>([\S\s]*)<\/code>$/ ).exec( stringifiedElement )[ 1 ];
-
- return data
- .replace( /</g, '<' )
- .replace( />/g, '>' );
-} The change causes two failing tests, though. But I think that they were wrong in the first place and that's the reason why they fail. If anyone loads
|
FYI, I'm about to create a PR with changes proposed by @oleq with additional tests and docs. |
…ocessor, as suggested by @oleq at #5901 (comment). Ignore HTML elements inside `<pre><code>`. Closes: #5901.
PR that fixes OP is drafted at #7240. |
Fix (code-block): Stop rendering ` ` when restoring the state of an empty code block. Closes #5901.
Closing as done, with smaller followup issue #7259 |
Let me first thank you for the highly anticipated code block feature! Apart from this issue it seems to work great and covers all basics already.
📝 Provide detailed reproduction steps (if any)
Create empty code block:
Call
textEditor.getData()
and get<pre><code class="language-text-plain"> </code></pre><p>text</p>
Create new instance of CKEditor and call
textEditor.getData('<pre><code class="language-text-plain"> </code></pre><p>text</p>')
- i.e. with what.getData()
previously returned.✔️ Expected result
❌ Actual result
📃 Other details
Similar problem happens when code block contains "&", after which is returned from
.getData()
as&
but then displayed literally from.setData()
.If you'd like to see this fixed sooner, add a 👍 reaction to this post.
The text was updated successfully, but these errors were encountered: