-
Notifications
You must be signed in to change notification settings - Fork 3.4k
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
Render quill delta without instantiating an editor #993
Comments
This is something that I have been wondering about. The guide mentions https://github.com/ottypes/rich-text/ but it does not seem to include any renderer. I have found this project https://github.com/casetext/quill-render but it looks outdated and no longer maintained, and it also involves a DOM. The Quill Delta format is yet-another-custom-rich-text-format, which even if open, would turn problematic to use for persistence of content (in a db, etc.), because well, it is non-standard. Finally while the format is simple, it is non-trivial to render as it is an action log, so the rendering engine needs to be 1:1 with the editing engine (including edge case bugs). Rolling out an engine (or a third party) would thus face all the usual problems of "code rot", because the expected render is not defined by the format, but by what the user saw during edition. |
@EricGrange Deltas are JSON and should save fine in many databases, such as Postgres or MongoDB. Are you encountering issues? |
The problem is not saving JSON itself but saving user content in custom (as If there was a renderer to html available, there would be no such issue: This way user content and db are not strongly tied to quilljs and its At the moment it is my understanding that rendering a delta to html Le 24 sept. 2016 17:03, "Jason Chen" notifications@github.com a écrit :
|
If the scope is the particular JSON Quill produces then we should similarly scope to the particular HTML Quill produces. Through those lenses, HTML has the same issue. If you stored the HTML Quill produced in a database and one day wanted to switch to another editor, that editor will produce different HTML for the same content expressed by Quill through HTML. Now you could do some fuzzy matching with HTML parsers and libraries are out there to do this but this is much more complicated than a JSON array. HTML is undisputedly a more complex and expressive of a format, and, stored a string, requires a parser to even begin interpreting. |
You can convert Quill Delta to HTML on the server with node.js and jsdom without using a real browser. jsdom is a javascript implementation of the DOM. All the issues with HTML that jhchen raised are obviously still valid. var jsdom = require("jsdom");
jsdom.env({
html: '<div id="editor-container"></div>',
scripts: [
'https://cdnjs.cloudflare.com/ajax/libs/webcomponentsjs/0.7.22/MutationObserver.js',
'https://cdn.quilljs.com/1.0.4/quill.js'],
onload: function (window) {
var document = window.document;
// fake getSelection
// https://github.com/tmpvar/jsdom/issues/317
document.getSelection = function() {
return {
getRangeAt: function() {}
};
};
var container = window.document.getElementById("editor-container");
var quill = new window.Quill(container, {});
var delta = {
ops: [
{ insert: 'Gandalf', attributes: { bold: true } },
{ insert: ' the ' },
{ insert: 'Grey', attributes: { color: '#ccc' } }
]
};
quill.setContents(delta);
console.log(document.querySelector(".ql-editor").innerHTML);
}
}); |
The issue with html is actually completely different, because it's I am not sure what you mean with fuzzy matching: the content for me is For example if someone enters content that contains the sentence "the But if the same content is described by deltas, and because of some bug a The same issue exists with alternative rendering engines from delta to When html or text is stored, displaying it may be technically complex if Stored deltas on the other hand need to be fully executed (as it is a Or in other words, the risk that in 5 years rendering current quill deltas All that said, the execution trouble with deltas come from delete & retain Le 24 sept. 2016 19:38, "Jason Chen" notifications@github.com a écrit :
|
@EricGrange Sounds like we disagree on the guarantees and implications of a standard. Less open to opinion is that by design Deltas used to represent documents will only ever have insert operations.
So as you say, most of the concerns are moot. |
@jhchen I think the point me and @EricGrange are getting at is that it seems that the rendering of deltas is coupled to quill itself and wondering what are our options when it comes to displaying the content outside of an editor context (quill or other) |
@yourGuy Deltas are implemented it its own library in which you can use on its own. In the end it is just JSON so if you don't care about the methods Delta implements (which may or may not be useful depending on your use case) you are free to use the data structure in vanilla Javascript, which can be as easy as something like this: html = delta.slice(0, 500).ops.map(function(op) {
if (typeof op.insert !== 'string') return '';
let html = op.insert;
if (op.attributes.bold) {
html = '<strong>' + html + '</strong>';
}
return html;
}).join(''); I assume this issue is more about the particular HTML Quill chooses to generate from Deltas. That by definition has ties to Quill. This is not a detachable piece at the moment, which is why this Issue is still open. |
@jhchen there is one problem with separate lib for converting Delta to HTML - it requires to pass all common and custom formats that already registered in Quill instance due to editing usage. So if we could have method to get HTML from Delta via Quill instance, this will reduce formats registering/passing duplication. Currently i have to use Quill editor readonly instance for proper Delta -> HTML rendering with all registered custom formats. |
I think the renderer, and I hope there is a plan to make one, should include the custom module registration, but again just the rendering part. |
+1 |
The reason why I do not choose to use Quill editor currently is that I got stuck while trying to convert delta to pure HTML for display purpose |
Quill is an amazing piece of tech, really so impressed the further I dive into it. As with other people, though, my main stumbling block for using it is that there are actually no guides or demos showing how to use it where the use-case is to have editors create content and have that content rendered in HTML for reading by consumers. The path from editing to rendering isn't clear. I believe the implicit way of rendering content is creating a Quill editor with no toolbar and There needs to be an option that allows developers to access the rendered HTML rather than the Delta JSON. This would allow developers to save the rendered HTML for later use in addition to saving Deltas for further parsing. Perhaps this is simply an add-on module that needs to be written or already exists? I'm definitely not yet an expert in Quill so perhaps what I'm suggesting already exists. I can see how the rendering of HTML from a Delta document can be subjective and potentially customizable per app, but there's just no word on the normal use case for rendering Quill documents anywhere so it's hard to dive in. |
HTML needs to be sanitized and protected against various things, and you The delta format allows merge & history, and also naturally provides a On Tue, Nov 15, 2016 at 7:05 PM, Jerry Orr notifications@github.com wrote:
|
To build on what @fightingtheboss said, Here is a Codepen of how I'm using Quill to show design-time previews of dynamic run-time HTML: http://codepen.io/benallfree/pen/aBmjjv. Click on the far-right icon to insert another form. Mouse over to alter state and remove elements. I have a content rendering engine with a feature similar to WordPress's shortcode API. At page load, shortcodes such as I use Quill as a visual editor where the user sees a visual preview or sample of what In my case, I save both the deltas and the rendered output back to the database. That means blots need to know how to render themselves.
There's more to it, but that is the essence of a renderable base class. Subclasses must implement the All of this leads me to the conclusion that blots should know how to return rendered versions of themselves. Right now, I am getting by with a subclass that replaces If we do this, I can envision a plugin ecosystem of rich visual design interfaces that know how to render their own output. Imagine an editable video embed that lets the user search YouTube/Vimeo/Vine by keyword and select a suitable video. The uses cases of design-time edit interfaces for blots are incredible (to me). |
Very surprised this hasn't been implemented yet. Don't get me wrong, Quill looks amazing, just surprised this wasn't considered a very basic requirement for 1.0 I appreciate the benefits of the delta formats over storing html inside the db, but without a built-in way to render the content without creating an editor full instance, how do you use the editor in a real scenario? |
@fabiosussetto Save the |
@benallfree this breaks a lot of cool things like updating display format for image/video or all formats markup, cause old HTML will not update. And also requires a lot of sanitizing before displaying plain HTML received from back-end |
@artaommahe I generally agree. I was proposing a solution specifically to @fabiosussetto's desire to display the HTML without loading Quill. I think your suggestion is to render a page from stored Quill deltas instead of the stored HTML, right? That would require a server-side rendering library of some kind. There are a few nodejs-based rendering libs, but anyone outside Node is out of luck as far as I know. I started to write a Delta renderer in PHP, but then I elected to just store the HTML instead. I agree that sanitizing Deltas would be easier than sanitizing HTML. Ultimately, I abandoned Quill on my project because allowing users to have rich editing control is just too fraught with problems. In my case, since my users won't know Markdown or any other safer language, I elected to build a drag-and-drop component designer where the component layout is fixed and the user is only allowed to edit specific data rather than the layout/markup. I still save the HTML back to the server because it is a trusted environment, but if I wanted to be safer I could use Vue.js on the server side to render the content from the data. So I'd still be tied to Node.js for server-side rendering, but I vastly prefer that strategy over rendering Quill deltas. |
yes, this is my current usecase
nope. Server side rendering forced to duplicate formats between front-end quill editor and back-end renderer that is awful. I prefer front-end rendering from Delta before displaying without instantiating full quill editor in readonly mode. |
Is search engine indexing an issue in your use case? |
there is no issues with google search engine, it runs all js and then analyze (we'r using angular). Other search engines does not matter for us. |
Please excuse my ignorance on this topic, but I haven't been able to find an answer for this anywhere else yet. If a malicious user were to put html inside of a delta json (say in a sentence), would the html be displayed on the front-end when read back from the server? In that case, do we have to build a sophisticated sanitizer on the backend to parse the json delta format before saving? Or does quill filter out this stuff automatically? I don't fully understand the implications of something like dangerouslyPasteHTML ... does that mean deltas can contain html, or is there a special node in the delta for this? It would help to know this before using quill for rendering, or converting to html and sanitizing it server (or client) side display. Need more info. |
@rquast Think of it this way: a very malicious user could post something to the server that looks like it came from Quill but was actually hand-crafted for evil purposes :) So regardless of what Quill or any client-side technology does, the server code should never trust what it receives. @EricGrange's comment above about sanitization was (I think) just to mention that sanitizing a Quill delta format is easier than trying to sanitize HTML. I don't have an opinion on that statement, but I think that's what he was trying to say. |
@benallfree if something malicious was sent back from the server, and you used quill to render the delta, then if quill sanitized that on the frontend, then you wouldn't have to worry? It's just that otherwise, you have to sanitize all of strings inside of the delta json on the server side. That's not straight forward.. means you have to hard code the format of the delta json into something that can sanitize it on the server side. Either that or render html (getHTML) before sanitizing on either client or server sides. I don't believe it's necessarily wrong for a database to store XSS code. It's up to the developer to prevent the browser from parsing that code (be it before it goes into the database, or before it gets sent, or before it gets displayed). |
@rquast I think it comes down to preference and use case, but for me, storing malware in my database and trusting a client-side tool to remove it feels too brittle. I don't want garbage in my database in the first place. I think I would go out of my way to avoid an architecture like that. So, my architecture would be as follows:
I mentioned in a comment above - even this architecture seemed too brittle for my use case. Giving the user control over layout and formatting is just disastrous in my experience. There is a reason, for example, that Facebook doesn't allow rich edits on posts and comments. But they do allow emojis and @ tags which produce consistently formatted embellishments. Github uses Markdown in favor of allowing rich editing, I think for the same reason. Quill and rich editors in general have a really narrow set of use cases when long-term user experience is taken into consideration. |
@benallfree starting to think the same. It would be good if JSON Schema was used so you could validate the structure both client and server side as well as check for xss using regex in the schema. Without something like that, you can't trust the integrity. Like you said, rendering the HTML on the server side and running it through a strong sanitizer is also another layer to prevent xss coming through. Fortunately, my use case is for site admins, so they are less likely to muck things up or try any XSS (hopefully). edit like what this guy did (but include xss checks).. https://github.com/dnephin/quill-data-format |
@rquast Yep I agree, if the use case is internal or backend, Quill probably works fine and the security considerations are nil. For public use...a different story! :) |
I wrote a javascript library(available at quillgethtml ) that adds in a function to the quill editor titled |
@boomanaiden154 looks great! Should get it listed here too https://github.com/quilljs/awesome-quill |
Hi there ! Quill is a wonderfull project and it would be amazing if deltas were even more explicit. Indeed, we can save the JSON in our backends but not having a schema has many drawbacks :
It's not about a lack of trust in the Quill codebase (as explained in #1145 ), it's about reducing the cost of the representation of quill deltas in other systems than JS applications so that it feels more open to the developers. I originally posted this comment in the JSON schema ticket but moved it up here for more visibility. |
Solutions already exist, see https://github.com/quilljs/awesome-quill#deltas for a list of other projects in JS, NodeJS, PHP, Python, Go, etc. |
@lode node-quill-converter cannot handle delta of custom inline blot like mark-tag |
Its strange over 3 years and still no clear solution for this which I can totally rely on prod, as I understand there is no perfect solution yet, we still have to use quill instance to render deltas? Correct me if I'm wrongs guys |
I'm also trying to use quill for editing posts and comments, and then the plan would be to :
|
Hey I found this repo and will try it out: |
Current best solution seems to be to convert the deltas to HTML: https://github.com/quilljs/awesome-quill#deltas |
Hey , |
+1 |
1 similar comment
+1 |
@benallfree's comment helped resolve this for me:
Ask yourself if you really need rich text... or if you really just need to show links and line breaks. If so, you can probably get away with a combination of these (and maybe markdown behind the scenes if you really want bold text). |
I need this functionality for example to render blog entry markup without the need for JS. Best is not to second guess what the functionality might be required for as there are probably many use cases for that. |
FWIW GitHub use of markdown pretty much restrict it to quick-n-dirty developer docs or discussions, markdown is not a realistic option for the general public. Since my first comments in 2016, I have switched to using the Chromium Embedded Framework to render the deltas, using a tank to kill a mosquito so to speak, but it provides the most reliable rendering. The processing can happen in queued background tasks server-side and subsequently cached, so there is no performance issue. Yet again, this is heavy computationnally-wise, but the code to perform it is quite simple and you can get pixel-perfect results, both of these were deciding factors. |
@marcin-lulek-cint agreed. I didn't mean to assume, just sharing an option for people like me (to be clear I’m not a maintainer or associated with this project) |
I wrote my own delta renderer; it's not perfect, and its API needs a serious overhaul (very hard to customize) but it has thorough tests and, with effort, you can teach it to handle custom formats: I experimented with using JSDom plus an actual Quill instance for delta->HTML, and although this is good for backend use, I needed something that was synchronous and instantaneous for use in browsers where the Quill editor itself is not available. There is probably a middle ground available, where one uses JSDom plus Quill's |
Save the html output from quill editor. Then render it as an innerHTML on a div. Give class="ql-editor" to the div and the html will be formatted as we see it in the editor. No need to instantiate editor context. Just import quill's css file. Vue example:
|
A bit ridiculous half a decade in and there's no clear solution. Spent over a week trying to figure out what was the best solution for react, and I guess it's still creating a readonly quill and hoping there's no XSS issues? (But maybe there's built in protection? I havent quite understood that.) Some people have mentioned converting deltas to html, but that's really not secure. And on JS frameworks like ReactJS, you really want to avoid using dangerouslySetInnerHTML. (And there's nothing that will convert a delta to JSX) Why is there nothing in the documentation explicitly about rendering a Quill Delta? Seems like a huge oversight. |
Since this is not obvious from reading this whole giant thread - you can use this package https://github.com/nozer/quill-delta-to-html to convert deltas => html without instantiating an editor. I confirmed that in cases where many comments are rendered (25+), the performance of this package is orders of magnitude faster |
I didn't know what a WYSIWYG was few weeks ago, so I noticed what it was when I needed one for my app and after a bit of research, now I come to github to find one, I see this one's the most rated in github? like for real?, who hell is using this? what's delta? |
Part of the problem here is that the Quill docs give the impression of a complete ecosystem with interoperability, but the reality is that there are some major restrictions on what Deltas can be used for re display and rendering if you're not willing to spend time engineering around them in q a painful way. In my web application I use Quill to render editable text, and just grab the text for processing and analysis on the backend in a brute force way. You then mount and unmount the saved text into an iframe instance as necessary, and then send what's needed to Quill for editing if user clicks edit. It's not sophisticated (in fact it's caveman code - I hide my face in shame) but for my use case it works. |
I'm using this on a Django site and just use the html key of the saved value : {
"delta":"{\\"ops\\":[{\\"insert\\":\\"Some content to edit\\\\nEdited 8\\\\n\\"}]}",
"html":"<p>Some content to edit</p><p>Edited 8</p>"
} The problem I found is there are often a lot of ql classes in the rendered output which exist in the editor css. Those selectors all seem to rely on .qs-editor as an ancestor. E.g. center some text, the p element gets a class ql-align-center. The snow.css has the following rule: .ql-editor .ql-align-center {
text-align: center;
} I used a fudge and just wrap the html in a container with that class: <div class="ql-editor">
{{ post.content.html|safe }}
</div> Seems to work for anything I've tested it with, but it's an odd omission to not have any css for use outside of the editor. Makes the rich text a bit useless if it can only render properly in a form editor. |
Yeah well... Spent 2 days trying to figure out how to use Quill properly in Laravel (or any PHP env really), but it's just too painful. |
It makes sense to me at least to store the html, otherwise you have to generate that each page load from the delta. Seems a lot of overhead. Tiptap works off the html directly, there's no delta to mess with, but it's a bit more bare-bones - you need to create your own toolbar buttons for example, and there is no native support for embedding content like images and video (other than youtube), but there are plugins available. |
What do people use to render quill content in a non editor context? Does quill exposes a method for that, or is the a basic rendering library?
I use quill as part of a templating app. I save the different editable blocks in the delta format later I'd like to render that content without instantiating the editor. And preferably with loading a much smaller lib then quill if anybody can recommend one.
Thanx
The text was updated successfully, but these errors were encountered: