Rich text editor ueditor


Rich text editor ueditor

1. Integrating ueditor with spspring boot

1.1 introduction to ueditor

Ueditor developed by Baidu
Official website…
Official documents…

1.2. Download

Download link from official website…
I use Java back-end, so download JSP version, UTF-8 version
Rich text editor ueditor

Download address of development version…

Post download directory structure
Rich text editor ueditor

There is a DDoS vulnerability in the common-fileupload.jar package. Please upgrade to the latest version as soon as possible. The direct link is Apache fileUpload jar…

1.3. Add ueditor to the local Maven library,

Using eclipse’s import
Right click – > Import – > install or deploy an aitifact to Maven Repository – > enter relevant information

The generated file is very complete

If you don't add it, you need to put the jar package under lib and introduce the following in pom.xml

1.4. Spring boot integrates ueditor

Create a spring boot project. The POM. XML file is as follows

  <!--  Encoding when copying files -- >
  <!-- Valid only when spring boot is inherited -- >
  <!--  Tomcat parsing JSP dependencies -- >

Add dependency ueditor dependency


Put the downloaded folder named ueditor-1.4 under webapps
Write ueditor01.html under ueditor-1.4, as follows

<!DOCTYPE html>

<meta charset="UTF-8">

<!-- Load editor container -- >
<script id="container" name="content" type="text/plain">
  Here is your initialization
<!-- Configuration file -- >
<script type="text/javascript" charset="utf-8"></script>
<!-- Editor source code file -- >
<script type="text/javascript" charset="utf-8"></script>
<script type="text/javascript">
<!-- Instantiation editor -- >
var ue = UE.getEditor('container');


The display is as follows

Be sure to start the back-end of the item, and you need to load the controller. JSP file
Rich text editor ueditor
If the project is not started, an error is reported as follows

Rich text editor ueditor
There are two solutions. If you don’t use front-end and back-end separation, make sure that JSP has controller.jsp and config.json

1.5. Separation of front and rear ends

The purpose of front-end and back-end separation is to remove the dependency of Tomcat embedded Jasper
Write controller


import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;


public class UeditorController {
  public void getConfigInfo(HttpServletRequest request, HttpServletResponse response) {
    String rootPath = request.getSession().getServletContext().getRealPath("/");
    try {
      String exec = new ActionEnter(request, rootPath).exec();
      PrintWriter writer = response.getWriter();
    } catch (IOException e) {

Modify editor.config.js

//Server unified request interface path
, serverUrl: URL +"ueditor/controller" /*"jsp/controller.jsp"*/

Parameters sent


Parameters returned

{state: configuration file initialization failed}

Analysis of source code, String)
public ActionEnter(HttpServletRequest request, String rootPath) {
   this.request = request;
   this.rootPath = rootPath;
   this.actionType = request.getParameter("action");
   this.contextPath = request.getContextPath();
   this.configManager = ConfigManager.getInstance(this.rootPath, this.contextPath, request.getRequestURI());

Rich text editor ueditor
Construction method of configmanager
Rich text editor ueditor
Initenv method
Rich text editor ueditor

Did you find config.json in the same level folder of originalpapt
The value of orginpath is as follows

if (contextPath.length() > 0) {
    this.originalPath = this.rootPath + uri.substring(contextPath.length());
} else {
    this.originalPath = this.rootPath + uri;

So what’s the purpose of rootpath?


The value of URI


The value of contextpath


The solution is to get the static directory as rootpath and put config.json under ueditor-1.4/ueditor in the static directory
The data returned after successful configuration is as follows


1.6. Setting up image upload

I test the picture upload is a problem, such as



{state: "upload data not found"}

Upload source code analysis
Rich text editor ueditor
Rich text editor ueditor

Rich text editor ueditor
Rich text editor ueditor

So does HttpServletRequest have data? There is no problem with data code, but why not?
Reason: there is a conflict between ueditor’s own fileUpload component and spring’s
The solution is to use servlet
Write Servlet


import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

//Invalid test with annotation
//@WebServlet(name = "UEditorServlet", urlPatterns = "/UEditor")
public class UEditorServlet extends HttpServlet {

  public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    doPost(request, response);

  public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    response.setHeader("Content-Type", "text/html");
    PrintWriter out = response.getWriter();
    ServletContext application = this.getServletContext();
    URL systemResource = ClassLoader.getSystemResource("");
    String rootPath = systemResource.getFile();
    //String rootPath = application.getRealPath("/");

    String action = request.getParameter("action");
    String result = new ActionEnter(request, rootPath).exec();
    if (action != null &&
      (action.equals("listfile") || action.equals("listimage"))) {
      rootPath = rootPath.replace("\", "/");
      result = result.replaceAll(rootPath, "/");

  public ServletRegistrationBean servletRegistrationBean() {
    return new ServletRegistrationBean(new UEditorServlet(), "/ueditor-1.4/UEditor");

Config.json path: srcmainresourceeditor-1.4config.json
Test the upload file, upload success, after the success of the path is targetclassesueditorjsploadimage20200615
The access path is
The default access path is…
Modify the upload and save path in config.json
Replace / ueditor / JSP / upload with / litengjava spring boot ueditor / ueditor / JSP / upload, which has 8 places

1.7. Configuration parameters

Pass in custom parameters
The editor has many customizable parameter items, which can be passed into the editor when instantiating
var ue = UE.getEditor(‘container’, {

autoHeight: false

Configuration items can also be modified through ueditor.config.js file. Please refer to the front-end configuration item description for specific configuration method…

initialFrameHeight: window.screen.availHeight-300,

1.8. Setting and reading editor contents

The contents of the editor can be set and read through the getcontent and setcontent methods

//The operation of the editor is best done after the editor is ready
ue.ready(function() {
    //Set the content of the editor
    //Get HTML content, return: < p > hello</p>
    var html = ue.getContent();
    //Get plain text content, return: Hello
    var txt = ue.getContentTxt();

Detailed documentation
Ueditor website:
Ueditor API documentation:
Ueditor GitHub address:…

2. Use ueditor

2.1. Customize tool icons

Customize Toolbar Icon
The button list on the ueditor toolbar can be customized, and the requirements can be realized by modifying the configuration items

Configuration item Modification Description
How to modify configuration items:
1. Method 1: modify the toolbars in ueditor.config.js
2. Method 2: pass in the tools parameter when instantiating the editor
var ue = UE.getEditor(‘container'{toolbars:[]});
Other configuration items: configuration item description
Simple list

toolbars: [
    ['fullscreen', 'source', 'undo', 'redo', 'bold']

Multiline list

toolbars: [
  ['fullscreen', 'source', 'undo', 'redo'],
  ['bold', 'italic', 'underline', 'fontborder', 'strikethrough', 'superscript', 'subscript', 'removeformat', 'formatmatch', 'autotypeset', 'blockquote', 'pasteplain', '|', 'forecolor', 'backcolor', 'insertorderedlist', 'insertunorderedlist', 'selectall', 'cleardoc']

Two line example: custom toolbar
Toolbar button split line
The vertical line ‘|’ is used to represent the dividing line in the configuration item

Complete list of buttons

toolbars: [
        'anchor' // anchor
        'undo' // undo
        'redo '// redo
        'bold', // bold
        'indent' // indent the first line
        'snapscreen ', // screenshot
        'italics' // italics
        'underline', // underline
        'strikethrough '// delete line
        'subscript ', // subscript
        'fontborder', // character border
        'superscript '// superscript
        'formatmatch', // format brush
        'source ', // source code
        'blockquote', // reference
        'pasteplain', // plain text paste mode
        'select all '// select all
        'print', // print
        'Preview', // Preview
        'horizontal', // dividing line
        'removeformat '// clear format
        'time ', // time
        'date ', // date
        'unlink' // unlink
        'insertrow' // insert row before
        'insertcol' // insert column before
        'mergelight ', // right merge cells
        'mergedown '// merge cells below
        'delete row '// delete row
        'deletecol '// delete column
        'splittorows' // split into lines
        'splittocols' // split into columns
        'split to cells' // split cells completely
        'delete caption '// delete table title
        'inserttitle' // insert title
        'mergecells', // merge multiple cells
        'delete table '// delete table
        'cleardoc' // clear document
        'insertparagraph before table' // 'insert row before table'
        'insertcode', // code language
        'fontfamily', // font
        'fontsize', // font size
        'paragraph', // paragraph format
        'simpleupload '// single image upload
        'insertimage', // upload multiple images
        'edittable', // table properties
        'edittd', // cell properties
        'link', // hyperlink
        'emotion' // expression
        'spechars', // special characters
        'searchreplace '// query replace
        'map '// Baidu map
        'GMap', // Google Maps
        'insertvideo' // video
        'help', // help
        'justify left' // align left
        'justify right' // align right
        'justify center' // align Center
        'justify justify' // align both ends
        'forecolor' // font color
        'backcolor' // background color
        'insertorderedlist' // ordered list
        'insert unordered list' // unordered list
        'fullscreen', // full screen
        'directionalityltr '// enter from left to right
        'directionalityrtl '// enter from right to left
        'rowspacingtop' // front margin
        'rowspacingbottom', // after segment
        'pagebreak', // paging
        'insertframe' // insert iframe
        'imagine one', // default
        'imageleft', // floating left
        'imagelight' // right float
        'attachment' // attachment
        'imagecenter' // Center
        'wordimage' // image transfer
        'lineheight', // line spacing
        'edittip', // edit prompt
        'customstyle', // custom title
        'autotypeset', // automatic typesetting
        'webapp' // Baidu app
        'touppercase ', // uppercase
        'tower case ', // lowercase
        'background', // background
        'template ', // template
        'scratch '// doodle
        'music '// music
        'inserttable' // insert table
        'drafts' // load from scratch box
        'charts', // charts

2.2. Front end configuration item description

Setting configuration items on instantiation

var ue = UE.getEditor('container', {
    toolbars: [
        ['fullscreen', 'source', 'undo', 'redo', 'bold']
    autoHeightEnabled: true,
autoFloatEnabled: true

Read configuration item
Read configuration items can be read through the getopt method

var lang = ue.getOpt('lang'); // Default return: zh cn

Front end configuration item description
UEDITOR_ HOME_ URL {path string} [default value: automatically obtained according to the path of the config file] / / add a path for the editor instance, which cannot be commented. The value used by the author http://localhost :8080/ueditor-1.4/

2.3. Catalogue description

Ueditor download package has two types: source package and deployment package
The source code package contains the source code of ueditor, the background code and the use examples

  1. Deployment package directory description

The file directory structure after decompression of the deployment package is as follows
Directory list after ueditor decompression
Dialog: pop up the resources and JS files corresponding to the dialog box
Lang: files displayed in the editor
PHP or JSP or ASP or net: Backstage files related to server side operation
Themes: style pictures and style files
Third party: third party plug-ins (including code highlighting, source code editing, etc.)
Ueditor.all.js: the result of code merging in the development version, and the package file of all files in the directory
Ueditor.all.min.js: the compressed version of ueditor.all.js file, which is recommended for formal deployment
Ueditor.config.js: the configuration file of the editor. It is suggested to be placed in the same directory as the instantiation page of the editor
Ueditor.parse.js: the edited content displays the page reference, and automatically loads forms, lists, code highlights and other styles. See the content display document for details
Ueditor.parse.min.js: the compressed version of ueditor.parse.js file, which is recommended to be used in the formal deployment of content display page

  1. Source package directory description

The file directory structure of the source code package after decompression is as follows
Directory list after ueditor decompression
Some directories and files of the source code package are consistent with the name of the deployment package, and the purpose will be the same, as follows:
_ Doc: partial markdown document
_ Example: use of ueditor
_ Parse: source code of ueditor.parse.js. See the content display document for the usage of parse
_ SRC: ueditor.all.js source code, packing method see grunt packing document
_ Srccore: ueditor core code
_ Srcplugins: plug in files
_ Srcui: UI related files
_ Srcadapter: bridging layer file, connecting ueditor core and UI code
PHP: directory of PHP background files
Phpconfig.json: the back-end configuration file, where all the front-end and back-end configuration items are placed
Phpcontroller.php: receives all the requested interface files, determines the action parameter through it, and distributes specific tasks to other PHP files
phpaction_ Crawler: crash the code of remote file and transfer it to file for use
phpaction_ Upload: upload image, attachment, video processing code
phpaction_ List: list online pictures or attachments
Phpupload.class.php: the class used to upload files
Jsp: directory of JSP background files
Jspconfig.json: the back-end configuration file, where all the front-end and back-end configuration items are placed
Jspcontroller.jsp: interface file to receive all requests
Jsplib: all used jar packages, among which ueditor – *. Jar package is the tool for all background processing logic of ueditor
Jspsrc: Java source code of uedior – * jar file in Lib
ASP: directory of ASP background files
Net: the directory of. Net background file
App_ Code: the file on is the source code of the application.
Bin: inside is the application dependency library. Currently, it depends on the JSON Library of newtonsoft. Bin directory and app_ The code directory is protected by the application program, so there is no need to worry about being accessed by users.
Config.json: it is the configuration file of ueditor back-end, and the more important configuration items have been introduced in the previous section.
Controller.ashx: it is the entry of ueditor request, which distributes different actions to different handlers for processing.
Net.sln: it is the solution file of the project. If you install visual studio 2013 or above, you can open it to carry out the transformation of the project. is the net background use file.
Web.config: is the configuration file for the application
Dialog: same as deployment package description
Lang: same as deployment package description
Themes: same as deployment package description
Third party: same as deployment package description update record of ueditor of each version
Gruntfile.js: the task file executed by grunt, which is used to package the source code package into the deployment version. See the grunt Packaging document for the packaging method
License: open source protocol specification certificate, ueditor uses MIT open source protocol
Ueditor.config.js: front end configuration file
Ueditor.parse.js: the parse file used before merging will be loaded automatically_ File in parse

2.4. Submit form

1. According to the deployment editor tutorial, complete the editor loading
2. Put the container in the form and set the path to submit, such as the < form > tag in the following code
3. Add a name value to the script

  <form action="server.php" method="post">
    <!--  Load editor container -- >
    <script id="container" name="content" type="text/plain">
      Here is your initialization
  <!--  Configuration file -- >
  <script type="text/javascript"></script>
  <!--  Editor source code file -- >
  <script type="text/javascript"></script>
  <!--  Instantiation editor -- >
  <script type="text/javascript">
    var editor = UE.getEditor('container');

2.5. Editing content display

We use ueditor to enable users to edit rich text content in the page, but this should only be a means. Our ultimate goal is to present the content edited by users. That is the display of content. It turns out that we don’t think about this, we only focus on the editing side. However, with the increase and complexity of editor output content, such as chart display, code highlight, custom list label, etc., if they are all processed in the final output editing data, it will inevitably lead to the output data with redundant content, and also to a large extent hard coded display customization effect. Based on these problems, uparse came into being.

1. Find ueditor.parse.js in the download package
2. Load uparse.js according to your path

    <meta http-equiv="Content-Type" content="text/html;charset=utf-8" />

Record uparse. JS to the page, different directory structure, different path
After loading uparse.js, you can call uparse to perform content parsing.

//The syntax of uparse
Cssselector tells uparse that you put the edit data in that container, such as a Div
<div id="content">

Cssselector is “content”. Now it supports three formats, tag, ID and class. In other words, you can render multiple places in the page. Options is a JSON object. Based on version 1.3.5, configurable parameters.

    Rootpath: the path to // ueditor. This should be given so that uparse can find the third party directory
    //Because you need to import those JS files in the directory, of course, they will be loaded on demand according to your editing data
    liiconpath: ' '// customize the address of the list label image, which is the default address
    Listdefaultpaddingleft: '20' // customize the horizontal spacing between list label and text

Generally, just give a rootpath, others can use the default value. Generally, add the following code at the bottom of the page

uParse('.content', {
    rootPath: '../'

This representation parses the content in the container where classname is content.
The complete JS is as follows

<meta charset="UTF-8">
<script type="text/javascript" charset="utf-8"></script>

<div id="content">
    <p>I'm Li Tong</p>
    <p>I am a post-90s programmer</p>
<script type="text/javascript">
uParse('content', {
    rootPaht: './ueditor-1.4'

The display is as follows
Rich text editor ueditor

In the production environment, the content must be obtained from the back end and displayed in the Div

3. Use case of ueditor

3.1. Collect the reasons for users’ dissatisfaction

The interface is as follows

<!DOCTYPE html>
    Author: [email protected]
    Time: February 21, 2019
    Description: collect users' dissatisfaction reasons

<meta charset="UTF-8">
<!-- Editor default profile -- >
<script type="text/javascript" charset="utf-8"></script>
<!-- Editor source code file -- >
<script type="text/javascript" charset="utf-8"></script>
<script type="text/javascript" charset="utf-8"></script>
<!-- Engineering variables -- >
<script type="text/javascript" charset="utf-8"></script>
<!--base64 client-->
<script type="text/javascript" charset="utf-8"></script>
<script type="text/javascript" charset="utf-8"></script>
<!-- Email prompt -- >
<script type="text/javascript" charset="utf-8"></script>
<link rel="stylesheet" href="../layui/css/layui.css" media="all" />
* {
    Font family: "Microsoft YaHei";
    margin: 0;
    padding: 0;

li {
    list-style: none;

.inputElem {
    height: 22px;
    line-height: 22px;
    border: 1px solid #ff4455;

.auto-tip li {
    width: 100%;
    height: 30px;
    line-height: 30px;
    font-size: 16px;
    background: #eee;

.auto-tip li.hoverBg {
    background: #ddd;
    cursor: pointer;

.auto-tip li .em {
    color: #FF0000;

.red {
    color: #000000;

.hidden {
    display: none;

form {
    padding: 15px;
<script type="text/javascript">
window.onload = function() {
    //Initialization prompt plug in
    new EmailAutoComplete({
        Parentcls: 'parentemail' // the parent class of the current input element
        Targetcls: 'email' // target input element

<form class="layui-form" action="reason" method="post">
    <input type="hidden" name="sessionid" />
    <div class="layui-form-item">
        < label class = "layui form label" > email address < / label >
        <div class="layui-input-block">
            <div class="parentemail">
                < input type = "text" name = "email" lay verify = "title" autocomplete = "off" placeholder = "please input email" class = "layui input email" >
    <div class="layui-form-item" id="phone">
        < label class = "layui form label" > mobile number < / label >
        <div class="layui-input-block">
            < input type = "text" name = "phone" lay verify = "title" autocomplete = "off" placeholder = "please input mobile phone number" class = "layui input" >
    <div class="layui-form-item">
        < label class = "layui form label" > user questions < / label >
        <div class="layui-input-block">
            < input type = "text" name = "userquestion" lay verify = "title" autocomplete = "off" placeholder = "please enter the title" class = "layui input" readonly = "readonly" >
    <div class="layui-form-item">
        < label class = "layui form label" > standard questions < / label >
        <div class="layui-input-block">
            < input type = "text" name = "question" lay verify = "title" autocomplete = "off" placeholder = "please enter the title" class = "layui input" readonly = "readonly" >
    <div class="layui-form-item layui-form-text">
        < label class = "layui form label" > answer < / label >
        <div class="layui-input-block">
            < textarea placeholder = "please input content" name = "answer" class = "layui textarea" readonly = "readonly" > < / textarea >
    <div class="layui-form-item layui-form-text">
        < label class = "layui form label" > reasons
        <div class="layui-input-block">
            <script id="container" name="reason" type="text/plain"></script>
    <div class="layui-form-item">
        <div class="layui-input-block">
            Submit now
<script type="text/javascript" charset="utf-8"></script>
<script type="text/javascript">
$(function() {
UE.Editor.prototype.placeholder = function(justPlainText) {
    var _editor = this;
    _editor.addListener("focus", function() {
        var localHtml = _editor.getPlainTxt();
        if($.trim(localHtml) === $.trim(justPlainText)) {
            _editor.setContent(" ");
    _editor.addListener("blur", function() {
        var localHtml = _editor.getContent();
        if(!localHtml) {
    _editor.ready(function() {
var ue = UE.getEditor('container');
UE. Placeholder ("please enter the reason for your dissatisfaction");
var msg = getQueryVariable("msg");
var sessionid = getQueryVariable("sessionid");
if( {
    console.log("sessionid=" + sessionid);
document.getElementsByName("sessionid")[0].value = sessionid;

 *Get HTTP request parameters
 * @param {Object} variable
function getQueryVariable(variable) {
    var query =;
    var vars = query.split("&");
    for(var i = 0; i < vars.length; i++) {
        var pair = vars[i].split("=");
        If (pair [0] = = variable) {// Base64 contains the = = sign after encoding
            var retval = "";
            for(var j = 1; j < pair.length; j++) {
                retval += pair[j];
            retval = decodeURIComponent(retval); // Decoding URL
            return retval;
 *Fill in the questions and answers
 * @param {Object} msg
function fill(msg) {
    if(!msg) {
        return false;
    var array = msg.split(' '); //split char space
    var userQuestionBase64 = array[2];
    var questionBase64 = array[3];
    var answerBase64 = array[4];
    if( {
        console.log("user question:" + userQuestionBase64);
        console.log("question:" + questionBase64);
        console.log("answer:" + answerBase64);

    base64Client.decode(userQuestionBase64, 'GBK', function(text) {
        document.getElementsByName("userQuestion")[0].value = text;

    base64Client.decode(questionBase64, 'GBK', function(text) {
        document.getElementsByName("question")[0].value = text;

    base64Client.decode(answerBase64, 'GBK', function(text) {
        document.getElementsByName("answer")[0].value = text;
$(function() {
    var uri = ajax.getRootName() + "/config/getProjectVariable?";
    ajax.get(uri, function(data) {
        if(data === 'false') {

Recommended Today

High concurrency and multithreading

1、 What is high concurrency High concurrency is a problem encountered in the process of system operation“A large number of operation requests are encountered in a short time”The situation mainly occurs inA large number of requests are received in web system(e.g. ticket snatching of 12306; Tmall double 11. The occurrence of this situation will cause […]