基本Json格式化。

This commit is contained in:
2026-03-29 19:25:59 +08:00
parent 4c8cf346ea
commit 1bc2c2bcbf
10 changed files with 376 additions and 0 deletions

20
.clang-format Normal file
View File

@@ -0,0 +1,20 @@
BasedOnStyle: LLVM
IndentWidth: 4
PointerAlignment: Left
AccessModifierOffset: -4
ReflowComments: true
SpacesBeforeTrailingComments: 3
AllowShortFunctionsOnASingleLine: None
AllowShortEnumsOnASingleLine: false
BreakBeforeBraces: Custom
BraceWrapping:
AfterFunction: true
AfterClass: true
TabWidth: 4
ColumnLimit: 130
IncludeBlocks: Regroup
IncludeCategories:
- Regex: '^<.*>'
Priority: 1
- Regex: '^".*"'
Priority: 2

12
.clangd Normal file
View File

@@ -0,0 +1,12 @@
Hover:
ShowAKA: Yes
Diagnostics:
UnusedIncludes: None # 禁用未使用头文件提示
Suppress: [
anon_type_definition, # 禁用匿名的typedef提示
unused-variable, # 禁用未使用变量提示
unused-function, # 禁用未使用函数提示
unused-includes,
]
ClangTidy:
Remove: misc-unused-alias-decls

3
.gitignore vendored Normal file
View File

@@ -0,0 +1,3 @@
build/
.cache/
.lingma/

145
.vscode/settings.json vendored Normal file
View File

@@ -0,0 +1,145 @@
{
"files.autoSave": "onFocusChange",
"editor.fontSize": 14,
"editor.fontFamily": "'Mononoki Nerd Font Mono', 'Mononoki Nerd Font Mono', 'Mononoki Nerd Font Mono'",
"editor.wordWrap": "on",
"terminal.integrated.fontFamily": "'Mononoki Nerd Font Mono'",
"cmake.configureOnOpen": true,
//"C_Cpp.intelliSenseEngine": "disabled",
"cmake.debugConfig": {
"console": "externalTerminal",
"setupCommands": [
{
"description": "-gdb-set charset utf-8",
"text": "-gdb-set charset UTF-8"
},
{
"description": "Enable gdb pretty-printing",
"text": "-enable-pretty-printing",
"ignoreFailures": true
}
],
//"visualizerFile": "${workspaceRoot}/.vscode/qt6.natvis",
},
"cmake.configureArgs": [
"-Wno-dev"
],
"cmake.configureSettings": {
"CMAKE_PREFIX_PATH": "C:/local"
//"CXXLIBRARY_TEST": "ON"
},
"cmake.options.statusBarVisibility": "visible",
"cmake.generator": "Ninja",
"C_Cpp.default.compileCommands": "${workspaceRoot}/build/compile_commands.json",
"C_Cpp.default.cppStandard": "c++17",
"C_Cpp.default.configurationProvider": "ms-vscode.cmake-tools",
"editor.inlayHints.enabled": "off",
"editor.unicodeHighlight.allowedLocales": {
"ja": true,
"zh-hant": true,
"zh-hans": true
},
"files.associations": {
"*.cfg": "json",
"xstring": "cpp",
"algorithm": "cpp",
"array": "cpp",
"atomic": "cpp",
"cctype": "cpp",
"charconv": "cpp",
"chrono": "cpp",
"clocale": "cpp",
"cmath": "cpp",
"condition_variable": "cpp",
"cstddef": "cpp",
"cstdint": "cpp",
"cstdio": "cpp",
"cstdlib": "cpp",
"cstring": "cpp",
"ctime": "cpp",
"cwchar": "cpp",
"exception": "cpp",
"filesystem": "cpp",
"forward_list": "cpp",
"fstream": "cpp",
"functional": "cpp",
"initializer_list": "cpp",
"iomanip": "cpp",
"ios": "cpp",
"iosfwd": "cpp",
"iostream": "cpp",
"istream": "cpp",
"iterator": "cpp",
"limits": "cpp",
"list": "cpp",
"locale": "cpp",
"map": "cpp",
"memory": "cpp",
"mutex": "cpp",
"new": "cpp",
"optional": "cpp",
"ostream": "cpp",
"ratio": "cpp",
"sstream": "cpp",
"stdexcept": "cpp",
"streambuf": "cpp",
"string": "cpp",
"string_view": "cpp",
"system_error": "cpp",
"thread": "cpp",
"tuple": "cpp",
"type_traits": "cpp",
"typeinfo": "cpp",
"unordered_map": "cpp",
"utility": "cpp",
"vector": "cpp",
"xfacet": "cpp",
"xhash": "cpp",
"xiosbase": "cpp",
"xlocale": "cpp",
"xlocbuf": "cpp",
"xlocinfo": "cpp",
"xlocmes": "cpp",
"xlocmon": "cpp",
"xlocnum": "cpp",
"xloctime": "cpp",
"xmemory": "cpp",
"xmemory0": "cpp",
"xstddef": "cpp",
"xtr1common": "cpp",
"xtree": "cpp",
"xutility": "cpp",
"bit": "cpp",
"compare": "cpp",
"concepts": "cpp",
"coroutine": "cpp",
"format": "cpp",
"stop_token": "cpp",
"bitset": "cpp",
"complex": "cpp",
"cstdarg": "cpp",
"set": "cpp",
"variant": "cpp",
"expected": "cpp",
"source_location": "cpp",
"regex": "cpp",
"*.in": "cpp",
"deque": "cpp",
"future": "cpp",
"queue": "cpp",
"resumable": "cpp",
"any": "cpp",
"codecvt": "cpp",
"csignal": "cpp",
"cwctype": "cpp",
"memory_resource": "cpp",
"numeric": "cpp",
"random": "cpp",
"shared_mutex": "cpp",
"cinttypes": "cpp",
"cfenv": "cpp",
"unordered_set": "cpp",
"ranges": "cpp",
"typeindex": "cpp"
}
}

19
CMakeLists.txt Normal file
View File

@@ -0,0 +1,19 @@
cmake_minimum_required(VERSION 3.16)
project(aux_cmd LANGUAGES CXX)
set(CMAKE_CXX_STANDARD 17)
if (MSVC)
add_compile_options(/utf-8)
endif()
set(SOURCES
formater/fmt.json.h formater/fmt.json.cpp
util/axc.util.h util/axc.util.cpp
)
find_package(cxxLibrary CONFIG REQUIRED)
include_directories(${CMAKE_CURRENT_SOURCE_DIR})
add_executable(aux_cmd main.cpp ${SOURCES})
target_link_libraries(aux_cmd PRIVATE cxxLibrary::cxxLibrary)

45
formater/fmt.json.cpp Normal file
View File

@@ -0,0 +1,45 @@
#include "fmt.json.h"
#include <boost/nowide/fstream.hpp>
#include <iostream>
#include <nlohmann/json.hpp>
using json = nlohmann::json;
JsonFormatter::JsonFormatter()
{
}
std::string JsonFormatter::format(const std::string& path, const FormatterArg& arg)
{
std::string result;
boost::nowide::ifstream ifs(path);
if (!ifs.is_open())
return "";
std::string content((std::istreambuf_iterator<char>(ifs)), std::istreambuf_iterator<char>());
// std::cout << "Content: " << content << std::endl;
formatContent(content, arg, result);
return result;
}
bool JsonFormatter::formatContent(const std::string& content, const FormatterArg& arg, std::string& outContent)
{
try {
json j = json::parse(content);
outContent = j.dump(arg.indent);
return true;
} catch (json::parse_error& e) {
AxcUtil::getLogger()->error("Parse json content error: [{}], return default content.", e.what());
return false;
}
}
bool JsonFormatter::save(const std::string& path, const std::string& content)
{
boost::nowide::ofstream ofs(path);
if (!ofs.is_open())
return false;
ofs << content;
return true;
}

22
formater/fmt.json.h Normal file
View File

@@ -0,0 +1,22 @@
#ifndef FMT_JSON_H
#define FMT_JSON_H
#include <string>
#include "util/axc.util.h"
class JsonFormatter
{
public:
JsonFormatter();
public:
std::string format(const std::string& path, const FormatterArg& arg);
bool formatContent(const std::string& content, const FormatterArg& arg, std::string& outContent);
bool save(const std::string& path, const std::string& content);
private:
std::shared_ptr<spdlog::logger> logger;
};
#endif // FMT_JSON_H

52
main.cpp Normal file
View File

@@ -0,0 +1,52 @@
#include <CLI11.hpp>
#include <consoleapi2.h>
#include <iostream>
#include "formater/fmt.json.h"
#include "util/axc.util.h"
#include <zoost/zoost.h>
int main(int argc, char* argv[])
{
zoostCommon::SetOutputU8();
if (!AxcUtil::initLogger("aux_cmd.log")) {
std::cerr << "Failed to init logger." << std::endl;
return 1;
}
// AxcUtil::getLogger()->info("Starting...");
// 中文测试。
CLI::App app("A simple command line tool");
argv = app.ensure_utf8(argv);
FormatterArg formatArg;
try {
auto jsonSub = app.add_subcommand("json", "Json Operator.");
jsonSub->add_option("-i,--indent", formatArg.indent, "Indent size for json format");
jsonSub->add_option("-f,--file", formatArg.file, "format file.")->required()->check(CLI::ExistingFile);
app.parse(argc, argv);
if (jsonSub->parsed()) {
JsonFormatter jf;
auto content = jf.format(formatArg.file, formatArg);
if (content.empty()) {
AxcUtil::getLogger()->error("Failed to format json file.");
return 1;
}
if (!jf.save(formatArg.file, content)) {
AxcUtil::getLogger()->error("Failed to save json file.");
return 1;
} else {
AxcUtil::getLogger()->info("Json file saved successfully.");
}
}
} catch (const CLI::ParseError& e) {
return app.exit(e);
}
std::cout << "Hello, world! This is ..." << std::endl;
return 0;
}

39
util/axc.util.cpp Normal file
View File

@@ -0,0 +1,39 @@
#include "axc.util.h"
#include <boost/nowide/iostream.hpp>
#include <spdlog/common.h>
#include <spdlog/sinks/rotating_file_sink.h>
#include <spdlog/sinks/stdout_color_sinks.h>
#include <vector>
static std::shared_ptr<spdlog::logger> logger;
bool AxcUtil::initLogger(const std::string& logFile)
{
if (logger) {
return true;
}
try {
auto fileSink = std::make_shared<spdlog::sinks::rotating_file_sink_mt>("aux_cmd.log", 1024 * 1024 * 5, 3);
auto consoleSink = std::make_shared<spdlog::sinks::stdout_color_sink_mt>();
fileSink->set_pattern("[%Y-%m-%d %H:%M:%S.%e][%l]: %v");
consoleSink->set_pattern("[%H:%M:%S.%e] %^[%l] %v%$");
std::vector<spdlog::sink_ptr> sinks{fileSink, consoleSink};
logger = std::make_shared<spdlog::logger>("aux_cmd", sinks.begin(), sinks.end());
logger->set_level(spdlog::level::debug);
logger->flush_on(spdlog::level::debug);
spdlog::register_logger(logger);
} catch (const spdlog::spdlog_ex& ex) {
boost::nowide::cerr << "Error creating logger: " << ex.what() << std::endl;
return false;
}
return true;
}
std::shared_ptr<spdlog::logger> AxcUtil::getLogger()
{
if (!logger) {
logger = spdlog::get("aux_cmd");
}
return logger;
}

19
util/axc.util.h Normal file
View File

@@ -0,0 +1,19 @@
#ifndef AXC_UTIL_H
#define AXC_UTIL_H
#include <spdlog/spdlog.h>
#include <string>
struct FormatterArg {
int indent{4};
std::string file;
};
class AxcUtil
{
public:
static bool initLogger(const std::string& logFile);
static std::shared_ptr<spdlog::logger> getLogger();
};
#endif