remove log components, just format directly with fmtlib

This commit is contained in:
mat 2023-12-25 15:18:38 -03:00
parent d76c40e981
commit c57db81910
8 changed files with 107 additions and 243 deletions

View file

@ -81,7 +81,7 @@ if (PROJECT_IS_TOP_LEVEL AND NOT GEODE_BUILDING_DOCS)
set(MAT_JSON_AS_INTERFACE ON)
endif()
CPMAddPackage("gh:geode-sdk/json#a47f570")
CPMAddPackage("gh:fmtlib/fmt#9.1.0")
CPMAddPackage("gh:fmtlib/fmt#10.1.1")
CPMAddPackage("gh:gulrak/filesystem#3e5b930")
target_compile_definitions(${PROJECT_NAME} INTERFACE MAT_JSON_DYNAMIC=1)

View file

@ -12,156 +12,81 @@
#include <vector>
#include <span>
#include <fmt/core.h>
namespace cocos2d {
GEODE_DLL std::string format_as(cocos2d::CCArray*);
GEODE_DLL std::string format_as(cocos2d::ccColor3B const&);
GEODE_DLL std::string format_as(cocos2d::ccColor4B const&);
GEODE_DLL std::string format_as(cocos2d::ccColor4F const&);
GEODE_DLL std::string format_as(cocos2d::CCNode*);
GEODE_DLL std::string format_as(cocos2d::CCObject*);
GEODE_DLL std::string format_as(cocos2d::CCPoint const&);
GEODE_DLL std::string format_as(cocos2d::CCRect const&);
GEODE_DLL std::string format_as(cocos2d::CCSize const&);
}
namespace gd {
inline std::string format_as(gd::string const& value) {
return value;
}
}
namespace ghc::filesystem {
inline std::string format_as(ghc::filesystem::path const& value) {
return value.string();
}
}
namespace geode {
#pragma warning(disable : 4251)
class Mod;
Mod* getMod();
GEODE_DLL std::string format_as(Mod*);
namespace log {
using log_clock = std::chrono::system_clock;
GEODE_DLL std::string generateLogName();
// Parse overloads
GEODE_DLL std::string parse(cocos2d::CCArray*);
GEODE_DLL std::string parse(cocos2d::ccColor3B const&);
GEODE_DLL std::string parse(cocos2d::ccColor4B const&);
GEODE_DLL std::string parse(cocos2d::ccColor4F const&);
GEODE_DLL std::string parse(cocos2d::CCNode*);
GEODE_DLL std::string parse(cocos2d::CCObject*);
GEODE_DLL std::string parse(cocos2d::CCPoint const&);
GEODE_DLL std::string parse(cocos2d::CCRect const&);
GEODE_DLL std::string parse(cocos2d::CCSize const&);
GEODE_DLL std::string parse(Mod*);
GEODE_DLL std::string parse(gd::string const&);
template <class T>
requires std::convertible_to<T*, cocos2d::CCNode*>
std::string parse(T* node) {
return parse(static_cast<cocos2d::CCNode*>(node));
}
template <class T>
requires(
std::convertible_to<T*, cocos2d::CCObject*> &&
!std::convertible_to<T*, cocos2d::CCNode*>
)
std::string parse(T* node) {
return parse(static_cast<cocos2d::CCObject*>(node));
}
template <typename T>
requires requires(T b) {
std::stringstream() << b;
}
std::string parse(T const& thing) {
std::stringstream buf;
buf << thing;
return buf.str();
}
// todo: maybe add a debugParse function for these?
template <class T>
requires requires(T t) {
parse(t);
}
std::string parse(std::optional<T> const& thing) {
if (thing.has_value()) {
return "opt(" + parse(thing.value()) + ")";
}
return "nullopt";
}
template <class T>
requires requires(T t) {
parse(t);
}
std::string parse(std::vector<T> const& thing) {
std::string res = "[";
bool first = true;
for (auto& t : thing) {
if (!first) {
res += ", ";
}
first = false;
res += parse(t);
}
res += "]";
return res;
}
template <class A, class B>
requires requires(A a, B b) {
parse(a);
parse(b);
}
std::string parse(std::pair<A, B> const& thing) {
return "(" + parse(thing.first) + ", " + parse(thing.second) + ")";
}
template <class... T, std::size_t... Is>
std::string parseTupleImpl(std::tuple<T...> const& tuple, std::index_sequence<Is...>) {
std::string ret = "(";
((ret += (Is == 0 ? "" : ", ") + parse(std::get<Is>(tuple))), ...);
ret += ")";
return ret;
}
template <class... T>
requires requires(T... t) {
(parse(t), ...);
}
std::string parse(std::tuple<T...> const& tuple) {
return parseTupleImpl(tuple, std::index_sequence_for<T...> {});
}
// Log component system
struct GEODE_DLL ComponentTrait {
virtual ~ComponentTrait() {}
virtual std::string _toString() = 0;
};
template <typename T>
struct ComponentBase : public ComponentTrait {
T m_item;
inline ~ComponentBase() override {}
inline ComponentBase(T const& item) : m_item(item) {}
// specialization must implement
inline std::string _toString() override {
return parse(m_item);
}
};
// template <class T>
// requires std::convertible_to<T*, cocos2d::CCNode*>
// std::string serialize(T* node) {
// return serialize(static_cast<cocos2d::CCNode*>(node));
// }
// template <class T>
// requires(
// std::convertible_to<T*, cocos2d::CCObject*> &&
// !std::convertible_to<T*, cocos2d::CCNode*>
// )
// std::string serialize(T* node) {
// return serialize(static_cast<cocos2d::CCObject*>(node));
// }
// Log
class GEODE_DLL Log final {
Mod* m_sender;
log_clock::time_point m_time;
std::vector<ComponentTrait*> m_components;
Severity m_severity;
std::string m_content;
friend class Logger;
public:
~Log();
Log(Mod* mod, Severity sev);
Log(Severity sev, Mod* mod, std::string content);
Log(Log&& l) = default;
Log& operator=(Log&& l) = default;
bool operator==(Log const& l);
// bool operator==(Log const& l) const;
std::string toString(bool logTime = true) const;
std::string toString(bool logTime, uint32_t nestLevel) const;
std::vector<ComponentTrait*>& getComponents();
std::string const& getContent() const;
log_clock::time_point getTime() const;
Mod* getSender() const;
Severity getSeverity() const;
Result<> addFormat(std::string_view formatStr, std::span<ComponentTrait*> comps);
};
class GEODE_DLL Logger {
@ -187,42 +112,31 @@ namespace geode {
static void clear();
};
GEODE_DLL void vlogImpl(Severity, Mod*, fmt::string_view format, fmt::format_args args);
template <typename... Args>
requires requires(Args... b) {
(parse(b), ...);
}
void internalLog(Severity sev, Mod* m, std::string_view formatStr, Args... args) {
Log l(m, sev);
std::array<ComponentTrait*, sizeof...(Args)> comps = { static_cast<ComponentTrait*>(new ComponentBase(args))... };
auto res = l.addFormat(formatStr, comps);
if (res.isErr()) {
internalLog(Severity::Warning, getMod(), "Error parsing log format \"{}\": {}", formatStr, res.unwrapErr());
return;
}
Logger::push(std::move(l));
inline void logImpl(Severity severity, Mod* mod, fmt::format_string<Args...> str, Args&&... args) {
vlogImpl(severity, mod, str, fmt::make_format_args(args...));
}
template <typename... Args>
void debug(Args... args) {
internalLog(Severity::Debug, getMod(), args...);
inline void debug(fmt::format_string<Args...> str, Args&&... args) {
logImpl(Severity::Debug, getMod(), str, std::forward<Args>(args)...);
}
template <typename... Args>
void info(Args... args) {
internalLog(Severity::Info, getMod(), args...);
inline void info(fmt::format_string<Args...> str, Args&&... args) {
logImpl(Severity::Info, getMod(), str, std::forward<Args>(args)...);
}
template <typename... Args>
void warn(Args... args) {
internalLog(Severity::Warning, getMod(), args...);
inline void warn(fmt::format_string<Args...> str, Args&&... args) {
logImpl(Severity::Warning, getMod(), str, std::forward<Args>(args)...);
}
template <typename... Args>
void error(Args... args) {
internalLog(Severity::Error, getMod(), args...);
inline void error(fmt::format_string<Args...> str, Args&&... args) {
logImpl(Severity::Error, getMod(), str, std::forward<Args>(args)...);
}
static void pushNest() {

View file

@ -179,8 +179,9 @@ namespace geode {
}
std::string toString(bool includeTag = true) const;
friend GEODE_DLL std::string format_as(VersionInfo const& version);
};
GEODE_DLL std::ostream& operator<<(std::ostream& stream, VersionInfo const& version);
class GEODE_DLL ComparableVersionInfo final {
protected:
@ -225,8 +226,8 @@ namespace geode {
}
std::string toString() const;
friend GEODE_DLL std::string format_as(ComparableVersionInfo const& version);
};
GEODE_DLL std::ostream& operator<<(std::ostream& stream, ComparableVersionInfo const& version);
}
template <class V>

View file

@ -455,7 +455,7 @@ void Loader::Impl::findProblems() {
log::debug("{} is not enabled", id);
continue;
}
log::debug(id);
log::debug("{}", id);
log::pushNest();
for (auto const& dep : mod->getMetadata().getDependencies()) {
@ -688,7 +688,7 @@ bool Loader::Impl::loadHooks() {
for (auto const& hook : m_uninitializedHooks) {
auto res = hook.second->addHook(hook.first);
if (!res) {
log::internalLog(Severity::Error, hook.second, "{}", res.unwrapErr());
log::logImpl(Severity::Error, hook.second, "{}", res.unwrapErr());
hadErrors = true;
}
}

View file

@ -15,7 +15,7 @@ using namespace cocos2d;
// Parse overloads
std::string log::parse(Mod* mod) {
std::string geode::format_as(Mod* mod) {
if (mod) {
return fmt::format("{{ Mod, {} }}", mod->getName());
}
@ -24,8 +24,9 @@ std::string log::parse(Mod* mod) {
}
}
std::string log::parse(CCObject* obj) {
std::string cocos2d::format_as(CCObject* obj) {
if (obj) {
// TODO: try catch incase typeid fails
return fmt::format("{{ {}, {} }}", typeid(*obj).name(), utils::intToHex(obj));
}
else {
@ -33,7 +34,7 @@ std::string log::parse(CCObject* obj) {
}
}
std::string log::parse(CCNode* obj) {
std::string cocos2d::format_as(CCNode* obj) {
if (obj) {
auto bb = obj->boundingBox();
return fmt::format(
@ -51,12 +52,12 @@ std::string log::parse(CCNode* obj) {
}
}
std::string log::parse(CCArray* arr) {
std::string cocos2d::format_as(CCArray* arr) {
std::string out = "[";
if (arr && arr->count()) {
for (int i = 0; i < arr->count(); ++i) {
out += parse(arr->objectAtIndex(i));
out += format_as(arr->objectAtIndex(i));
if (i < arr->count() - 1) out += ", ";
}
}
@ -65,47 +66,52 @@ std::string log::parse(CCArray* arr) {
return out + "]";
}
std::string log::parse(CCPoint const& pt) {
std::string cocos2d::format_as(CCPoint const& pt) {
return fmt::format("{}, {}", pt.x, pt.y);
}
std::string log::parse(CCSize const& sz) {
std::string cocos2d::format_as(CCSize const& sz) {
return fmt::format("{} : {}", sz.width, sz.height);
}
std::string log::parse(CCRect const& rect) {
return parse(rect.origin) + " | " + parse(rect.size);
std::string cocos2d::format_as(CCRect const& rect) {
return fmt::format("{} | {}", rect.origin, rect.size);
}
std::string log::parse(cocos2d::ccColor3B const& col) {
std::string cocos2d::format_as(cocos2d::ccColor3B const& col) {
return fmt::format("rgb({}, {}, {})", col.r, col.g, col.b);
}
std::string log::parse(cocos2d::ccColor4B const& col) {
std::string cocos2d::format_as(cocos2d::ccColor4B const& col) {
return fmt::format("rgba({}, {}, {}, {})", col.r, col.g, col.b, col.a);
}
std::string log::parse(gd::string const& str) {
return fmt::format("{}", std::string(str));
}
// Log
Log::Log(Mod* mod, Severity sev) : m_sender(mod), m_time(log_clock::now()), m_severity(sev) {}
void log::vlogImpl(Severity sev, Mod* mod, fmt::string_view format, fmt::format_args args) {
Log obj(sev, mod, fmt::vformat(format, args));
Logger::push(std::move(obj));
}
Log::Log(Severity sev, Mod* mod, std::string content) :
m_sender(mod),
m_time(log_clock::now()),
m_severity(sev),
m_content(std::move(content)) {}
Log::~Log() {
for (auto comp : m_components) {
delete comp;
}
}
bool Log::operator==(Log const& l) {
return this == &l;
}
// bool Log::operator==(Log const& l) {
// return this == &l;
// }
std::string Log::toString(bool logTime) const {
return toString(logTime, 0);
}
std::string Log::toString(bool logTime, uint32_t nestLevel) const {
std::string res;
@ -149,17 +155,11 @@ std::string Log::toString(bool logTime, uint32_t nestLevel) const {
res += " ";
}
for (auto& i : m_components) {
res += i->_toString();
}
res += m_content;
return res;
}
std::vector<ComponentTrait*>& Log::getComponents() {
return m_components;
}
log_clock::time_point Log::getTime() const {
return m_time;
}
@ -172,59 +172,6 @@ Severity Log::getSeverity() const {
return m_severity;
}
Result<> Log::addFormat(std::string_view formatStr, std::span<ComponentTrait*> components) {
size_t compIndex = 0;
std::string current;
for (size_t i = 0; i < formatStr.size(); ++i) {
if (formatStr[i] == '{') {
if (i == formatStr.size() - 1) {
return Err("Unescaped { at the end of format string");
}
auto const next = formatStr[i + 1];
if (next == '{') {
current.push_back('{');
++i;
continue;
}
if (next == '}') {
if (compIndex >= components.size()) {
return Err("Not enough arguments for format string");
}
m_components.push_back(new ComponentBase(current));
m_components.push_back(components[compIndex++]);
current.clear();
++i;
continue;
}
return Err("You put something in between {} silly head");
}
if (formatStr[i] == '}') {
if (i == formatStr.size() - 1) {
return Err("Unescaped } at the end of format string");
}
if (formatStr[i + 1] == '}') {
current.push_back('}');
++i;
continue;
}
return Err("You have an unescaped }");
}
current.push_back(formatStr[i]);
}
if (!current.empty())
m_components.push_back(new ComponentBase(current));
if (compIndex != components.size()) {
return Err("You have left over arguments.. silly head");
}
return Ok();
}
// Logger
std::vector<Log>& Logger::logs() {
@ -256,7 +203,9 @@ void Logger::push(Log&& log) {
}
void Logger::pop(Log* log) {
geode::utils::ranges::remove(Logger::logs(), *log);
geode::utils::ranges::remove(Logger::logs(), [&](auto& elem) {
return &elem == log;
});
}
void Logger::pushNest() {

View file

@ -158,7 +158,7 @@ Result<> Mod::Impl::loadData() {
if (auto setting = this->getSetting(key)) {
// load its value
if (!setting->load(value.json())) {
log::internalLog(
log::logImpl(
Severity::Error,
m_self,
"{}: Unable to load value for setting \"{}\"",
@ -168,7 +168,7 @@ Result<> Mod::Impl::loadData() {
}
}
else {
log::internalLog(
log::logImpl(
Severity::Warning,
m_self,
"Encountered unknown setting \"{}\" while loading "
@ -215,7 +215,7 @@ Result<> Mod::Impl::saveData() {
for (auto& [key, value] : m_settings) {
coveredSettings.insert(key);
if (!value->save(json[key])) {
log::error("Unable to save setting \"" + key + "\"");
log::error("Unable to save setting \"{}\"", key);
}
}

View file

@ -320,7 +320,7 @@ struct MDParser {
default:
{
log::warn("Unhandled text type {}", type);
log::warn("Unhandled text type {}", static_cast<int>(type));
}
break;
}
@ -413,7 +413,7 @@ struct MDParser {
default:
{
log::warn("Unhandled block enter type {}", type);
log::warn("Unhandled block enter type {}", static_cast<int>(type));
}
break;
}
@ -516,7 +516,7 @@ struct MDParser {
default:
{
log::warn("Unhandled block leave type {}", type);
log::warn("Unhandled block leave type {}", static_cast<int>(type));
}
break;
}
@ -573,7 +573,7 @@ struct MDParser {
default:
{
log::warn("Unhandled span enter type {}", type);
log::warn("Unhandled span enter type {}", static_cast<int>(type));
}
break;
}
@ -627,7 +627,7 @@ struct MDParser {
default:
{
log::warn("Unhandled span leave type {}", type);
log::warn("Unhandled span leave type {}", static_cast<int>(type));
}
break;
}

View file

@ -124,8 +124,8 @@ std::string VersionInfo::toString(bool includeTag) const {
return fmt::format("v{}.{}.{}", m_major, m_minor, m_patch);
}
std::ostream& geode::operator<<(std::ostream& stream, VersionInfo const& version) {
return stream << version.toString();
std::string geode::format_as(VersionInfo const& version) {
return version.toString();
}
// ComparableVersionInfo
@ -179,6 +179,6 @@ std::string ComparableVersionInfo::toString() const {
return prefix + m_version.toString();
}
std::ostream& geode::operator<<(std::ostream& stream, ComparableVersionInfo const& version) {
return stream << version.toString();
std::string geode::format_as(ComparableVersionInfo const& version) {
return version.toString();
}