Получение данных из файла XML в базу данных MySQL - PullRequest
0 голосов
/ 03 мая 2018

Я должен получить данные из XML-файла и должен войти в базу данных. Не было ошибки при запуске файла python, но данные не попадают в базу данных. Я не могу найти, где я ошибся. Было бы очень полезно, если бы кто-нибудь мог мне помочь.

Вот мой код Python,

from xml.etree import ElementTree
import mysql.connector

dom = ElementTree.parse('profile.xml')

ticker = dom.findall('TICKER')
name = dom.findall('NAME')
address = dom.findall('ADDRESS')
phone = dom.findall('PHONE')
website = dom.findall('WEBSITE')
sector = dom.findall('SECTOR')
industry = dom.findall('INDUSTRY')
full_time = dom.findall('FULL_TIME')
bus_summ = dom.findall('BUS_SUMM')

ticker_list = [t.text for t in ticker]
name_list = [t.text for t in name]
add_list = [t.text for t in address]
phn_list = [t.text for t in phone]
site_list = [t.text for t in website]
sec_list = [t.text for t in sector]
ind_list = [t.text for t in industry]
emp_list = [t.text for t in full_time]
sum_list = [t.text for t in bus_summ]

db = mysql.connector.Connect(host = 'localhost', user = 'root', password ='root' , database = 'nldb_project')
cur = db.cursor()
query = "INSERT INTO profiles(`prof_ticker`,`name`,`address`,`phonenum`,`website`,`sector`,`industry`,full_time`,`bus_summ`) VALUES (%s, %s, %s, %s, %s, %s, %s, %s, %s)"

sqltuples = [(t,n,a,p,s,sec,i,e,su) for t,n,a,p,s,sec,i,e,su in zip(ticker_list,name_list,add_list,phn_list,site_list,sec_list,ind_list,emp_list,sum_list)]
cur.executemany(query,sqltuples)

Я использую версию Python 3.6.5.

Вот мой код xml,

<?xml version="1.0"?>
<collection shelf = 'profile'>
<INFO>
    <TICKER>AAPL</TICKER>
    <NAME> Apple Inc.</NAME>
    <ADDRESS>1 Infinite Loop;Cupertino, CA 95014;United State</ADDRESS>
    <PHONE>408-996-1010</PHONE>
    <WEBSITE>http://www.apple.com</WEBSITE>
    <SECTOR>Technology</SECTOR>
    <INDUSTRY>Consumer Electronics</INDUSTRY>
    <FULL_TIME>100,000</FULL_TIME>
    <BUS_SUMM>Apple</BUS_SUMM>
    <SOURCE>https://finance.yahoo.com/quote/AAPL/profile?p=AAPL</SOURCE> 
</INFO>
<INFO>
    <TICKER>T</TICKER>
    <NAME> AT and T Inc.</NAME>
    <ADDRESS>208 South Akard Street;Dallas, TX 75202;United States</ADDRESS>
    <PHONE>210-821-4105</PHONE>
    <WEBSITE>http://www.att.com</WEBSITE>
    <SECTOR>Communication Services</SECTOR>
    <INDUSTRY> Telecom Services</INDUSTRY>
    <FULL_TIME>254,000</FULL_TIME>
    <BUS_SUMM>at and t</BUS_SUMM>
    <SOURCE>https://finance.yahoo.com/quote/T/profile?p=T</SOURCE>
</INFO>
<INFO>
    <TICKER>IBM</TICKER>
    <NAME>International Business Machines Corporation</NAME>
    <ADDRESS>1 New Orchard Road;Armonk, NY 10504;United States</ADDRESS>
    <PHONE>914-499-1900</PHONE>
    <WEBSITE>http://www.ibm.com</WEBSITE>
    <SECTOR>Technology</SECTOR>
    <INDUSTRY> Information Technology Services</INDUSTRY>
    <FULL_TIME>366,600</FULL_TIME>
    <BUS_SUMM>ibm</BUS_SUMM>
    <SOURCE>https://finance.yahoo.com/quote/IBM/profile?p=IBM</SOURCE>
</INFO>
<INFO>
    <TICKER>TWTR</TICKER>
    <NAME>Twitter,Inc.</NAME>
    <ADDRESS>1355 Market Street;Suite 900;San Francisco, CA 94103;United States</ADDRESS>
    <PHONE>415-222-9670</PHONE>
    <WEBSITE>http://www.twitter.com</WEBSITE>
    <SECTOR>Technology</SECTOR>
    <INDUSTRY>Internet Content Information</INDUSTRY>
    <FULL_TIME>3,372</FULL_TIME>
    <BUS_SUMM>twitter</BUS_SUMM>
    <SOURCE>https://finance.yahoo.com/quote/TWTR/profile?p=TWTR</SOURCE>
</INFO>
<INFO>
    <TICKER>TSLA</TICKER>
    <NAME>Tesla,Inc.</NAME>
    <ADDRESS>3500 Deer Creek Road;Palo Alto, CA 94304;United States</ADDRESS>
    <PHONE>650-681-5000</PHONE>
    <WEBSITE>http://www.tesla.com</WEBSITE>
    <SECTOR>Consumer Cyclical</SECTOR>
    <INDUSTRY>Auto Manufacturers</INDUSTRY>
    <FULL_TIME>37,543</FULL_TIME>
    <BUS_SUMM>tesla</BUS_SUMM>
    <SOURCE>https://finance.yahoo.com/quote/TSLA/profile?p=TSLA</SOURCE>
</INFO>
<INFO>
    <TICKER>PYPL</TICKER>
    <NAME>PayPal Holdings, Inc.</NAME>
    <ADDRESS>2211 North First Street;San Jose, CA 95131;United States</ADDRESS>
    <PHONE>408-967-1000</PHONE>
    <WEBSITE>http://www.paypal.com</WEBSITE>
    <SECTOR>Financial Services</SECTOR>
    <INDUSTRY>Credit Services</INDUSTRY>
    <FULL_TIME>18,700</FULL_TIME>
    <BUS_SUMM>paypal</BUS_SUMM>
    <SOURCE>https://finance.yahoo.com/quote/PYPL/profile?p=PYPL</SOURCE>
</INFO>
</collection>

Ответы [ 2 ]

0 голосов
/ 04 мая 2018

причина ваших проблем

У вас есть 18 списков, которые все пусты, поэтому вы не видите никакого эффекта на базу данных после вставки.

Я не могу найти, где я ошибся.

Ваши проблемы проистекают из недоразумения по поводу использования findall():

Element.findall() находит только элементы с тегом, которые являются прямыми дочерние элементы текущего элемента.

Итак, позвольте мне взять ticker в качестве примера:

ticker = dom.findall('TICKER')

Что такое dom? Он просто указывает на корневой элемент вашего XML-дерева, который в вашем случае равен collection:

>>> dom
<Element 'collection' at 0x7f5e24a42e10>

Теперь спросите себя: каковы прямые элементы коллекции? Вы видите, что есть 6 INFO прямых дочерних элементов и абсолютно нет TICKER элемента.

>>> infos = dom.findall('INFO')
>>> len(infos)
6

Поэтому, когда вы запускаете ticker = dom.findall('TICKER'), вы просто ищете прямых потомков коллекции, которые называются TICKER, и, так как их нет, ваш список ticker пуст.

>>> ticker = dom.findall('TICKER')
>>> ticker
[]

Итак, позже в вашем коде, когда вы запустите это: ticker_list = [t.text for t in ticker] вы просто зацикливаетесь на пустом списке, и вы ничего не получаете из ничего, я имею в виду:

>>> ticker_list = [t.text for t in tickers]
>>> ticker_list
[]

Теперь примените эту аргументацию к 8 оставшимся первым спискам с соответствующими им 8 списками во второй части вашего кода.

Как исправить проблемы?

Как решить вашу проблему тогда? Что ж, если вы поняли то, что я объяснил выше, вы уже на полпути к решению ваших проблем. Давайте сделаем это:

После загрузки вашего XML-файла в dom, инициализируйте 9 пустых списков, которые вам нужны:

>>> ticker_list = []
>>> name_list = []
>>> add_list = []
>>> phn_list = []
>>> site_list = []
>>> sec_list = []
>>> ind_list = []
>>> emp_list = []
>>> sum_list = []

Затем переберите свои данные, учитывая их иерархию и принципы работы findall(). Например, давайте сосредоточимся на ticker_list:

>>> dom
<Element 'collection' at 0x7f5e24a42e10>
>>> infos = dom.findall('INFO')
>>> for info in infos:
...     tickers = info.findall('TICKER')
...     for ticker in tickers:
...             ticker_list.append(ticker.text)
... 
>>> ticker_list
['AAPL', 'T', 'IBM', 'TWTR', 'TSLA', 'PYPL']

Теперь выполните ту же логику для остальных 8 списков, которые вы ищете:

>>> infos = dom.findall('INFO')
>>> for info in infos:
...     tickers = info.findall('TICKER')
...     for ticker in tickers:
...             ticker_list.append(ticker.text)
...     names = info.findall('NAME')
...     for name in names:
...             name_list.append(name.text)
...     adds = info.findall('ADDRESS')
...     for add in adds:
...             add_list.append(add.text)
...     phns = info.findall('PHONE')
...     for phn in phns:
...             phn_list.append(phn.text)
...     sites = info.findall('WEBSITE')
...     for site in sites:
...             site_list.append(site.text)
...     secs = info.findall('SECTOR')
...     for sec in secs:
...             sec_list.append(sec.text)
...     inds = info.findall('INDUSTRY')
...     for ind in inds:
...             ind_list.append(ind.text)
...     emps = info.findall('FULL_TIME')
...     for emp in emps:
...             emp_list.append(emp.text)
...     sums = info.findall('BUS_SUMM')
...     for sum in sums:
...             sum_list.append(sum.text)

Теперь в ваших списках есть данные, и вставка должна работать успешно.

Дополнительное примечание:

Конечно, iter значительно упростит код, чем при использовании findall()

0 голосов
/ 03 мая 2018

При подключении к базе данных начинается новая транзакция по умолчанию. Если автоматическая фиксация отключена (обычно по умолчанию), вы должны подтвердить, что подтвердили любые внесенные вами изменения, или откатить, чтобы отменить их.

Просто добавьте

db.commit()

в и из вашего кода для фиксации изменений.

Могут быть и другие ошибки, было бы лучше, если бы вы предоставили profile.xml для тестирования. По крайней мере, в запросе отсутствует кавычка для одного из полей.

...