Сначала предыстория... Мне понадобилось для одной хитрой платформы поставлять курсы валют. По умолчанию эта платформа умеет забирать курсы валют с национального банка Украины и с центрального банка России. При этом если допустим ты указываешь, что необходимо брать курсы валют с Украины, то там в перечне курсов появляется стоимость рубля в гривнах, а если берёшь курсы валют с ЦБР (центральный банк России), то там есть стоимость гривен. В целом на платформе по расписанию срабатывает скрипт, который забирает котировки в XML формате с сайтов банков, далее он их парсит и кладет в базу данных. Проблема вся в том, что формат представления XML отличается конкретно и по идее надо переписывать парсер. Но мне то надо забирать курсы валют с национального банка кыргызской республики (НБКР), а там вообще третий формат... Я решил пойти по наименьшему пути сопротивления - а именно забирать курсы с НБКР и приводить их в такой же вид, как XML у ЦБР, а дальше отдавать результат на саму платформу. Так вот у каждой валюты есть свой цифровой уникальный код + как оказалось у некоторых банков есть свой внутренний идентификатор каждой валюты (например у ЦБР выглядит примерно так - R01234). Так вот в XML у ЦБР я нашел идентификаторы под все вообразимые валюты, кроме рубля. Немного поставило меня в ступор, но я решил проблему тем, что для своего парсера валют ввёл внутренний идентификатор от балды. Ну как бы ладно - всё работает и хорошо... Далее я сливаю XML файл с НБКР (а дело было 9 июля) и глядя в него смотрю на дату актуальности курсов валют на определенный период и вижу что она равняется 10 июля (т.е. такое складывается ощущение, что в НБКР работают Нострадамусы и они наперед знают какой будет курс валют на завтра)... Ну как бы фиг с ним - главное что пашет... А теперь код:
Писано всё это дело на python 3 версии...
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
# Скрипт для сбора данных о курсах валют с НБКР с дальнейшим преобразованием вида XML файла
# Дата последнего исправления: 9.07.2014
# Разработал: Constantine
#------------------------------------------------------------------------------------------------------------------------------------
# Импорт необходимых модулей
from datetime import datetime
from urllib.request import Request, urlopen, urlretrieve
from urllib.error import URLError
import xml.etree.ElementTree as etree
import os
# Начало программы
print ('\n \t',str(datetime.now()))
print ('-'*40)
# Объявление переменных
ndaily = ('daily.xml') # Необработанный XML файл, получаемый с www.nbkr.kg и находящийся в директории, где пашет парсер
geturl = ('http://www.nbkr.kg/XML/daily.xml') # Урл, откуда берём необработанный XML
rdaily = ('course.xml') # Куда будем сохранять данные
# Объявление функций
def checkget(text): # Функция проверки связи и доступности файла daily.xml на сервере НБКР
req = Request(text)
try:
response = urlopen(req)
return 1
except URLError as e:
if hasattr(e, 'reason'):
print('Server nbkr.kg is unavaliable.')
print('Reason: ', e.reason)
elif hasattr(e, 'code'):
print('Server return an error code.')
print('Error code: ', e.code)
else:
# everything is fine
print ('Ok')
return 0
def restest(rfile):
try:
with open(rfile, 'r+') as file:
pass
return 1
except IOError as e:
print ("Cant find result file. Trying to create new...")
return 0
def restest2(rfile):
try:
with open(rfile, 'w', encoding='utf8') as file:
pass
return 1
except IOError as e:
print ("Can't create result file. Check your permissions...")
return 0
def parser(nd, rd):
try:
tree = etree.parse(nd)
root = tree.getroot()
f = open(rd, 'w', encoding='utf8')
f.write('<?xml version="1.0" encoding="windows-1251" ?>\n')
f.write('<ValCurs Date="'+root.attrib['Date']+'" ''name="'+root.attrib['Name']+'">\n')
for i in range(len(root)):
isocode = (root[i].attrib['ISOCode'])
if isocode == 'USD':
idc = 'R01235'
numcode = '840'
vname = 'Доллар США'
elif isocode == 'EUR':
idc = 'R01239'
numcode = '978'
vname = 'Евро доллар'
elif isocode == 'KZT':
idc = 'R01335'
numcode = '398'
vname = 'Казахский тенге'
elif isocode == 'RUB':
idc = 'R06785'
numcode = '643'
vname = 'Российский рубль'
f.write('<Valute ID="'+idc+'">\n')
f.write(' <NumCode>'+numcode+'</NumCode>\n')
f.write(' <CharCode>'+isocode+'</CharCode>\n')
f.write(' <Nominal>'+root[i].find('Nominal').text+'</Nominal>\n')
f.write(' <Name>'+vname+'</Name>\n')
f.write(' <Value>'+root[i].find('Value').text+'</Value>\n')
f.write('</Valute>\n')
f.write('</ValCurs>')
f.close()
return 1
except:
return 0
# Начало работы программы
print ('System check... ')
abc = checkget(geturl)
if abc < 1:
print ('Can not establish a connection. Please check your channels')
elif abc == 1:
print ('File on nbkr.kg is avaliable. \nDownload begining... ')
destination = geturl.rsplit('/',1)[1]
urlretrieve(geturl, destination)
print ('File download ',geturl, 'is done.')
else:
print ('Unexpected error. Programm exiting...')
if os.path.isfile(ndaily) and os.path.getsize(ndaily)>0:
print ('File is ready... Data load is begining...')
else:
print ('File not ready for loading, probably daily.xml is corupt!')
wt = restest(rdaily)
if wt==1:
resp = parser(ndaily, rdaily)
elif wt==0:
wta = restest2(rdaily)
if wta ==1:
print ('File course.xml has been created, Trying to parse and load data into file...')
resp = parser(ndaily, rdaily)
elif wta ==0:
print ("Can't make result file. Please check your pewrmissions...")
if resp == 1:
print ('Data load is done!\n'+'-'*40)
else:
print ('Can\'t load data. File is unavaliable for write.')
# Конец программы
Комментариев нет:
Отправить комментарий