polybar-dwm/include/utils/command.hpp
Michael Carlberg e3065d0e6c feat(ipc): New ipc module
Add a new module that allow users to configure hooks
on received ipc messages. The hook will execute the defined
shell script and the output of the script will be used
as the module content.

Ref #84
2016-11-14 09:26:40 +01:00

87 lines
1.9 KiB
C++

#pragma once
#include "common.hpp"
#include "components/logger.hpp"
#include "utils/threading.hpp"
LEMONBUDDY_NS
namespace command_util {
DEFINE_ERROR(command_error);
DEFINE_CHILD_ERROR(command_strerror, command_error);
/**
* Wrapper used to execute command in a subprocess.
* In-/output streams are opened to enable ipc.
*
* Example usage:
*
* @code cpp
* auto cmd = command_util::make_command("cat /etc/rc.local");
* cmd->exec();
* cmd->tail([](string s) { std::cout << s << std::endl; });
* @endcode
*
* @code cpp
* auto cmd = command_util::make_command(
* "while read -r line; do echo data from parent process: $line; done");
* cmd->exec(false);
* cmd->writeline("Test");
* cout << cmd->readline();
* cmd->wait();
* @endcode
*
* @code cpp
* auto cmd = command_util::make_command("for i in 1 2 3; do echo $i; done");
* cmd->exec();
* cout << cmd->readline(); // 1
* cout << cmd->readline() << cmd->readline(); // 23
* @endcode
*/
class command {
public:
explicit command(const logger& logger, string cmd);
~command();
int exec(bool wait_for_completion = true);
void terminate();
bool is_running();
int wait();
void tail(callback<string> callback);
int writeline(string data);
string readline();
int get_stdout(int c);
int get_stdin(int c);
pid_t get_pid();
int get_exit_status();
protected:
const logger& m_log;
string m_cmd;
int m_stdout[2];
int m_stdin[2];
pid_t m_forkpid;
int m_forkstatus;
threading_util::spin_lock m_pipelock;
};
using command_t = unique_ptr<command>;
template <typename... Args>
command_t make_command(Args&&... args) {
return make_unique<command>(configure_logger().create<const logger&>(), forward<Args>(args)...);
}
}
using command = command_util::command;
using command_t = command_util::command_t;
LEMONBUDDY_NS_END