简体   繁体   English

TinyMCE & Flask - 图片上传

[英]TinyMCE & Flask - Image upload

I am trying to integrate tinyMce on a blog app using Flask. I have the images uploading and displaying correctly inside the editor but when the user wants to read the entire article my image does not display.我正在尝试使用 Flask 在博客应用程序上集成 tinyMce。我在编辑器中正确上传和显示图像,但是当用户想要阅读整篇文章时,我的图像不显示。

     * Serving Flask app "blog.py"
     * Environment: production
       WARNING: This is a development server. Do not use it in a production deployment.
       Use a production WSGI server instead.
     * Debug mode: off
    [2020-08-31 19:08:56,321] INFO in __init__: Blog site startup.
     * Running on http://127.0.0.1:5000/ (Press CTRL+C to quit)

    ...

    127.0.0.1 - - [31/Aug/2020 19:09:07] "POST /image-upload HTTP/1.1" 200 -
    Validating Image....[OK]
    /static/user_uploads/img_0992.jpeg
    127.0.0.1 - - [31/Aug/2020 19:09:37] "POST /create-post HTTP/1.1" 302 -
    127.0.0.1 - - [31/Aug/2020 19:09:37] "GET /index HTTP/1.1" 200 -
    127.0.0.1 - - [31/Aug/2020 19:09:37] "GET /jsglue.js HTTP/1.1" 200 -
    127.0.0.1 - - [31/Aug/2020 19:09:40] "GET /post/1 HTTP/1.1" 200 -
    127.0.0.1 - - [31/Aug/2020 19:09:40] "GET /jsglue.js HTTP/1.1" 200 -
    127.0.0.1 - - [31/Aug/2020 19:09:40] "GET /post/static/user_uploads/img_0992.jpeg HTTP/1.1" 404 

TinyMCE init: TinyMCE 初始化:

tinymce.init({
    selector: 'textarea',
    plugins: [
        'advlist autolink link image imagetools lists charmap print preview hr anchor pagebreak spellchecker',
        'searchreplace wordcount visualblocks visualchars code fullscreen insertdatetime media nonbreaking',
        'save table contextmenu directionality template paste textcolor codesample'
    ],
    toolbar: 'insertfile undo redo | styleselect | bold italic forecolor | alignleft aligncenter alignright alignjustify | bullist numlist | link image | print preview media fullpage | emoticons',
    images_upload_url: Flask.url_for('blog.image_uploader'),
    images_reuse_filename: false,
    automatic_uploads: true,
});

Flask view: Flask 查看:

@blog.route('/image-upload', methods=['POST'])
@login_required
def image_uploader():
    """
    Upload post images from tinyMce editor.
    Save image to path.
    returns: json { location: path }
    """

    # Get the file user has uploaded inside the tinymce editor.
    uploaded_file = request.files.get('file')

    if uploaded_file:
        filename = secure_filename(uploaded_file.filename).lower()

        # Validate the contents of the file.  Check the header of the file is infact an image.
        valid_img_ext = validate_img(uploaded_file.stream)

        # Split filename and extension, rename & add correct extension.
        filename = secure_filename(os.path.splitext(filename)[0] + valid_img_ext)

        img_path = os.path.join(current_app.config['IMG_UPLOAD_PATH'], filename)

        # Check if user directory exists, create if nessecary.
        if not os.path.exists(current_app.config['IMG_UPLOAD_PATH']):
            try:
                os.makedirs(current_app.config['IMG_UPLOAD_PATH'])
            except OSError as e:
                if e.errno != errno.EEXIST:
                    raise

        # Save the image.
        uploaded_file.save(img_path)
        location = url_for('static', filename='user_uploads/' + filename)
        print(location)

        # Return image path back to editor
        return jsonify({'location': location})

    abort(Response('404 - Image failed to upload'))


@blog.route('/post/<post_id>')
def post_detail(post_id):
    post = Post.query.get(post_id)
    return render_template('article.html', post=post)

As you can see above, the image validates and saves correctly.正如您在上面看到的,图像正确验证并保存。 I then try to view the article and I get a 404 - /post/static/user_uploads/img_0992.jpeg How do I stop the path being prefixed with /post/ so I simply get /static/user_uploads/img_0992.jpeg然后我尝试查看文章,我得到一个404 - /post/static/user_uploads/img_0992.jpeg如何停止以/post/为前缀的路径,所以我只是得到/static/user_uploads/img_0992.jpeg

for example, changing例如,改变

@blog.route('/post/<post_id>')

to

@blog.route('/<post_id>')

The image loads as it should, but this isn't a feasible solution图像加载正常,但这不是一个可行的解决方案

127.0.0.1 - - [31/Aug/2020 19:45:05] "GET /static/user_uploads/img_0992.jpeg HTTP/1.1" 200 -

Also, if I open up the console and add a / to the img src, the image loads as it should.此外,如果我打开控制台并将 / 添加到 img src,则图像会按原样加载。

<img alt="" height="267" src="static/user_uploads/img_0992.jpeg" width="200">

to

<img alt="" height="267" src="/static/user_uploads/img_0992.jpeg" width="200">

Where am I going wrong with this?我哪里错了?

Solved:解决了:

Needed to add需要添加

    relative_urls: false,
    images_upload_base_path: '/static/user_uploads',

to the tinymce.init()到 tinymce.init()

example:例子:

tinymce.init({
    selector: 'textarea',
    relative_urls: false,
    plugins: [
        'advlist autolink link image imagetools lists charmap print preview hr anchor pagebreak spellchecker',
        'searchreplace wordcount visualblocks visualchars code fullscreen insertdatetime media nonbreaking',
        'save table directionality template paste codesample'
    ],
    toolbar: 'insertfile undo redo | styleselect | bold italic forecolor | alignleft aligncenter alignright alignjustify | bullist numlist | link image | print preview media fullpage | emoticons',
    images_upload_url: Flask.url_for('blog.image_uploader'),
    images_reuse_filename: false,
    automatic_uploads: true,
    images_upload_base_path: '/static/user_uploads',
});

and return the filename from the view并从视图中返回文件名

return jsonify({'location': filename})

It prevents a new copy from being created when the uploaded file is edited with "images Tools".当使用“图像工具”编辑上传的文件时,它可以防止创建新副本。 It is created only when you upload a new file.它仅在您上传新文件时创建。

Make the following setting.进行以下设置。

tinymce.init({
            paste_data_images: false,
            images_reuse_filename: true,
            automatic_uploads: true,
            images_upload_handler: function (blobInfo, success, failure, progress) {
                                
                var  formData = new FormData();
                formData.append('file', blobInfo.blob(), blobInfo.filename());
                
                $.ajax({
                    type:'POST',
                    url:  'ajax.upload.php',
                    data: formData,
                    dataType: 'json',
                    cache:false,
                    contentType: false,
                    processData: false,
                    success:function(r){
                        if (r.error) {
                            alert("r.error");
                        } else if (r.message) {
                            success(r.message.location);
                        }                        
                    },
                    complete: function (jqXHR,exception) {
                       $('.tox-dialog__busy-spinner').hide();
                    },
                    error: function (jqXHR,exception) {
                        
                    }
                });
                
            }  
  });

PHP CODE: PHP 代码:

 // Yüklenecek dosya adı, yüklenen dosyaların adlarında var ise mevcut ad kullanılır.
    if( $_SESSION['TEMP_UPLOADED_IMAGES'][$handle_normal->file_src_name] === true ){
        
        // Dosya zaten mevcut ise otomatik olarak yeniden adlandırmayı devre dışı bırakır. Bu durumda mevcut dosya isimleri var ise üzerine yazılır.
        $handle_normal->file_overwrite = true;
        
             
        
        // Yüklenecek dosyanın adı mevcut adıyla kullanılır. Yeni adlandırma yapılmaz.
        $random_file_name = $handle_normal->file_src_name_body;
    } else {
        // Yüklenecek dosya rastgele adlandırılır.
        $random_file_name = $vd->randomNumbers(10));
    }

This code will run on every file upload.此代码将在每次文件上传时运行。 (after upload) (上传后)

$_SESSION['TEMP_UPLOADED_IMAGES'][$handle_normal->file_dst_name] = true;

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM