KindEditor

1、进入官网

  KindEditor是一种在线HTML编辑器插件,能实现的效果就是我们平时发表文章以及评论的时候可以对文本进行样式的编辑,以及上传图片、插入代码等。类似的编辑器插件还有:TinyEditor、UEEditor、CkEditor等。

2、下载

  • 官网下载:http://kindeditor.net/down.php

3、文件夹说明

├── asp                          asp示例
├── asp.net                    asp.net示例
├── attached                  空文件夹,放置关联文件attached
├── examples                 HTML示例
├── jsp                          java示例
├── kindeditor-all-min.js 全部JS(压缩)
├── kindeditor-all.js        全部JS(未压缩)
├── kindeditor-min.js      仅KindEditor JS(压缩)
├── kindeditor.js            仅KindEditor JS(未压缩)
├── lang                        支持语言
├── license.txt               License
├── php                        PHP示例
├── plugins                    KindEditor内部使用的插件
└── themes                   KindEditor主题

4、基本使用

<textarea name="content" id="content"></textarea>
 
<script src="/static/jquery-1.12.4.js"></script>
<script src="/static/plugins/kind-editor/kindeditor-all.js"></script>
<script>
    $(function () {
        initKindEditor();
    });
 
    function initKindEditor() {
        var kind = KindEditor.create('#content', {
             '100%',       // 文本框宽度(可以百分比或像素)
            height: '300px',     // 文本框高度(只能像素)
            minWidth: 200,       // 最小宽度(数字)
            minHeight: 400      // 最小高度(数字)
        });
    }
</script>

5、详细参数

     http://kindeditor.net/docs/option.html

6、上传文件示例

 1 <!DOCTYPE html>
 2 <html>
 3 <head lang="en">
 4     <meta charset="UTF-8">
 5     <title></title>
 6 </head>
 7 <body>
 8 
 9 <div>
10     <h1>文章内容</h1>
11     {{ request.POST.content|safe }}
12 </div>
13 
14 
15 <form method="POST">
16     <h1>请输入内容:</h1>
17     {% csrf_token %}
18     <div style=" 500px; margin: 0 auto;">
19         <textarea name="content" id="content"></textarea>
20     </div>
21     <input type="submit" value="提交"/>
22 </form>
23 
24 <script src="/static/jquery-1.12.4.js"></script>
25 <script src="/static/plugins/kind-editor/kindeditor-all.js"></script>
26 <script>
27     $(function () {
28         initKindEditor();
29     });
30 
31     function initKindEditor() {
32         var a = 'kind';
33         var kind = KindEditor.create('#content', {
34              '100%',       // 文本框宽度(可以百分比或像素)
35             height: '300px',     // 文本框高度(只能像素)
36             minWidth: 200,       // 最小宽度(数字)
37             minHeight: 400,      // 最小高度(数字)
38             uploadJson: '/kind/upload_img/',
39             extraFileUploadParams: {
40                 'csrfmiddlewaretoken': '{{ csrf_token }}'
41             },
42             fileManagerJson: '/kind/file_manager/',
43             allowPreviewEmoticons: true,
44             allowImageUpload: true
45         });
46     }
47 </script>
48 </body>
49 </html>
HTML
 1 import os
 2 import json
 3 import time
 4 
 5 from django.shortcuts import render
 6 from django.shortcuts import HttpResponse
 7 
 8 
 9 def index(request):
10     """
11     首页
12     :param request:
13     :return:
14     """
15     return render(request, 'index.html')
16 
17 
18 def upload_img(request):
19     """
20     文件上传
21     :param request:
22     :return:
23     """
24     dic = {
25         'error': 0,
26         'url': '/static/imgs/20130809170025.png',
27         'message': '错误了...'
28     }
29 
30     return HttpResponse(json.dumps(dic))
31 
32 
33 def file_manager(request):
34     """
35     文件管理
36     :param request:
37     :return:
38     """
39     dic = {}
40     root_path = '/Users/wupeiqi/PycharmProjects/editors/static/'
41     static_root_path = '/static/'
42     request_path = request.GET.get('path')
43     if request_path:
44         abs_current_dir_path = os.path.join(root_path, request_path)
45         move_up_dir_path = os.path.dirname(request_path.rstrip('/'))
46         dic['moveup_dir_path'] = move_up_dir_path + '/' if move_up_dir_path else move_up_dir_path
47 
48     else:
49         abs_current_dir_path = root_path
50         dic['moveup_dir_path'] = ''
51 
52     dic['current_dir_path'] = request_path
53     dic['current_url'] = os.path.join(static_root_path, request_path)
54 
55     file_list = []
56     for item in os.listdir(abs_current_dir_path):
57         abs_item_path = os.path.join(abs_current_dir_path, item)
58         a, exts = os.path.splitext(item)
59         is_dir = os.path.isdir(abs_item_path)
60         if is_dir:
61             temp = {
62                 'is_dir': True,
63                 'has_file': True,
64                 'filesize': 0,
65                 'dir_path': '',
66                 'is_photo': False,
67                 'filetype': '',
68                 'filename': item,
69                 'datetime': time.strftime('%Y-%m-%d %H:%M:%S', time.gmtime(os.path.getctime(abs_item_path)))
70             }
71         else:
72             temp = {
73                 'is_dir': False,
74                 'has_file': False,
75                 'filesize': os.stat(abs_item_path).st_size,
76                 'dir_path': '',
77                 'is_photo': True if exts.lower() in ['.jpg', '.png', '.jpeg'] else False,
78                 'filetype': exts.lower().strip('.'),
79                 'filename': item,
80                 'datetime': time.strftime('%Y-%m-%d %H:%M:%S', time.gmtime(os.path.getctime(abs_item_path)))
81             }
82 
83         file_list.append(temp)
84     dic['file_list'] = file_list
85     return HttpResponse(json.dumps(dic))
View

7、XSS过滤特殊标签

处理依赖

pip3 install beautifulsoup4
#!/usr/bin/env python
# -*- coding:utf-8 -*-
from bs4 import BeautifulSoup


class XSSFilter(object):
    __instance = None

    def __init__(self):
        # XSS白名单
        self.valid_tags = {
            "font": ['color', 'size', 'face', 'style'],
            'b': [],
            'div': [],
            "span": [],
            "table": [
                'border', 'cellspacing', 'cellpadding'
            ],
            'th': [
                'colspan', 'rowspan'
            ],
            'td': [
                'colspan', 'rowspan'
            ],
            "a": ['href', 'target', 'name'],
            "img": ['src', 'alt', 'title'],
            'p': [
                'align'
            ],
            "pre": ['class'],
            "hr": ['class'],
            'strong': []
        }

    @classmethod
    def instance(cls):
        if not cls.__instance:
            obj = cls()
            cls.__instance = obj
        return cls.__instance

    def process(self, content):
        soup = BeautifulSoup(content, 'lxml')
        # 遍历所有HTML标签
        for tag in soup.find_all(recursive=True):
            # 判断标签名是否在白名单中
            if tag.name not in self.valid_tags:
                tag.hidden = True
                if tag.name not in ['html', 'body']:
                    tag.hidden = True
                    tag.clear()
                continue
            # 当前标签的所有属性白名单
            attr_rules = self.valid_tags[tag.name]
            keys = list(tag.attrs.keys())
            for key in keys:
                if key not in attr_rules:
                    del tag[key]

        return soup.renderContents()


if __name__ == '__main__':
    html = """<p class="title">
                        <b>The Dormouse's story</b>
                    </p>
                    <p class="story">
                        <div name='root'>
                            Once upon a time there were three little sisters; and their names were
                            <a href="http://example.com/elsie" class="sister c1" style='color:red;background-color:green;' id="link1"><!-- Elsie --></a>
                            <a href="http://example.com/lacie" class="sister" id="link2">Lacie</a> and
                            <a href="http://example.com/tillie" class="sister" id="link3">Tilffffffffffffflie</a>;
                            and they lived at the bottom of a well.
                            <script>alert(123)</script>
                        </div>
                    </p>
                    <p class="story">...</p>"""

    v = XSSFilter.instance().process(html)
    print(v)
XSS实例
#!/usr/bin/env python
# -*- coding:utf-8 -*-
from bs4 import BeautifulSoup


class XSSFilter(object):
    __instance = None

    def __init__(self):
        # XSS白名单
        self.valid_tags = {
            "font": ['color', 'size', 'face', 'style'],
            'b': [],
            'div': [],
            "span": [],
            "table": [
                'border', 'cellspacing', 'cellpadding'
            ],
            'th': [
                'colspan', 'rowspan'
            ],
            'td': [
                'colspan', 'rowspan'
            ],
            "a": ['href', 'target', 'name'],
            "img": ['src', 'alt', 'title'],
            'p': [
                'align'
            ],
            "pre": ['class'],
            "hr": ['class'],
            'strong': []
        }

    def __new__(cls, *args, **kwargs):
        """
        单例模式
        :param cls:
        :param args:
        :param kwargs:
        :return:
        """
        if not cls.__instance:
            obj = object.__new__(cls, *args, **kwargs)
            cls.__instance = obj
        return cls.__instance

    def process(self, content):
        soup = BeautifulSoup(content, 'lxml')
        # 遍历所有HTML标签
        for tag in soup.find_all(recursive=True):
            # 判断标签名是否在白名单中
            if tag.name not in self.valid_tags:
                tag.hidden = True
                if tag.name not in ['html', 'body']:
                    tag.hidden = True
                    tag.clear()
                continue
            # 当前标签的所有属性白名单
            attr_rules = self.valid_tags[tag.name]
            keys = list(tag.attrs.keys())
            for key in keys:
                if key not in attr_rules:
                    del tag[key]

        return soup.renderContents()


if __name__ == '__main__':
    html = """<p class="title">
                        <b>The Dormouse's story</b>
                    </p>
                    <p class="story">
                        <div name='root'>
                            Once upon a time there were three little sisters; and their names were
                            <a href="http://example.com/elsie" class="sister c1" style='color:red;background-color:green;' id="link1"><!-- Elsie --></a>
                            <a href="http://example.com/lacie" class="sister" id="link2">Lacie</a> and
                            <a href="http://example.com/tillie" class="sister" id="link3">Tilffffffffffffflie</a>;
                            and they lived at the bottom of a well.
                            <script>alert(123)</script>
                        </div>
                    </p>
                    <p class="story">...</p>"""

    obj = XSSFilter()
    v = obj.process(html)
    print(v)
基于__new__实现的单例方式
原文地址:https://www.cnblogs.com/sxzwj/p/6385631.html