From a54261a5831aa9a091846fc477da5c703e3370a3 Mon Sep 17 00:00:00 2001 From: Anatoly Kalin Date: Mon, 20 Nov 2023 18:08:35 +0300 Subject: [PATCH] [EN-8147] Add the ability to accept IPF URI as a symbols' source. --- .../isolated/Isolated.hpp | 18 +++++++++------ src/internal/Isolate.cpp | 23 +++++++++++++++++++ src/internal/utils/CmdArgsUtils.cpp | 12 +++++++--- tools/Tools/src/Args/Args.cpp | 4 ++-- 4 files changed, 45 insertions(+), 12 deletions(-) diff --git a/include/dxfeed_graal_cpp_api/isolated/Isolated.hpp b/include/dxfeed_graal_cpp_api/isolated/Isolated.hpp index 4c64242f..e87fa6b5 100644 --- a/include/dxfeed_graal_cpp_api/isolated/Isolated.hpp +++ b/include/dxfeed_graal_cpp_api/isolated/Isolated.hpp @@ -15,12 +15,16 @@ struct StringList { }; struct TimeFormat { - static /* dxfg_time_format_t* */ void* getDefault() noexcept; - static /* dxfg_time_format_t* */ void* getGmt() noexcept; - static /* dxfg_time_format_t* */ void* withTimeZone(/* dxfg_time_format_t* */ void* timeFormat) noexcept; - static /* dxfg_time_format_t* */ void* withMillis(/* dxfg_time_format_t* */ void* timeFormat) noexcept; - static std::int64_t parse(/* dxfg_time_format_t* */ void* timeFormat, const std::string& value) noexcept; - static std::string format(/* dxfg_time_format_t* */ void* timeFormat, std::int64_t value) noexcept; + static /* dxfg_time_format_t* */ void *getDefault() noexcept; + static /* dxfg_time_format_t* */ void *getGmt() noexcept; + static /* dxfg_time_format_t* */ void *withTimeZone(/* dxfg_time_format_t* */ void *timeFormat) noexcept; + static /* dxfg_time_format_t* */ void *withMillis(/* dxfg_time_format_t* */ void *timeFormat) noexcept; + static std::int64_t parse(/* dxfg_time_format_t* */ void *timeFormat, const std::string &value) noexcept; + static std::string format(/* dxfg_time_format_t* */ void *timeFormat, std::int64_t value) noexcept; +}; + +struct Tools { + static std::unordered_set /* dxfg_string_list* */ parseSymbols(const std::string &symbolList) noexcept; }; namespace api { @@ -62,7 +66,7 @@ struct InstrumentProfileCollector { static bool addUpdateListener(/* dxfg_ipf_collector_t* */ void *instrumentProfileCollectorHandle, /* dxfg_ipf_update_listener_t* */ void *listener) noexcept; static bool removeUpdateListener(/* dxfg_ipf_collector_t* */ void *instrumentProfileCollectorHandle, - /* dxfg_ipf_update_listener_t* */ void *listener) noexcept; + /* dxfg_ipf_update_listener_t* */ void *listener) noexcept; }; struct InstrumentProfileConnection { diff --git a/src/internal/Isolate.cpp b/src/internal/Isolate.cpp index c1c8f30b..2d62a06e 100644 --- a/src/internal/Isolate.cpp +++ b/src/internal/Isolate.cpp @@ -243,6 +243,29 @@ std::string TimeFormat::format(/* dxfg_time_format_t* */ void *timeFormat, std:: return result; } +std::unordered_set /* dxfg_string_list* */ +Tools::parseSymbols(const std::string &symbolList) noexcept { + std::unordered_set result{}; + + auto graalStringList = runIsolatedOrElse( + [](auto threadHandle, auto &&symbolList) { + return dxfg_Tools_parseSymbols(dxfcpp::bit_cast(threadHandle), symbolList.c_str()); + }, + nullptr, symbolList); + + if (!graalStringList) { + return result; + } + + for (auto i = 0; i < graalStringList->size; i++) { + result.emplace(dxfcpp::toString(graalStringList->elements[i])); + } + + StringList::release(graalStringList); + + return result; +} + namespace api { static dxfcpp::DXEndpoint::State graalStateToState(dxfg_endpoint_state_t state) { diff --git a/src/internal/utils/CmdArgsUtils.cpp b/src/internal/utils/CmdArgsUtils.cpp index ea5a839c..a3b2e934 100644 --- a/src/internal/utils/CmdArgsUtils.cpp +++ b/src/internal/utils/CmdArgsUtils.cpp @@ -9,13 +9,13 @@ #include #include #include +#include #include #include #include #include #include #include -#include #include #include @@ -131,7 +131,7 @@ std::unordered_set CmdArgsUtils::parseSymbols(const std::string & return {}; } - auto parsed = parseStringSymbols(trimmedSymbols); + auto parsed = isolated::Tools::parseSymbols(trimmedSymbols); if (parsed.contains("*") || parsed.contains("all") || parsed.contains("All") || parsed.contains("ALL")) { return {WildcardSymbol::ALL}; @@ -141,7 +141,13 @@ std::unordered_set CmdArgsUtils::parseSymbols(const std::string & } std::unordered_set CmdArgsUtils::parseCandleSymbols(const std::string &symbols) noexcept { - auto parsed = parseStringSymbols(symbols); + auto trimmedSymbols = trimStr(symbols); + + if (trimmedSymbols.empty()) { + return {}; + } + + auto parsed = isolated::Tools::parseSymbols(trimmedSymbols); return parsed | ranges::views::transform([](auto &&s) { return CandleSymbol::valueOf(s); diff --git a/tools/Tools/src/Args/Args.cpp b/tools/Tools/src/Args/Args.cpp index 7ba4d8da..50690da6 100644 --- a/tools/Tools/src/Args/Args.cpp +++ b/tools/Tools/src/Args/Args.cpp @@ -23,8 +23,8 @@ const std::string SymbolsArg::NAME{"symbols"}; const std::size_t SymbolsArg::POSITION{2}; const std::string SymbolsArg::HELP_TEXT{R"( Comma-separated list of symbol names to get events for (e.g. "IBM, AAPL, MSFT"). -Use "all" for wildcard subscription. -The "dxfeed.wildcard.enable" property must be set to true to enable wildcard subscription. +Use "all" for wildcard subscription. The "dxfeed.wildcard.enable" property must be set to true to enable wildcard subscription. +A symbol filter set format can also be used as symbols source, for example: "ipf[https://demo:demo@tools.dxfeed.com/ipf?TYPE=STOCK]" )"}; const std::string PropertiesArg::NAME{"properties"};