当前位置: 首页 > 面试题库 >

python ast.literal_eval和datetime

易英奕
2023-03-14
问题内容

我有一个字符串"{'datetime': datetime.datetime(2010, 11, 21, 0, 56, 58)}",我想将其转换为它代表的对象。使用ast.literal_eval()

ValueError: malformed string;

因为它不允许构造对象(即datetime调用)。无论如何,要么可以ast正确地处理此问题,要么可以确保eval防止代码注入?


问题答案:

跟随伊格纳西奥·巴斯克斯(Ignacio Vazquez-brams)的想法:

import ast
import datetime

def parse_datetime_dict(astr,debug=False):
    try: tree=ast.parse(astr)
    except SyntaxError: raise ValueError(astr)
    for node in ast.walk(tree):
        if isinstance(node,(ast.Module,ast.Expr,ast.Dict,ast.Str,
                            ast.Attribute,ast.Num,ast.Name,ast.Load, ast.Tuple)): continue
        if (isinstance(node,ast.Call)
                and isinstance(node.func, ast.Attribute)
                and node.func.attr == 'datetime'): continue
        if debug:
            attrs=[attr for attr in dir(node) if not attr.startswith('__')]
            print(node)
            for attrname in attrs:
                print('    {k} ==> {v}'.format(k=attrname,v=getattr(node,attrname)))
        raise ValueError(astr)
    return eval(astr)

good_strings=["{'the_datetime': datetime.datetime(2010, 11, 21, 0, 56, 58)}"]
bad_strings=["__import__('os'); os.unlink",
             "import os; os.unlink",
             "import(os)", # SyntaxError
             ]

for astr in good_strings:
    result=parse_datetime_dict(astr)    
    print('{s} ... [PASSED]'.format(s=astr))

for astr in bad_strings:
    try:
        result=parse_datetime_dict(astr)
    except ValueError:
        print('{s} ... [REJECTED]'.format(s=astr))
    else:
        sys.exit('ERROR: failed to catch {s!r}'.format(s=astr))

产量

{'the_datetime': datetime.datetime(2010, 11, 21, 0, 56, 58)} ... [PASSED]
__import__('os'); os.unlink ... [REJECTED]
import os; os.unlink ... [REJECTED]
import(os) ... [REJECTED]


 类似资料:
  • 问题内容: 我们正在将JSON发送到由swagger定义的API,其中一些属性是DateTime,格式为yyyy-MM- ddThh:mm:ss.000Z(毫秒数必须为3位,否则端点上的验证失败),而有些则是Date(否)时间)属性。 我已经看到很多消息说使用这样的格式化程序: 但这不能将DateTimes转换为正确的格式,C#如何处理仅Date类型?它似乎总是序列化为DateTime.MinVa

  • 问题内容: 关于它们有很多传说。我想知道真相。以下两个示例之间有什么区别? 问题答案: 不确定从何处获得传说,但: 提交按钮 与: IE6将在标记之间提交此按钮的所有文本,其他浏览器将仅提交值。使用可使您在按钮的设计上享有更大的布局自由度。从各种意图和目的看,它乍一看似乎很棒,但是各种浏览器怪癖使它有时很难使用。 在您的示例中,IE6将发送到服务器,而其他大多数浏览器将不发送任何内容。要使其跨浏览

  • 什么区别以及如何正确重写代码?

  • 问题内容: 在我的SQL Server我有测试,其中只包含三行一个非常简单的表: ,和(,,)。 SQL中的DateTime格式类似于:。 C#中的DateTime格式类似于:。 我使用以下代码获取C#DateTime格式: 如果我尝试将其放入,则会出现错误: 日历不支持由字符串表示的DateTime。 在我的C#应用​​程序中,我正在尝试查找破损日期之间的总小时数。我有点想使用它了,但是它只适用

  • 我试图理解为什么下面两个代码块会产生不同的结果。 代码块1按预期工作,并返回从数据库中查找的提供程序的数组。另一方面,代码块2返回函数数组。在理解promissione.all()和async/await时,我觉得缺少了一些简单的东西。 代码块的差异如下: > 块1:创建许诺函数数组,然后使用map运算符将其包装在异步函数中。 块2:许诺函数的数组被创建为异步函数。因此,不调用map运算符。 如果

  • 问题内容: 我才刚刚开始研究SQL。 我有一个SQL Server 2008r2数据库,它将返回两个字段DocDate和InvValue。我需要将InvValues汇总为今天的MTD和YTD,所以看起来像 我已经做了大量的Google搜寻,并且可以使用SUM&DATEPART进行一项或多项,但是我坚持尝试两者兼而有之。 有人可以给我一些伪代码,以帮助我进一步谷歌。 谢谢@戈登·利诺夫(Gordon