Интеграция API Курсы валют Центрального Банка РФ в веб-платформе Falcon Space
Введение
В этой статье разберем как можно получать актуальные котировки валют по API от Центрального банка РФ.
Как это работает на демостенде Falcon Space - демостенд по получению котировок ЦБ РФ API. На нем можно посмотреть как это работает на живом примере.
Ниже идет описание обмена по API с сайтами, предоставляющими информацию о курсах валют.
Получение котировок валют с сайта ЦБ РФ
Описание - http://www.cbr.ru/development/SXML/
для получения котировок на заданный день
нужно отправить GET запрос вида: http://www.cbr.ru/scripts/XML_daily.asp?date_req=02/03/2002
где date_req= Date of query (dd/mm/yyyy)
Если параметр(date_req) отсутствует, то вы получите документ на последнюю зарегистрированную дату.
В некоторых ситуациях, например, когда запрос отправлен вечером – актуальные данные на завтра (Дата в будущем).
<!--?xml version="1.0" encoding="windows-1251"?-->
<valcurs date="06.06.2020" name="Foreign Currency Market">
…
<valute id="R01235">
<numcode>840</numcode>
<charcode>USD</charcode>
<nominal>1</nominal>
<name>Доллар США</name>
<value>68,6319</value>
</valute>
<valute id="R01239">
<numcode>978</numcode>
<charcode>EUR</charcode>
<nominal>1</nominal>
<name>Евро</name>
<value>77,9658</value>
</valute>
…
</valcurs>
Пример API Request по запросу валют.
CREATE PROCEDURE [dbo].[api_currencyRatesCBR_request]
@parameters ExtendedDictionaryParameter READONLY, -- входящие параметры для внутренней обработки (используйте Key, Value2)
@username nvarchar(32) -- текущий пользователь.
--
,@date_req nvarchar(10) = ''
AS
BEGIN
-- date_req= Date of query (dd/mm/yyyy)
-- * если параметр(date_req) отсутствует, то Вы получите документ на последнюю зарегистрированную дату.
-- 103 = дд/мм/гггг = 04/06/2020
IF LEN( ISNULL ( @date_req , '' ) )=0
-- SET @date_req = CONVERT ( nvarchar(10) , GETDATE() , 103 )
SET @date_req = CONVERT ( nvarchar(10) , GETDATE() +1 , 103 ) -- ПО ФАКТУ ВСЕГДА ЕСТЬ КУРС НА ЗАВТРА !!!
-- exec as_print @str = @date_req
DECLARE @apiUrl nvarchar(max) = '' -- Финальная строка для отправки -- @apiStr -- ФАКТИЧЕСКИ ЭТО Url
SET @apiUrl = 'http://www.cbr.ru/scripts/XML_daily.asp?'
-- ОТЛАДКА
-- SET @apiUrl = 'http://www.cbr.ru/scripts/XML_daily.asp?date_req=04/06/2020'
-- SET @apiUrl = 'http://www.cbr.ru/scripts/XML_daily.asp?date_req=' + ISNULL ( @date_req , '' )
-- ОТЛАДКА
insert into as_trace ( header, text, username, code , created ) values( '@apiUrl', @apiUrl , @username, 'api_currencyRatesCBR_request' , GETDATE() )
-- SELECT 1 Msg, Result, Url (адрес, куда будет идти запрос)
select '' Msg, 1 Result, @apiUrl Url
-- SELECT 2 PARAMETERS - параметры, которые будут передаваться во внешний источник
-- select 'id' name, '5' value, '' [type] -- form (в форме передается), header (в http headers), get запросы передавайте прямо в URL
END
PROCEDURE [dbo].[api_currencyRatesCBR_response]
Результат запроса может быть как сообщение с информацией, так и сообщение с ошибкой.
Список возможных сообщений об ошибках.
1 - Ошибка! В результате запроса @response нет корневого элемента ValCurs!
Если ошибок в ответе не обнаружено, из ответа выбираются такие данные:
Курс Доллар США и Евро.
Пример текста – результат: Курс на 06.06.2020 USD - Доллар США: 68,6319. EUR - Евро: 77,9658.
CREATE PROCEDURE [dbo].[api_currencyRatesCBR_response]
@response nvarchar(max),
@parameters ExtendedDictionaryParameter READONLY, -- входящие параметры для внутренней обработки (используйте Key, Value2 - те же что и на request)
@username nvarchar(32)
AS
BEGIN
-- ОТЛАДКА
insert into as_trace ( header, text, username, code , created ) values( '@response - 1 , 1024 ', SUBSTRING ( @response , 1 , 1024 ) , @username, 'api_currencyRatesCBR_response' , GETDATE() )
DECLARE @xml_STR Nvarchar(max)
SET @xml_STR = @response
DECLARE @xml xml -- переменная в которую преобразуем полученную строку
-- Условия работы / Конвертация строка - xml
-- 1. Тип данных Nvarchar(max)
-- 2. Unicode string with N == > Строки начинаются с N'== >N' "UTF-16"
-- ПРИХОДИТ КОДИРОВКА encoding="windows-1251"
-- set @xml_STR = REPLACE( @xml_STR ,'UTF-8','UTF-16')
set @xml_STR = REPLACE( @xml_STR ,'windows-1251','UTF-16')
set @xml =convert (xml, @xml_STR)
-- select @xml
DECLARE @exist_ValCurs bit = 0
select @exist_ValCurs = @xml.exist('/ValCurs')
IF @exist_ValCurs = 0
BEGIN
SELECT 'Ошибка! В результате запроса @response нет корневого элемента ValCurs! ' Msg, 0 Result, @response Response
RETURN
END
-- OpenXML --
DECLARE @hdoc int -- Дескриптор - указатель (handle) на создаваемую структуру дерева XML (потом будет использоваться в OPENXML и sp_xml_removedocument);
-- подготовка документа для работы - присвоение Дескриптор @hdoc
-- теперь к данным @xml можно обратиться FROM OPENXML (@hdoc ...
EXEC sp_xml_preparedocument @hdoc OUTPUT , @xml
-- Во врем. переменную
DECLARE @tmp_currencyRates Table ( id int identity not null
-- , ValDate Nvarchar(100) null
, NumCode Nvarchar(100) null, CharCode Nvarchar(100) null
, Nominal Nvarchar(100) null, Name Nvarchar(100) null, Value Nvarchar(100) null
)
-- Дата
DECLARE @valuteDate Nvarchar(32)
SELECT @valuteDate = X.ValCurDate FROM OPENXML (@hdoc, '/ValCurs',2) WITH ( ValCurDate Nvarchar(100) '@Date') AS X
-- SELECT @ValCurDate
-- все строки дублируются по 5 раза - по числу полей - ПОСТАВИТЬ DISTINCT
-- SELECT DISTINCT X. *
INSERT INTO @tmp_currencyRates
SELECT DISTINCT X.NumCode , X.CharCode , X.Nominal , X.Name , X.Value
FROM OPENXML (@hdoc, '/ValCurs/Valute/*',2) -- * - В Конце строки - работает
WITH ( -- '.' -- ТОЧКА - ВЫВОД ТЕКУЩЕЙ СТРОКИ -- ТУТ НЕ РАБОТАЕТ
NumCode Nvarchar(100) '../NumCode' -- РАБОТАЕТ -- '../CharCode'
, CharCode Nvarchar(100) '../CharCode'
, Nominal Nvarchar(100) '../Nominal'
, Name Nvarchar(100) '../Name'
, Value Nvarchar(100) '../Value'
)
AS X
-- Удалить дескриптор
EXEC sp_xml_removedocument @hdoc
-- SELECT * FROM @tmp_currencyRates
DECLARE @USDCharCode NVARCHAR(MAX) ,@USDName NVARCHAR(MAX) ,@USDValue NVARCHAR(MAX) , @USDNominal NVARCHAR(MAX)
,@EURCharCode NVARCHAR(MAX) ,@EURName NVARCHAR(MAX) ,@EURValue NVARCHAR(MAX) , @EURNominal NVARCHAR(MAX)
SELECT @USDCharCode = CharCode ,@USDName = Name ,@USDValue = Value ,@USDNominal = Nominal
FROM @tmp_currencyRates WHERE CharCode = 'USD'
SELECT @EURCharCode = CharCode ,@EURName = Name ,@EURValue = Value , @EURNominal = Nominal
FROM @tmp_currencyRates WHERE CharCode = 'EUR'
-- -- Курс 69,0151 за 1(Nominal) = Доллар США (Name)
-- SELECT 1
select 'Курс на ' + ISNULL( @valuteDate, '' )
+ ' ' + ISNULL( @USDCharCode, '' ) +' - '+ ISNULL( @USDName, '' ) +': '+ ISNULL( @USDValue , '' ) +'.'
+ ' ' + ISNULL( @EURCharCode, '' ) +' - '+ ISNULL( @EURName, '' ) +': '+ ISNULL( @EURValue , '' ) +'.'
AS Msg
, 1 Result, @response Response
-- SELECT 2 Внешние действия
END
Получение котировок валют через сайт www.cbr-xml-daily.ru
Сайт - https://www.cbr-xml-daily.ru/ предоставляет те же данные в разных форматах. В нашем случае будет получен ответ в формате JSON.
PROCEDURE [dbo].[api_currencyRatesCBRF_JSON_request]
Параметры запроса
- Адрес сервиса (URL): https://www.cbr-xml-daily.ru/daily_json.js
- Метод запроса: GET
- Формат на выходе: JSON
Входные данные запроса – нет.
Дата не передаётся, при необходимости получить исторические данные запрос будет иметь вид.
https://www.cbr-xml-daily.ru/archive/2020/06/02/daily_json.js
Примечание 1. В некоторых ситуациях, например, когда запрос отправлен вечером – актуальные данные на завтра (Дата в будущем).
Пример текста ответа - response.
Приведен с сокращениями.
{
"Date": "2020-06-06T11:30:00+03:00",
"PreviousDate": "2020-06-05T11:30:00+03:00",
"PreviousURL": "//www.cbr-xml-daily.ru/archive/2020/06/05/daily_json.js",
"Timestamp": "2020-06-05T16:00:00+03:00",
"Valute": {
…
"USD": {
"ID": "R01235",
"NumCode": "840",
"CharCode": "USD",
"Nominal": 1,
"Name": "Доллар США",
"Value": 68.6319,
"Previous": 69.0151
},
"EUR": {
"ID": "R01239",
"NumCode": "978",
"CharCode": "EUR",
"Nominal": 1,
"Name": "Евро",
"Value": 77.9658,
"Previous": 77.3245
},
…
}
}
CREATE PROCEDURE [dbo].[api_currencyRatesCBRF_JSON_request]
@parameters ExtendedDictionaryParameter READONLY, -- входящие параметры для внутренней обработки (используйте Key, Value2)
@username nvarchar(32) -- текущий пользователь.
AS
BEGIN
DECLARE @apiUrl nvarchar(max) = '' -- Финальная строка для отправки -- @apiStr -- ФАКТИЧЕСКИ ЭТО Url
SET @apiUrl = 'https://www.cbr-xml-daily.ru/daily_json.js'
-- История курсов можно брать в архиве https://www.cbr-xml-daily.ru/archive/2020/06/02/daily_json.js
-- ОТЛАДКА
insert into as_trace ( header, text, username, code , created ) values( '@apiUrl', @apiUrl , @username, 'api_currencyRatesCBRF_JSON_request' , GETDATE() )
-- SELECT 1 Msg, Result, Url (адрес, куда будет идти запрос)
select '' Msg, 1 Result, @apiUrl Url
-- SELECT 2 PARAMETERS - параметры, которые будут передаваться во внешний источник
-- select 'id' name, '5' value, '' [type] -- form (в форме передается), header (в http headers), get запросы передавайте прямо в URL
END
PROCEDURE [dbo].[api_currencyRatesCBRF_JSON_response]
Результат запроса может быть как сообщение с информацией, так и сообщение с ошибкой.
Список возможных сообщений об ошибках.
- 1 - 'Ошибка! Строка @response не является JSON!' (Проверка ответа оператором ISJSON() ).
- 2 – 'Ошибка! Запрос @response вернул ошибку! ' @errorText '. code: ' @errorcode '. explanation: ' @errorexplanation. Если в тексте ответа присутствуют поля: error, code, explanation.
Если ошибок в ответе не обнаружено, из ответа выбираются такие данные:
Курс Доллар США и Евро.
Пример текста – результат: Курс на 06.06.2020 USD - Доллар США: 68,6319. EUR - Евро: 77,9658.
CREATE PROCEDURE [dbo].[api_currencyRatesCBRF_JSON_response]
@response nvarchar(max),
@parameters ExtendedDictionaryParameter READONLY, -- входящие параметры для внутренней обработки (используйте Key, Value2 - те же что и на request)
@username nvarchar(32)
AS
BEGIN
-- ОТЛАДКА
insert into as_trace ( header, text, username, code , created ) values( '@response - 1 , 1024 ', SUBSTRING ( @response , 1 , 1024 ) , @username, 'api_currencyRatesCBRF_JSON_response' , GETDATE() )
DECLARE @json1 NVARCHAR(MAX) = N''
SET @json1 = @response
-- Для проверки правильности JSON формата существует функция ISJSON, которая возвращает 1, если это JSON, 0 — если нет и NULL, если был передан NULL
DECLARE @presentJSON bit = 0
SELECT @presentJSON = ISNULL( ISJSON( @json1 ) , 0 )
IF @presentJSON <> 1
BEGIN
SELECT 'Ошибка! Строка @response не является JSON!' Msg, 0 Result, @response Response
RETURN
END
-- Обработка ошибки в ответе
DECLARE @presentError bit = 0 , @errorText NVARCHAR(MAX) , @errorcode NVARCHAR(MAX) , @errorexplanation NVARCHAR(MAX)
-- Данные
,@valuteDate NVARCHAR(16)
,@USDCharCode NVARCHAR(MAX) ,@USDName NVARCHAR(MAX) ,@USDValue NVARCHAR(MAX)
,@EURCharCode NVARCHAR(MAX) ,@EURName NVARCHAR(MAX) ,@EURValue NVARCHAR(MAX)
SELECT @presentError = IIF( JSON_VALUE( @json1, '$.error') IS NULL , 0 , 1 )
, @errorText = JSON_VALUE( @json1, '$.error')
, @errorcode = JSON_VALUE( @json1, '$.code')
, @errorexplanation= JSON_VALUE( @json1, '$.explanation')
-- Данные
, @valuteDate = JSON_VALUE( @json1, '$.Date')
, @USDCharCode = JSON_VALUE( @json1, '$.Valute.USD.CharCode')
, @USDName = JSON_VALUE( @json1, '$.Valute.USD.Name')
, @USDValue = JSON_VALUE( @json1, '$.Valute.USD.Value')
, @EURCharCode = JSON_VALUE( @json1, '$.Valute.EUR.CharCode')
, @EURName = JSON_VALUE( @json1, '$.Valute.EUR.Name')
, @EURValue = JSON_VALUE( @json1, '$.Valute.EUR.Value')
IF @presentError = 1
BEGIN
SELECT 'Ошибка! Запрос @response вернул ошибку! '+ ISNULL( @errorText, '' ) + '. code: ' +ISNULL( @errorcode, '' )+ '. explanation: ' +ISNULL( @errorexplanation, '' )AS Msg
, 0 Result, @response Response
RETURN
END
-- SELECT 1
select 'Курс на ' + ISNULL( @valuteDate, '' )
+ ' ' + ISNULL( @USDCharCode, '' ) +' - '+ ISNULL( @USDName, '' ) +': '+ ISNULL( @USDValue , '' ) +'.'
+ ' ' + ISNULL( @EURCharCode, '' ) +' - '+ ISNULL( @EURName, '' ) +': '+ ISNULL( @EURValue , '' ) +'.'
AS Msg
, 1 Result, @response Response
-- SELECT 2 Внешние действия
END
Проверка - Официальные курсы валют на заданную дату, устанавливаемые ежедневно
https://www.cbr.ru/currency_base/daily/
Заключение
Таким образом довольно легко получать данные и с других источников по аналогии - создаем запрос request к внешнему API, платформа выполняет запрос, а затем происходит обработка результата в процедуре response.
По данной схеме можно внедрить практически любой API, работающий с GET/POST запросами.
Google поиск по нашей документации
- Руководства
- Основа Falcon Space
- Основные компоненты
- Возможности
- Коммуникация с пользователем
- Дизайн, стилизация
- API, Интеграции Создание сервиса API для сайта. Программный интерфейс веб-платформы Как сделать вебхук (webhook) Прием платежей через Яндекс.Кассу Онлайн-платежи. Интеграция с Робокассой (платежный шлюз) Zapier интеграция на платформе Falcon Space Интеграция API DaData.ru подсказки по адресам Интеграция коллтрекинга МАНГО ОФИС (режим Площадка) Интеграция API Курсы валют Центрального Банка РФ в веб-платформе Falcon Space Интеграция API Почта РФ Интеграция API Служба доставки СДЭК (CDEK) Интеграция API Служба доставки Деловые линии Интеграция API IpGeoBase Город по IP-адресу Интеграция импорт и парсинг файла CSV Интеграция API DaData.ru Город по IP-адресу Как вычислить расстояние между 2 точками с координатами через Google Maps Передача файлов по FTP Сканирование штрихкодов и QR кодов через камеру и с картинок Получение данных контрагента по ИНН Прием платежей на сайте через CloudPayments Программное взаимодействие через API между 2 разными экземплярами Falcon Как сделать интеграцию с Мой Склад Внедрение подсказок dadata на сайт Вывод точек на карте Яндекс. Интеграция с Яндекс Карты Интеграция с телефонией Zadarma.com Как передать скрытый параметр при исходящем запросе из Request процедуры в Response Получение данных о контрагенте - интеграция с сервисом ЗаЧестныйБизнес Интеграция с AMO CRM Как импортировать данные в базу CRM из Google Контакты Вход/регистрация через ВКонтакте(vk.com) Интеграция CRM с онлайн чатом на сайте (Replain) Загрузка на форме текстовых файлов и обработка их в процедуре SaveItem Как связать yandex metrika clientID с пользователем на сайте и посмотреть полный путь его по сайту? Входящий API. Как учесть в отклике результат внешних действий в API
- Каталоги
- Навигация
- Документы
- Дополнительные компоненты
- Продвижение, SEO
- Системные моменты
- HOWTO
- HOWTO Таблицы
- HOWTO Формы
- Работа с SQL
- HOWTO JS
- HOWTO Верстка
- Решение проблем
Falcon Space
Это снижение стоимости владения
за счет меньшего количества людей для поддержки и узкого стека разработки. Про снижение стоимости владения продуктом
Это быстрое внесение изменений
по ходу эксплуатации программы. Как создается функционал на платформе
Это простой удобный интерфейс
адаптация под мобильные устройства. Про юзабилити платформы