为了账号安全,请及时绑定邮箱和手机立即绑定

Python3将网页中的一堆JavaScript变量抓取到python dict对象中

Python3将网页中的一堆JavaScript变量抓取到python dict对象中

SMILET 2021-05-13 17:17:43
我正在使用请求和BeautifulSoup4从网页下载和抓取信息,我成功地将其范围缩小到了我要从中获取数据的特定<script>标记内的所有内容。为了使这部分代码正常工作,我跳过了所有请求和BS4的内容,只是在代码的开头添加了这个字符串,如下所示:Content = '''// <![CDATA[devicetype = "computer";isios = false;videocdn = "media";videopath = "updates/na/vid01";poster = {    "file": "preview/vidsplash.jpg",    "st": "1557499029",    "et": "1557502629",    "hs": "f3ad16f42fec5224d323915cdfbf43ed"};attachname = "some-video-00001234";videos[0] = {    "wmv": {        "file": "wmv/01.wmv",        "name": "01",        "duration": 502,        "size": "195.1MB",        "wid": 854,        "hgt": 480,        "st": "1557499029",        "et": "1557502629",        "hs": "a0cfdef3b8b9e3dea576368a5bfbaef9",        "caps": []    },    "h264": {        "file": "h264/01.mp4",        "name": "01",        "duration": 502,        "size": "73.9MB",        "wid": 854,        "hgt": 480,        "st": "1557499029",        "et": "1557502629",        "hs": "32901a1870d0b32458b465ac9c3d6cad",        "caps": [{            "file": "001.jpg",      另请注意,这是美化的。通常,“ poster”和“ videos [0]”变量将分别位于其自己的行中,而不是多行,并且像这样缩进。这不是来自<script>标记的完整数据集,我只是剥离了重复的部分,以使大家都能对数据的结构有所了解。另请注意,“ videos [0]”将类似的数据结构重复到“ videos [1]”中,依此类推。我想做的是将那个大的多行字符串以某种方式转换为正确的字典,我可以在我的python代码中进行操作以提取所需的位print(NewContent)输出:{'devicetype' = 'computer', 'isios' = False, "videocdn" = "media"}等等。我一直在纠结于js2py,试图让它做我需要做的事情,但是到目前为止,我得到的最远就是这个代码:splitrawlines = CONTENT.splitlines()rawvars = []for line in splitrawlines:    # need to add the videos declaration in case it gets to a line where it expects it to already be declared.    rawvars.append(js2py.eval_js("videos = [];\n" + line))print(rawvars)唯一的问题是它不会将其输出为dict,而是将其输出为列表,我可能仍然可以使它工作,但是它甚至不是python可以操纵的列表,从技术上讲它还是一个js2py.base.JsObjectWrapper对象。我可以将该对象转换为字符串,但是将字符串转换为列表的唯一方法是用空格分隔字符串中的所有内容,并将每个单独的部分丢入列表中自己的条目中。我基本上有一个已经格式化的列表,就在一个字符串中。我可能用那个代码走错了方向,但这是到目前为止我得到的最接近的代码。因此,我需要找到一种方法来将基本上已经格式化为完整列表的字符串转换为实际的列表对象,或者更可取的是,找到一种不同的方式来将随机JavaScript代码中的所有变量转换为本机python变量可以操纵。
查看完整描述

1 回答

?
慕容708150

TA贡献1831条经验 获得超4个赞

JavaScript数据大多为JSON格式,因此您可以使用python模块json将其转换为python s dictionary。


作为示例数据,在"videos[0] = "创建正确的JSON数据之后,您可以data = json.loads(stringg)用来创建字典-然后可以获取ie。data['wmv']['size']


data = '''{

    "wmv": {

        "file": "wmv/01.wmv",

        "name": "01",

        "duration": 502,

        "size": "195.1MB",

        "wid": 854,

        "hgt": 480,

        "st": "1557499029",

        "et": "1557502629",

        "hs": "a0cfdef3b8b9e3dea576368a5bfbaef9",

        "caps": []

    },

    "h264": {

        "file": "h264/01.mp4",

        "name": "01",

        "duration": 502,

        "size": "73.9MB",

        "wid": 854,

        "hgt": 480,

        "st": "1557499029",

        "et": "1557502629",

        "hs": "32901a1870d0b32458b465ac9c3d6cad",

        "caps": [{

            "file": "001.jpg",

            "fs": {

                "st": "1557499029",

                "et": "1557502629",

                "hs": "5b328642a84fa6406bda527c18e46c27"

            },

            "tn": {

                "st": "1557499029",

                "et": "1557502629",

                "hs": "0a4ad7d0edf1b92538b8127f8e297c41"

            }

        }, {

            "file": "002.jpg",

            "fs": {

                "st": "1557499029",

                "et": "1557502629",

                "hs": "4390c0d9b321b5e86c88cb8ca5e56ede"

            },

            "tn": {

                "st": "1557499029",

                "et": "1557502629",

                "hs": "9cf83158268379df660d6d01750a047c"

            }

        }]

    }

}'''


import json


data = json.loads(data)


print(data['wmv']['size'])


# 195.1MB

如果每个变量都是一行,则可以用于split('\n')获取行,然后用于split('=')获取键和值。


然后,你必须要是值仅开始检查用{或[在使用json。其他值可以是普通字符串,因此不需要json-它可能只需要删除"。


Content = '''// <![CDATA[

devicetype = "computer";

isios = false;

videocdn = "media";

videopath = "updates/na/vid01";

poster = {"file": "preview/vidsplash.jpg","st": "1557499029","et": "1557502629","hs": "f3ad16f42fec5224d323915cdfbf43ed"};

attachname = "some-video-00001234";'''


import json


results = {}


for line in Content.split('\n'):

    if ' = ' in line:

        line = line[:-1]  # remove `;`


        key, val = line.split(' = ', 1)


        if val.startswith( ('[', '{') ):

            results[key] = json.loads(val)

        elif val.startswith('"'):

            val = val[1:-1] # remove `"`

            results[key] = val

        elif val == 'false':

            results[key] = False

        elif val == 'true':

            results[key] = True


print(results['devicetype'])

print(results['isios'])

print(results['videocdn'])

print(results['poster']['file'])


# computer

# False

# media

# preview/vidsplash.jpg


查看完整回答
反对 回复 2021-05-27
  • 1 回答
  • 0 关注
  • 282 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信