python 3 xml данные в переменные - PullRequest
0 голосов
/ 18 января 2020

Я хотел бы прочитать данные с моего солнечного инвертора и опубликовать их на pvoutput.org. Инвертор отвечает на это xml:

<Device Name="StecaGrid 4200" Type="Inverter" Serial="********************" BusAddress="1" NetBiosName="***************" IpAddress="***.***.****.***" DateTime="2020-01-18T16:31:31">
<Measurements>
<Measurement Value="225.492" Unit="V" Type="AC_Voltage"/>
<Measurement Value="0.442" Unit="A" Type="AC_Current"/>
<Measurement Value="83.860" Unit="W" Type="AC_Power"/>
<Measurement Value="49.983" Unit="Hz" Type="AC_Frequency"/>
<Measurement Value="470.400" Unit="V" Type="DC_Voltage"/>
<Measurement Value="0.182" Unit="A" Type="DC_Current"/>
<Measurement Value="85.840" Unit="W" Type="DC_Power"/>
<Measurement Value="20.000" Unit="°C" Type="Temp"/>
</Measurements>
</Device>
</root> 

Я использую следующий код для чтения данных:

import urllib.request, urllib.parse, urllib.error
import xml.etree.ElementTree as ET

url = 'http://***.***.***.***/measurements.xml'

uh = urllib.request.urlopen(url)
data = uh.read()

tree = ET.fromstring(data)

lst = tree.findall('Measurements')

counts = tree.findall('.//Measurement')
print(tree.findall('.//Measurement').find('AC_Voltage'))

for each in counts:
    print(each.attrib['Type'], each.attrib['Value'], each.attrib['Unit'])

Если светит солнце, результаты выглядят так:

C_Voltage 226.632 V
AC_Current 0.259 A
AC_Power 41.920 W
AC_Frequency 49.980 Hz
DC_Voltage 451.896 V
DC_Current 0.100 A
DC_Power 45.270 W
Temp 18.100 °C

Но когда значение равно 0, атрибут опускается.

Только если AC_Power> 0, я хочу загрузить данные. Как я могу сохранить эти атрибуты в переменных или массивах для создания URL-адреса POST?

1 Ответ

1 голос
/ 18 января 2020

лучшие парсеры типа " l xml" из beautifulsoup4 могут облегчить работу. предполагая, что опрос инвертора происходит через фиксированные промежутки времени, и вы периодически получаете данные в файле xml, вы можете сначала установить l xml и красивый суп с помощью следующей комбинированной команды:

python3 -m pip install l xml bs4 beautifulsoup4

теперь, что бы у вас ни было xml с любыми атрибутами и дочерними тегами, вы можете сделать следующий метод, используя beautifulsoup4, чтобы получить значение атрибута.

from bs4 import BeautifulSoup as soup
import requests
import lxml

def read_ac_power(file_name):
    data=open(file_name, 'r').read()
    variabul=soup(data,'lxml')
    val=variabul.findAll('measurement')[2]
    return val['value']

AC_Power=float(read_ac_power('inverter'))
print(AC_Power)

#compare the variable and send to server , use POST [or your preferred] method

Если вы не хотите хранить файл, удалите метод open (имя_файла, 'r'). Read () и подключите данные напрямую.

Пояснение

суть float () , которая явно преобразует строку из xml do c в float .

val=variabul.findAll('measurement')[2]  #AC_power is stored as 3rd item...

return val['value'] #returns a string & need conversion
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...