-
Notifications
You must be signed in to change notification settings - Fork 2
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
[MDAPI-211][C++] Implement logging management. (#64)
- Loading branch information
Showing
9 changed files
with
317 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
38 changes: 38 additions & 0 deletions
38
include/dxfeed_graal_cpp_api/isolated/logging/IsolatedLogging.hpp
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,38 @@ | ||
// Copyright (c) 2024 Devexperts LLC. | ||
// SPDX-License-Identifier: MPL-2.0 | ||
|
||
#pragma once | ||
|
||
#include "../../internal/Conf.hpp" | ||
|
||
#include "../../logging/Logging.hpp" | ||
#include "dxfeed_graal_cpp_api/internal/JavaObjectHandle.hpp" | ||
|
||
#include <cstdint> | ||
#include <string> | ||
#include <vector> | ||
|
||
DXFCXX_DISABLE_MSC_WARNINGS_PUSH(4251) | ||
|
||
DXFCPP_BEGIN_NAMESPACE | ||
|
||
namespace isolated::logging::IsolatedLogging { | ||
|
||
// int32_t dxfg_logging_listener_new(graal_isolatethread_t *thread, dxfg_logging_listener_function_t user_func, | ||
// void *user_data, DXFG_OUT dxfg_logging_listener_t **listener); | ||
JavaObjectHandle<Logging::ListenerTag> createListener(void* userFunc, void* userData); | ||
|
||
// int32_t dxfg_logging_set_listener(graal_isolatethread_t *thread, dxfg_logging_listener_t *listener); | ||
void setListener(const JavaObjectHandle<Logging::ListenerTag>& listener); | ||
|
||
//int32_t dxfg_logging_set_log_level(graal_isolatethread_t *thread, dxfg_logging_level_t level); | ||
void setLogLevel(Logging::Level level); | ||
|
||
//int32_t dxfg_logging_set_err_level(graal_isolatethread_t *thread, dxfg_logging_level_t level); | ||
void setErrFileLevel(Logging::Level level); | ||
|
||
} | ||
|
||
DXFCPP_END_NAMESPACE | ||
|
||
DXFCXX_DISABLE_MSC_WARNINGS_POP() |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,112 @@ | ||
// Copyright (c) 2024 Devexperts LLC. | ||
// SPDX-License-Identifier: MPL-2.0 | ||
|
||
#pragma once | ||
|
||
#include "../internal/Conf.hpp" | ||
#include "dxfeed_graal_cpp_api/internal/Handler.hpp" | ||
|
||
DXFCXX_DISABLE_MSC_WARNINGS_PUSH(4251) | ||
|
||
#include "../internal/Common.hpp" | ||
|
||
DXFCPP_BEGIN_NAMESPACE | ||
|
||
/** | ||
* | ||
*/ | ||
struct DXFCPP_EXPORT Logging final { | ||
struct ListenerTag {}; | ||
/** | ||
* Defines a set of standard logging levels that can be used to control logging output. | ||
*/ | ||
enum class Level { | ||
/// Indicates that all messages should be logged. | ||
ALL = 0, | ||
|
||
/// Indicates a highly detailed tracing message. | ||
TRACE, | ||
|
||
/// Is a message level providing tracing debug information. | ||
DEBUG, | ||
|
||
/// Is a message level for informational messages. | ||
INFO, | ||
|
||
/// Is a message level indicating a potential problem. | ||
WARN, | ||
|
||
/// Is a message level indicating a serious failure. | ||
ERROR, | ||
|
||
/// Is a special level that can be used to turn off logging. | ||
OFF, | ||
}; | ||
|
||
static std::string levelToString(Level level); | ||
|
||
private: | ||
static SimpleHandler<void(Level, std::int64_t /*timestamp*/, const std::string & /*threadName*/, | ||
std::int64_t /*threadId*/, const std::string & /*loggerName*/, | ||
const std::string & /*message*/)> | ||
handler_; | ||
|
||
struct Impl; | ||
|
||
public: | ||
/** | ||
* Initializes logging and sets the logging level. | ||
* | ||
* This is equivalent to the following code: | ||
* | ||
* ```cpp | ||
* System::setProperty("log.className", "com.devexperts.logging.InterceptableLogging"); | ||
* System::setProperty("log.level", levelToString(level)); | ||
* System::setProperty("err.level", levelToString(level)); | ||
* ``` | ||
* @param level The logging level. | ||
*/ | ||
static void init(Level level = Level::OFF); | ||
|
||
/** | ||
* Initializes logging, sets the path to the logging file and the logging level. | ||
* | ||
* This is equivalent to the following code: | ||
* | ||
* ```cpp | ||
* System::setProperty("log.className", "com.devexperts.logging.InterceptableLogging"); | ||
* System::setProperty("log.file", logFile); | ||
* System::setProperty("log.level", levelToString(logLevel)); | ||
* ``` | ||
* | ||
* @param logFile The logging file. | ||
* @param logLevel The logging level. | ||
*/ | ||
static void init(const std::string &logFile, Level logLevel = Level::INFO); | ||
|
||
/** | ||
* Initializes logging, sets the path to the file for logging, to the file for outputting errors and warnings, and | ||
* sets the logging level for both files. | ||
* | ||
* This is equivalent to the following code: | ||
* | ||
* ```cpp | ||
* System::setProperty("log.className", "com.devexperts.logging.InterceptableLogging"); | ||
* System::setProperty("log.file", logFile); | ||
* System::setProperty("log.level", levelToString(logLevel)); | ||
* System::setProperty("err.file", errFile); | ||
* System::setProperty("err.level", levelToString(errFileLevel)); | ||
* ``` | ||
* | ||
* @param logFile The logging file. | ||
* @param errFile The err file. | ||
* @param logLevel The logging level. | ||
* @param errFileLevel The err file logging level. | ||
*/ | ||
static void init(const std::string &logFile, const std::string &errFile, Level logLevel = Level::INFO, | ||
Level errFileLevel = Level::WARN); | ||
}; | ||
|
||
DXFCPP_END_NAMESPACE | ||
|
||
DXFCXX_DISABLE_MSC_WARNINGS_POP() |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,54 @@ | ||
// Copyright (c) 2024 Devexperts LLC. | ||
// SPDX-License-Identifier: MPL-2.0 | ||
|
||
#include <dxfg_api.h> | ||
|
||
#include <dxfeed_graal_cpp_api/isolated/IsolatedCommon.hpp> | ||
#include <dxfeed_graal_cpp_api/isolated/internal/IsolatedString.hpp> | ||
#include <dxfeed_graal_cpp_api/isolated/logging/IsolatedLogging.hpp> | ||
|
||
DXFCPP_BEGIN_NAMESPACE | ||
|
||
namespace isolated::logging::IsolatedLogging { | ||
|
||
// int32_t dxfg_logging_listener_new(graal_isolatethread_t *thread, dxfg_logging_listener_function_t user_func, | ||
// void *user_data, DXFG_OUT dxfg_logging_listener_t **listener); | ||
JavaObjectHandle<Logging::ListenerTag> createListener(void *userFunc, void *userData) { | ||
if (!userFunc) { | ||
throw InvalidArgumentException("Unable to execute function `dxfg_logging_listener_new`. The " | ||
"`userFunc` is nullptr"); | ||
} | ||
|
||
dxfg_logging_listener_t *isolatedListener{}; | ||
|
||
runGraalFunctionAndThrowIfMinusOne(dxfg_logging_listener_new, | ||
dxfcpp::bit_cast<dxfg_logging_listener_function_t>(userFunc), userData, | ||
&isolatedListener); | ||
|
||
return JavaObjectHandle<Logging::ListenerTag>(isolatedListener); | ||
} | ||
|
||
// int32_t dxfg_logging_set_listener(graal_isolatethread_t *thread, dxfg_logging_listener_t *listener); | ||
void setListener(const JavaObjectHandle<Logging::ListenerTag> &listener) { | ||
if (!listener) { | ||
throw InvalidArgumentException("Unable to execute function `dxfg_logging_set_listener`. The " | ||
"`listener` handle is invalid"); | ||
} | ||
|
||
runGraalFunctionAndThrowIfMinusOne(dxfg_logging_set_listener, | ||
dxfcpp::bit_cast<dxfg_logging_listener_t *>(listener.get())); | ||
} | ||
|
||
// int32_t dxfg_logging_set_log_level(graal_isolatethread_t *thread, dxfg_logging_level_t level); | ||
void setLogLevel(Logging::Level level) { | ||
runGraalFunctionAndThrowIfMinusOne(dxfg_logging_set_log_level, static_cast<dxfg_logging_level_t>(level)); | ||
} | ||
|
||
// int32_t dxfg_logging_set_err_level(graal_isolatethread_t *thread, dxfg_logging_level_t level); | ||
void setErrFileLevel(Logging::Level level) { | ||
runGraalFunctionAndThrowIfMinusOne(dxfg_logging_set_err_level, static_cast<dxfg_logging_level_t>(level)); | ||
} | ||
|
||
} // namespace isolated::logging::IsolatedLogging | ||
|
||
DXFCPP_END_NAMESPACE |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,98 @@ | ||
// Copyright (c) 2024 Devexperts LLC. | ||
// SPDX-License-Identifier: MPL-2.0 | ||
|
||
#include <dxfeed_graal_cpp_api/logging/Logging.hpp> | ||
#include <dxfeed_graal_cpp_api/system/System.hpp> | ||
|
||
#include <dxfg_api.h> | ||
|
||
#include <dxfeed_graal_cpp_api/isolated/event/IsolatedEventType.hpp> | ||
#include <dxfeed_graal_cpp_api/isolated/internal/IsolatedObject.hpp> | ||
#include <dxfeed_graal_cpp_api/isolated/logging/IsolatedLogging.hpp> | ||
#include <utility> | ||
|
||
DXFCPP_BEGIN_NAMESPACE | ||
|
||
std::string Logging::levelToString(Level level) { | ||
switch (level) { | ||
case Level::ALL: | ||
return "ALL"; | ||
case Level::TRACE: | ||
return "TRACE"; | ||
case Level::DEBUG: | ||
return "DEBUG"; | ||
case Level::INFO: | ||
return "INFO"; | ||
case Level::WARN: | ||
return "WARN"; | ||
case Level::ERROR: | ||
return "ERROR"; | ||
case Level::OFF: | ||
return "OFF"; | ||
} | ||
|
||
return "UNKNOWN"; | ||
} | ||
|
||
SimpleHandler<void(Logging::Level, std::int64_t /*timestamp*/, const std::string & /*threadName*/, | ||
std::int64_t /*threadId*/, const std::string & /*loggerName*/, const std::string & /*message*/)> | ||
Logging::handler_{}; | ||
|
||
struct Logging::Impl { | ||
static JavaObjectHandle<Logging::ListenerTag> listenerHandle; | ||
|
||
static void onLog(graal_isolatethread_t * /*thread*/, dxfg_logging_level_t level, int64_t timestamp, | ||
const char *threadName, int64_t threadId, const char *loggerName, const char *message, | ||
dxfg_exception_t * /*exception*/, const char * /*formattedMessage*/, void * /*userData*/) { | ||
handler_(static_cast<Level>(level), timestamp, threadName, threadId, loggerName, message); | ||
} | ||
}; | ||
|
||
JavaObjectHandle<Logging::ListenerTag> Logging::Impl::listenerHandle{}; | ||
|
||
void Logging::init(Level level) { | ||
System::setProperty("log.className", "com.devexperts.logging.InterceptableLogging"); | ||
System::setProperty("log.level", levelToString(level)); | ||
System::setProperty("err.level", levelToString(level)); | ||
} | ||
|
||
void Logging::init(const std::string &logFile, Level logLevel) { | ||
System::setProperty("log.className", "com.devexperts.logging.InterceptableLogging"); | ||
System::setProperty("log.file", logFile); | ||
System::setProperty("log.level", levelToString(logLevel)); | ||
} | ||
|
||
void Logging::init(const std::string &logFile, const std::string &errFile, Level logLevel, Level errFileLevel) { | ||
System::setProperty("log.className", "com.devexperts.logging.InterceptableLogging"); | ||
System::setProperty("log.file", logFile); | ||
System::setProperty("log.level", levelToString(logLevel)); | ||
System::setProperty("err.file", errFile); | ||
System::setProperty("err.level", levelToString(errFileLevel)); | ||
} | ||
|
||
// void Logging::setListener(std::function<void(Level, std::int64_t, const std::string &, std::int64_t, | ||
// const std::string &, const std::string &)> | ||
// listener) { | ||
// static auto id = static_cast<std::size_t>(-1); | ||
// | ||
// if (id != static_cast<std::size_t>(-1)) { | ||
// handler_ -= id; | ||
// } | ||
// | ||
// id = handler_ += std::move(listener); | ||
// | ||
// if (!Impl::listenerHandle) { | ||
// Impl::listenerHandle = | ||
// isolated::logging::IsolatedLogging::createListener(dxfcpp::bit_cast<void *>(&Impl::onLog), nullptr); | ||
// } | ||
// } | ||
// | ||
// void Logging::setLogLevel(Level level) { | ||
// isolated::logging::IsolatedLogging::setLogLevel(level); | ||
// } | ||
// | ||
// void Logging::setErrFileLevel(Level level) { | ||
// isolated::logging::IsolatedLogging::setErrFileLevel(level); | ||
// } | ||
|
||
DXFCPP_END_NAMESPACE |