Python如何解决secure_filename对中文不支持问题


Posted in Python onJuly 16, 2021

前言:最近使用到了secure_filename,然后悲剧的发现中文居然不展示出来,于是我慢慢的debug,终于找到问题了。

一、最近使用secure_filename发现的问题

文件名是中文版的,悲剧的是中文以及其他特殊字符会被省略。

Python如何解决secure_filename对中文不支持问题

二、后面找到了原因

原来secure_filename()函数只返回ASCII字符,非ASCII字符会被过滤掉。

三、解决方案

找到secure_filename(filename)函数,修改它的源代码。

secure_filename(filename)函数源代码:
def secure_filename(filename: str) -> str:
    r"""Pass it a filename and it will return a secure version of it.  This
    filename can then safely be stored on a regular file system and passed
    to :func:`os.path.join`.  The filename returned is an ASCII only string
    for maximum portability.

    On windows systems the function also makes sure that the file is not
    named after one of the special device files.

    >>> secure_filename("My cool movie.mov")
    'My_cool_movie.mov'
    >>> secure_filename("../../../etc/passwd")
    'etc_passwd'
    >>> secure_filename('i contain cool \xfcml\xe4uts.txt')
    'i_contain_cool_umlauts.txt'

    The function might return an empty filename.  It's your responsibility
    to ensure that the filename is unique and that you abort or
    generate a random filename if the function returned an empty one.

    .. versionadded:: 0.5

    :param filename: the filename to secure
    """
    filename = unicodedata.normalize("NFKD", filename)
    filename = filename.encode("ascii", "ignore").decode("ascii")

    for sep in os.path.sep, os.path.altsep:
        if sep:
            filename = filename.replace(sep, " ")
    filename = str(_filename_ascii_strip_re.sub("", "_".join(filename.split()))).strip(
        "._"
    )

    # on nt a couple of special files are present in each folder.  We
    # have to ensure that the target file is not such a filename.  In
    # this case we prepend an underline
    if (
        os.name == "nt"
        and filename
        and filename.split(".")[0].upper() in _windows_device_files
    ):
        filename = f"_{filename}"

    return filename

secure_filename(filename)函数修改后的代码:

def secure_filename(filename: str) -> str:
    r"""Pass it a filename and it will return a secure version of it.  This
    filename can then safely be stored on a regular file system and passed
    to :func:`os.path.join`.  The filename returned is an ASCII only string
    for maximum portability.

    On windows systems the function also makes sure that the file is not
    named after one of the special device files.

    >>> secure_filename("My cool movie.mov")
    'My_cool_movie.mov'
    >>> secure_filename("../../../etc/passwd")
    'etc_passwd'
    >>> secure_filename('i contain cool \xfcml\xe4uts.txt')
    'i_contain_cool_umlauts.txt'

    The function might return an empty filename.  It's your responsibility
    to ensure that the filename is unique and that you abort or
    generate a random filename if the function returned an empty one.

    .. versionadded:: 0.5

    :param filename: the filename to secure
    """
    filename = unicodedata.normalize("NFKD", filename)
    filename = filename.encode("utf8", "ignore").decode("utf8")   # 编码格式改变

    for sep in os.path.sep, os.path.altsep:
        if sep:
            filename = filename.replace(sep, " ")
    _filename_ascii_add_strip_re = re.compile(r'[^A-Za-z0-9_\u4E00-\u9FBF\u3040-\u30FF\u31F0-\u31FF.-]')
    filename = str(_filename_ascii_add_strip_re.sub('', '_'.join(filename.split()))).strip('._')             # 添加新规则

    # on nt a couple of special files are present in each folder.  We
    # have to ensure that the target file is not such a filename.  In
    # this case we prepend an underline
    if (
        os.name == "nt"
        and filename
        and filename.split(".")[0].upper() in _windows_device_files
    ):
        filename = f"_{filename}"

    return filename

四、效果展示

我们很清楚的看到了效果,目前是支持中文的

Python如何解决secure_filename对中文不支持问题

到此这篇关于Python如何解决secure_filename对中文不支持问题的文章就介绍到这了,更多相关Python secure_filename不支持中文内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Python 相关文章推荐
pytyon 带有重复的全排列
Aug 13 Python
Python配置文件解析模块ConfigParser使用实例
Apr 13 Python
使用Kivy将python程序打包为apk文件
Jul 29 Python
使用pandas实现csv/excel sheet互相转换的方法
Dec 10 Python
python科学计算之scipy——optimize用法
Nov 25 Python
Pyspark读取parquet数据过程解析
Mar 27 Python
Python如何合并多个字典或映射
Jul 24 Python
Django如何使用asyncio协程和ThreadPoolExecutor多线程
Oct 12 Python
python用分数表示矩阵的方法实例
Jan 11 Python
matplotlib交互式数据光标mpldatacursor的实现
Feb 03 Python
90行Python代码开发个人云盘应用
Apr 20 Python
Python基础之进程详解
May 21 Python
利用Matlab绘制各类特殊图形的实例代码
Flask response响应的具体使用
Python 快速验证代理IP是否有效的方法实现
Jul 15 #Python
Django路由层如何获取正确的url
Jul 15 #Python
Python实现排序方法常见的四种
Jul 15 #Python
手把手教你使用TensorFlow2实现RNN
一篇文章弄懂Python关键字、标识符和变量
You might like
PHP缓存技术的多种方法小结
2012/08/14 PHP
php中实现xml与mysql数据相互转换的方法
2014/12/25 PHP
php mysql_real_escape_string addslashes及mysql绑定参数防SQL注入攻击
2016/12/23 PHP
利用PHP内置SERVER开启web服务(本地开发使用)
2020/01/22 PHP
JSON.parse 解析字符串出错的解决方法
2010/07/08 Javascript
图片翻转效果具体实现代码
2014/01/09 Javascript
使用JavaScript 实现的人脸检测
2015/03/24 Javascript
javascript Array 数组常用方法
2015/04/05 Javascript
js控制div弹出层实现方法
2015/05/11 Javascript
基于Bootstrap+jQuery.validate实现表单验证
2016/05/30 Javascript
JS与HTML结合使用marquee标签实现无缝滚动效果代码
2016/07/05 Javascript
对javascript继承的理解
2016/10/11 Javascript
JS搜狐面试题分析
2016/12/16 Javascript
JavaScript 函数节流详解及方法总结
2017/02/09 Javascript
ionic2打包android时gradle无法下载的解决方法
2017/04/05 Javascript
Ionic3 UI组件之Gallery Modal详解
2017/06/07 Javascript
浅谈jQuery框架Ajax常用选项
2017/07/08 jQuery
AngularJS的$location使用方法详解
2017/10/19 Javascript
js中split()方法得到的数组长度问题
2018/07/19 Javascript
在vue中v-bind使用三目运算符绑定class的实例
2018/09/29 Javascript
js实现查询商品案例
2020/07/22 Javascript
python通过pil为png图片填充上背景颜色的方法
2015/03/17 Python
为何人工智能(AI)首选Python?读完这篇文章你就知道了(推荐)
2019/04/06 Python
python os.path.isfile 的使用误区详解
2019/11/29 Python
联想德国官网:Lenovo Germany
2018/07/04 全球购物
曼城官方网上商店:Manchester City
2019/09/10 全球购物
Zatchels官网:英国剑桥包品牌
2021/01/12 全球购物
实习单位评语
2014/04/26 职场文书
体育活动总结范文
2014/05/04 职场文书
减负增效提质方案
2014/05/23 职场文书
公司户外活动总结
2014/07/04 职场文书
防暑降温通知书
2015/04/27 职场文书
2015年社区科普工作总结
2015/05/13 职场文书
html实现随机点名器的示例代码
2021/04/02 Javascript
工厂无线对讲系统解决方案
2022/02/18 无线电
vue 自定义组件添加原生事件
2022/04/21 Vue.js