dropshell release 2025.0518.1300
Some checks failed
Dropshell Test / Build_and_Test (push) Has been cancelled
Some checks failed
Dropshell Test / Build_and_Test (push) Has been cancelled
This commit is contained in:
@ -13,6 +13,7 @@
|
||||
#include "utils/b64ed.hpp"
|
||||
#include "config.hpp"
|
||||
#include "utils/directories.hpp"
|
||||
#include "utils/output.hpp"
|
||||
|
||||
namespace dropshell
|
||||
{
|
||||
@ -21,6 +22,10 @@ namespace dropshell
|
||||
return (ret != -1 && WIFEXITED(ret) && (WEXITSTATUS(ret) == 0)); // ret is -1 if the command failed to execute.
|
||||
}
|
||||
|
||||
|
||||
// ----------------------------------------------------------------------------------------------------------
|
||||
// execute_local_command_interactive
|
||||
// ----------------------------------------------------------------------------------------------------------
|
||||
bool execute_local_command_interactive(const sCommand &command)
|
||||
{
|
||||
if (command.get_command_to_run().empty())
|
||||
@ -51,6 +56,9 @@ namespace dropshell
|
||||
}
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------------------------------------
|
||||
// execute_local_command_and_capture_output
|
||||
// ----------------------------------------------------------------------------------------------------------
|
||||
bool execute_local_command_and_capture_output(const sCommand &command, std::string *output)
|
||||
{
|
||||
ASSERT(output != nullptr, "Output string must be provided");
|
||||
@ -71,6 +79,9 @@ namespace dropshell
|
||||
return EXITSTATUSCHECK(ret);
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------------------------------------
|
||||
// execute_local_command
|
||||
// ----------------------------------------------------------------------------------------------------------
|
||||
bool execute_local_command(std::string command, std::string *output, cMode mode)
|
||||
{
|
||||
return execute_local_command("", command, {}, output, mode);
|
||||
@ -100,17 +111,25 @@ namespace dropshell
|
||||
return false;
|
||||
bool silent = hasFlag(mode, cMode::Silent);
|
||||
std::string full_cmd = command.construct_cmd(localpath::agent()) + " 2>&1" + (silent ? " > /dev/null" : "");
|
||||
int ret = system(full_cmd.c_str());
|
||||
|
||||
int ret=0;
|
||||
{
|
||||
SwitchColour sc(sColour::DEBUG, std::cerr);
|
||||
ret = system(full_cmd.c_str());
|
||||
}
|
||||
|
||||
bool ok = EXITSTATUSCHECK(ret);
|
||||
if (!ok && !silent)
|
||||
{
|
||||
std::cerr << "Error: Failed to execute command: " << std::endl;
|
||||
std::cerr << full_cmd << std::endl;
|
||||
PrintError("Error: Failed to execute command: ");
|
||||
PrintError(full_cmd);
|
||||
}
|
||||
return ok;
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------------------------------------
|
||||
// execute_ssh_command
|
||||
// ----------------------------------------------------------------------------------------------------------
|
||||
bool execute_ssh_command(const sSSHInfo &ssh_info, const sCommand &remote_command, cMode mode, std::string *output)
|
||||
{
|
||||
if (remote_command.get_command_to_run().empty())
|
||||
@ -144,6 +163,9 @@ namespace dropshell
|
||||
return rval;
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------------------------------------
|
||||
// makesafecmd
|
||||
// ----------------------------------------------------------------------------------------------------------
|
||||
std::string sCommand::makesafecmd(std::string agent_path, const std::string &command) const
|
||||
{
|
||||
if (command.empty())
|
||||
@ -153,6 +175,9 @@ namespace dropshell
|
||||
return commandstr;
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------------------------------------
|
||||
// construct_cmd
|
||||
// ----------------------------------------------------------------------------------------------------------
|
||||
std::string sCommand::construct_cmd(std::string agent_path) const
|
||||
{
|
||||
if (mCmd.empty())
|
||||
|
119
source/src/utils/output.cpp
Normal file
119
source/src/utils/output.cpp
Normal file
@ -0,0 +1,119 @@
|
||||
#include "output.hpp"
|
||||
#include <iostream>
|
||||
#include <mutex>
|
||||
|
||||
namespace {
|
||||
// Mutex to synchronize output
|
||||
std::mutex output_mutex;
|
||||
|
||||
// ANSI colour codes
|
||||
constexpr const char* GREY = "\033[90m";
|
||||
constexpr const char* RESET = "\033[0m";
|
||||
constexpr const char* DEBUG_COLOUR = "\033[36m"; // Cyan
|
||||
constexpr const char* INFO_COLOUR = "\033[32m"; // Green
|
||||
constexpr const char* WARNING_COLOUR = "\033[33m"; // Yellow
|
||||
constexpr const char* ERROR_COLOUR = "\033[31m"; // Red
|
||||
|
||||
// Tag and colour for each stream
|
||||
struct StreamInfo {
|
||||
const char* tag;
|
||||
const char* colour;
|
||||
};
|
||||
|
||||
const StreamInfo stream_infos[] = {
|
||||
{"[DBG]", DEBUG_COLOUR},
|
||||
{"[INF]", INFO_COLOUR},
|
||||
{"[WRN]", WARNING_COLOUR},
|
||||
{"[ERR]", ERROR_COLOUR}
|
||||
};
|
||||
|
||||
// Custom streambuf to prefix and colour each line
|
||||
class PrefixStreambuf : public std::streambuf {
|
||||
public:
|
||||
PrefixStreambuf(std::ostream& dest, const char* tag, const char* colour)
|
||||
: dest_(dest), tag_(tag), colour_(colour), at_line_start_(true) {}
|
||||
|
||||
protected:
|
||||
int overflow(int c) override {
|
||||
std::lock_guard<std::mutex> lock(output_mutex);
|
||||
if (c == EOF) return !EOF;
|
||||
if (at_line_start_ && c != '\n') {
|
||||
dest_ << GREY << tag_ << RESET << ' ' << colour_;
|
||||
at_line_start_ = false;
|
||||
}
|
||||
dest_.put(static_cast<char>(c));
|
||||
if (c == '\n') {
|
||||
dest_ << RESET;
|
||||
at_line_start_ = true;
|
||||
}
|
||||
return c;
|
||||
}
|
||||
private:
|
||||
std::ostream& dest_;
|
||||
const char* tag_;
|
||||
const char* colour_;
|
||||
bool at_line_start_;
|
||||
};
|
||||
|
||||
PrefixStreambuf debug_buf(std::clog, stream_infos[0].tag, stream_infos[0].colour);
|
||||
PrefixStreambuf info_buf(std::clog, stream_infos[1].tag, stream_infos[1].colour);
|
||||
PrefixStreambuf warning_buf(std::clog, stream_infos[2].tag, stream_infos[2].colour);
|
||||
PrefixStreambuf error_buf(std::cerr, stream_infos[3].tag, stream_infos[3].colour);
|
||||
|
||||
std::ostream debug_stream(&debug_buf);
|
||||
std::ostream info_stream(&info_buf);
|
||||
std::ostream warning_stream(&warning_buf);
|
||||
std::ostream error_stream(&error_buf);
|
||||
}
|
||||
|
||||
std::ostream& debug = debug_stream;
|
||||
std::ostream& info = info_stream;
|
||||
std::ostream& warning = warning_stream;
|
||||
std::ostream& error = error_stream;
|
||||
|
||||
void SetColour(sColour colour, std::ostream& os) {
|
||||
switch (colour) {
|
||||
case sColour::RESET:
|
||||
os << RESET;
|
||||
break;
|
||||
case sColour::DEBUG:
|
||||
os << DEBUG_COLOUR;
|
||||
break;
|
||||
case sColour::INFO:
|
||||
os << INFO_COLOUR;
|
||||
break;
|
||||
case sColour::WARNING:
|
||||
os << WARNING_COLOUR;
|
||||
break;
|
||||
case sColour::ERROR:
|
||||
os << ERROR_COLOUR;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void PrintDebug(const std::string& msg) {
|
||||
std::lock_guard<std::mutex> lock(output_mutex);
|
||||
debug << msg << '\n';
|
||||
}
|
||||
void PrintInfo(const std::string& msg) {
|
||||
std::lock_guard<std::mutex> lock(output_mutex);
|
||||
info << msg << '\n';
|
||||
}
|
||||
void PrintWarning(const std::string& msg) {
|
||||
std::lock_guard<std::mutex> lock(output_mutex);
|
||||
warning << msg << '\n';
|
||||
}
|
||||
void PrintError(const std::string& msg) {
|
||||
std::lock_guard<std::mutex> lock(output_mutex);
|
||||
error << msg << '\n';
|
||||
}
|
||||
|
||||
SwitchColour::SwitchColour(sColour colour, std::ostream& os) : os_(os), colour_(colour)
|
||||
{
|
||||
SetColour(colour_, os_);
|
||||
}
|
||||
|
||||
SwitchColour::~SwitchColour()
|
||||
{
|
||||
SetColour(sColour::RESET, os_);
|
||||
}
|
@ -4,6 +4,7 @@
|
||||
#include <iostream>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <ostream>
|
||||
|
||||
/*
|
||||
|
||||
@ -47,5 +48,37 @@ enum class sColour {
|
||||
|
||||
*/
|
||||
|
||||
// Output streams for different log levels
|
||||
extern std::ostream& debug;
|
||||
extern std::ostream& info;
|
||||
extern std::ostream& warning;
|
||||
extern std::ostream& error;
|
||||
|
||||
// Enum for colours
|
||||
enum class sColour {
|
||||
RESET,
|
||||
DEBUG,
|
||||
INFO,
|
||||
WARNING,
|
||||
ERROR
|
||||
};
|
||||
|
||||
// Set colour for a stream
|
||||
void SetColour(sColour colour, std::ostream& os = std::cerr);
|
||||
|
||||
// Helper print functions
|
||||
void PrintDebug(const std::string& msg);
|
||||
void PrintInfo(const std::string& msg);
|
||||
void PrintWarning(const std::string& msg);
|
||||
void PrintError(const std::string& msg);
|
||||
|
||||
class SwitchColour
|
||||
{
|
||||
public:
|
||||
SwitchColour(sColour colour, std::ostream& os = std::cerr);
|
||||
~SwitchColour();
|
||||
private:
|
||||
std::ostream& os_;
|
||||
sColour colour_;
|
||||
};
|
||||
#endif // OUTPUT_HPP
|
Reference in New Issue
Block a user