在python中创建一个符合特定JSON的JSON对象

2024-09-27 21:24:58 发布

您现在位置:Python中文网/ 问答频道 /正文

所以我要做的是使用一个预先存在的文件在python中对JSON对象进行反向工程。文件内容如下:

[
{
    "id": "PA_vnf",
    "name": "PA",
    "short-name": "PA",
    "description": "A firewall PaloAlto",
    "version": "1.0",
    "connection-point": [
        {
            "type": "VPORT",
            "name": "PA/cp0"
        },
        {
            "type": "VPORT",
            "name": "PA/cp1"
        },
        {
            "type": "VPORT",
            "name": "PA/cp2"
        }
    ],
    "vdu": [
        {
            "id": "pa_vdu",
            "external-interface": [
                {
                    "virtual-interface": {
                        "type": "VIRTIO"
                    },
                    "vnfd-connection-point-ref": "PA/cp0",
                    "name": "eth0"
                },
                {
                    "virtual-interface": {
                        "type": "VIRTIO"
                    },
                    "vnfd-connection-point-ref": "PA/cp1",
                    "name": "eth1"
                },
                {
                    "virtual-interface": {
                        "type": "VIRTIO"
                    },
                    "vnfd-connection-point-ref": "PA/cp2",
                    "name": "eth2"
                }
            ],
            "guest-epa": {
                "cpu-pinning-policy": "ANY"
            },
            "name": "vdu-1",
            "vm-flavor": {
                "storage-gb": 40,
                "memory-mb": 4096,
                "vcpu-count": 4
            },
            "image": "paloAlto_RIP"
        }
    ],
    "service-function-chain": "UNAWARE",
    "meta": "important info"
}
]

为了简单起见,目前我正在对所有键的值进行硬编码,示例代码如下所示:

^{pr2}$

我得到如下o/p:

{
"short-name": "PA",
"vdu": {
    "name": "vdu-1",
    "image": "paloAlto_RIP",
    "id": "pa_vdu",
    "external-interface": {
        "virtual-interface": {
            "type": "VIRTIO"
        },
        "vnfd-connection-point-ref": "PA/cp0",
        "name": "eth0"
    },
    "guest-epa": {
        "cpu-pinning-policy": "ANY"
    },
    "vm-flavor": {
        "storage-gb": 20,
        "vcpu-count": 4,
        "memory-mb": 1024
    }
},
"description": "A firewall PaloAlto",
"version": "1.0",
"service-function-chain": "UNAWARE",
"id": "PA_vnf",
"name": "PA"
}

上面的O/p很好,但是我希望像“外部接口”这样的某些属性有多个值,这是我做不到的。我在字典上尝试了append方法,但它总是给我抛出一个错误“'集合.defaultdict'object没有属性'append'。 我使用的示例append:ginfo['vdu']['external-interface']['vnfd-connection-point-ref'].append(“value”)

我不知道出什么问题了。另外,我如何得到输出中的第一个方括号,这在我的o/p中丢失了。我知道它应该是一个数组,但我不确定如何在dictionary对象上应用数组逻辑。在

如果解释不够清楚,请让我知道,因为我是在大约5个小时的不走运后键入这个帮助。在


Tags: namerefidtypevirtualconnectioninterfacepoint
3条回答

感谢您@Daniel Roseman和@klashxx我能够使用您的两个解决方案来构建最终代码。我把代码写在下面:

import json
import yaml
import sys
from collections import defaultdict

def nested_dict(n, type):
  if n == 1:
    return defaultdict(type)
  else:
    return defaultdict(lambda: nested_dict(n-1, type))

ginfo = nested_dict(5,list)
ginfo = []
ginfo.append({})
ginfo[0]['description'] = 'A firewall PaloAlto'
ginfo[0]['name'] = 'PA'
ginfo[0]['id']= 'PA_vnf'
ginfo[0]['version'] = '1.0'
ginfo[0]['service-function-chain'] = 'UNAWARE'
ginfo[0]['short-name'] = 'PA'
ginfo[0]['vdu'] = []
interfaces = []
interfaces.append({'virtual-interface': {'type': 'VIRTIO'},
                                   'vnfd-connection-point-ref': 'PA/cp0',
                                   'name': 'eth0'})
interfaces.append({'virtual-interface': {'type': 'VIRTIO'},
                                   'vnfd-connection-point-ref': 'PA/cp1',
                                   'name': 'eth1'})
interfaces.append({'virtual-interface': {'type': 'VIRTIO'},
                                   'vnfd-connection-point-ref': 'PA/cp2',
                                   'name': 'eth2'})
ginfo[0]['vdu'].append({'id': 'pa_vdu',
                 'name': 'vdu-1',
         'image': 'paloAlto_RIP',
                 'guest-epa':{'cpu-pinning-policy': 'ANY'},
                 'external-interface': interfaces,
                 'vm-flavor': {'storage-gb': 40,
                 'memory-mb': 4096,
                 'vcpu-count': 4}})
ginfo[0]['connection-point'] = []
cp =[]
cp.append({'type': 'VPORT',
    'name': 'PA/cp0'})
cp.append({'type': 'VPORT',
    'name': 'PA/cp1'})
cp.append({'type': 'VPORT',
    'name': 'PA/cp2'})
ginfo[0]['connection-point'].append({'connection-point': cp})
print(json.dumps(ginfo))

def nested_dict(n, type):
  if n == 1:
    return defaultdict(type)
  else:
    return defaultdict(lambda: nested_dict(n-1, type))

它喷出了如下o/p:

- "short-name": PA vdu: - name: "vdu-1" image: paloAlto_RIP id: pa_vdu "external-interface": - "virtual-interface": type: VIRTIO "vnfd-connection-point-ref": "PA/cp0" name: eth0 - "virtual-interface": type: VIRTIO "vnfd-connection-point-ref": "PA/cp1" name: eth1 - "virtual-interface": type: VIRTIO "vnfd-connection-point-ref": "PA/cp2" name: eth2 "guest-epa": "cpu-pinning-policy": ANY "vm-flavor": "storage-gb": 40 "vcpu-count": 4 "memory-mb": 4096 description: "A firewall PaloAlto" "connection-point": - "connection-point": - type: VPORT name: "PA/cp0" - type: VPORT name: "PA/cp1" - type: VPORT name: "PA/cp2" version: "1.0" "service-function-chain": UNAWARE id: PA_vnf name: PA

这在技术上是正确的。现在问题是双引号。我不希望属性使用双引号,但是值可以用双引号。属性的双引号随机出现。 再次感谢你的帮助。既然原来的问题已经回答了,我就把这个标记为已解决。在

你不能在字典上“应用数组逻辑”。如果你想要一个数组(比如一个列表),那么就用一个列表。在原始JSON中,connection_point和{}都是dict的列表,就像vdu中的{}一样。在

如果你真的还想一行一行地建立这个系统,你可以:

ginfo['vdu'] = []
ginfo['vdu'].append({})
ginfo['vdu'][0]['id'] = 'pa_vdu'

等等

Python表现力:

ginfo['vdu'] = []
interfaces = []
interfaces.append({'virtual-interface': {'type': 'VIRTIO'}, 
                   'vnfd-connection-point-ref': 'PA/cp0',
                   'name': 'eth0'})
...
...

ginfo['vdu'].append({'id': 'pa_vdu',
                     'external-interface': interfaces})

使用^{}结构的逆向工程更加清晰:

^{pr2}$

相关问题 更多 >

    热门问题