diff --git a/CMakeLists.txt b/CMakeLists.txt index 05c830c..3b7f0e2 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -57,7 +57,7 @@ add_dependencies(bottles cog) add_custom_target(cog ALL DEPENDS ${coggedfiles}) add_executable(cellar ${src}/cellar.cpp ${src}/commands.cpp ${src}/fs.cpp - ${src}/version.cpp) + ${src}/version.cpp ${src}/output.cpp) target_link_libraries(cellar ${Boost_LIBRARIES} bottles) install(TARGETS cellar bottles diff --git a/include/output.hpp b/include/output.hpp new file mode 100644 index 0000000..a962c8b --- /dev/null +++ b/include/output.hpp @@ -0,0 +1,14 @@ +#ifndef __OUTPUT_HPP +#define __OUTPUT_HPP + +#include + +namespace cellar { + namespace output { + extern void statement(std::string parm); + extern void warning(std::string parm); + extern void error(std::string); + } +} + +#endif // __OUTPUT_HPP diff --git a/src/bottles/active.cpp b/src/bottles/active.cpp index ec76458..91124cf 100644 --- a/src/bottles/active.cpp +++ b/src/bottles/active.cpp @@ -1,11 +1,11 @@ #include -#include #include #include #include #include "bottles.hpp" #include "internal/bottles.hpp" +#include "output.hpp" using namespace std; using namespace cellar::bottles; @@ -13,37 +13,43 @@ using namespace cellar::bottles; void cellar::bottles::print_active_bottle(int argc, vector argv) { map bottlemap = get_bottles(); if (bottlemap.find(".wine") == bottlemap.end()) { // not found - cout << "no active wine bottle" << endl; + output::error("no active wine bottle"); return; } Bottle active_bottle = bottlemap[".wine"]; string bottlepath = active_bottle.canonical_path; + stringstream outstr; + bool cellar_managed = true; if (active_bottle.type == bottle_symlink) { - cout << "symlink to "; + outstr << "symlink to "; string homedir = getenv("HOME"); if (active_bottle.canonical_path.substr(0, homedir.length()) == homedir) { bottlepath.replace(0, homedir.length() + 1, ""); // should convert "/home/someone/.wine.example" to ".wine.example" active_bottle = bottlemap[bottlepath]; } else { - cout << active_bottle.canonical_path << endl; + outstr << active_bottle.canonical_path; + cellar_managed = false; return; } } - switch (active_bottle.type) { - case bottle_anonymous: - cout << "anonymous wine bottle at " << active_bottle.canonical_path << endl; - return; - case bottle_labelled: - cout << active_bottle.config["name"] << " (~/" << bottlepath << ")"; - if (active_bottle.config.find("desc") != active_bottle.config.end()) { - cout << " - " << active_bottle.config["desc"]; - } - cout << endl; - return; - default: - cout << "broken or unsupported wine bottle" << endl; - return; + if (cellar_managed) { + switch (active_bottle.type) { + case bottle_anonymous: + outstr << "anonymous wine bottle at " << active_bottle.canonical_path; + break; + case bottle_labelled: + outstr << active_bottle.config["name"] << " (~/" << bottlepath << ")"; + if (active_bottle.config.find("desc") != active_bottle.config.end()) { + outstr << " - " << active_bottle.config["desc"]; + } + break; + default: + outstr << "broken or unsupported wine bottle"; + break; + } } + + output::statement(outstr.str()); } diff --git a/src/bottles/bottles.cpp b/src/bottles/bottles.cpp index eee6e2a..6a2d1bd 100644 --- a/src/bottles/bottles.cpp +++ b/src/bottles/bottles.cpp @@ -13,8 +13,10 @@ #include "internal/bottles.hpp" #include "dll.hpp" #include "fs.hpp" +#include "output.hpp" using namespace std; +using namespace cellar; using namespace cellar::bottles; using CommandFunction = cellar::commands::CommandFunction; @@ -31,7 +33,7 @@ DLL_PUBLIC map cellar::bottles::get_bottles() { map result; string homepath = getenv("HOME"); - vector homedir = cellar::fs::listdir(homepath); + vector homedir = fs::listdir(homepath); for (string item : homedir) { if (item.substr(0,5) == ".wine") { Bottle output; @@ -78,6 +80,8 @@ DLL_PUBLIC map cellar::bottles::get_bottles() { void cellar::bottles::print_bottles(int argc, vector argv) { map bottles = get_bottles(); + stringstream outstr; + for (auto item : bottles) { if (item.first == ".wine" || item.first == ".wine.template") { // .wine is considered to be "active", and .wine.template is used as a template @@ -85,20 +89,21 @@ void cellar::bottles::print_bottles(int argc, vector argv) { continue; } Bottle bottle = item.second; - cout << item.first << " - "; + outstr << item.first << " - "; switch (bottle.type) { case bottle_anonymous: - cout << "anonymous wine bottle"; + outstr << "anonymous wine bottle"; break; case bottle_symlink: - cout << "symlink to " << bottle.canonical_path; + outstr << "symlink to " << bottle.canonical_path; break; case bottle_labelled: - cout << bottle.config["name"]; + outstr << bottle.config["name"]; break; default: - cout << "broken or unsupported wine bottle"; + outstr << "broken or unsupported wine bottle"; } - cout << endl; + output::statement(outstr.str()); + outstr.str(""); } } diff --git a/src/cellar.cpp b/src/cellar.cpp index c8d24b8..5947eab 100644 --- a/src/cellar.cpp +++ b/src/cellar.cpp @@ -11,6 +11,7 @@ #include "bottles.hpp" #include "cellar.hpp" #include "commands.hpp" +#include "output.hpp" #include "version.hpp" using namespace std; @@ -18,8 +19,8 @@ using namespace cellar; using json = nlohmann::json; void cellar::print_header() { - cout << "cellar - bottle management tool for WINE connoisseurs" << std::endl; - cout << version::short_version() << std::endl; + output::statement("cellar - bottle management tool for WINE connoisseurs"); + output::statement(version::short_version()); } int main(int argc, char* argv[]) { @@ -57,7 +58,10 @@ int main(int argc, char* argv[]) { } commands::command_map[usercmd](subargv.size(), subargv); } else { - cerr << "invalid command: " << usercmd << endl; + stringstream errstr; + + errstr << "invalid command: " << usercmd; + output::error(errstr.str()); return 1; } return 0; diff --git a/src/fs.cpp b/src/fs.cpp index a8aeae3..cff1148 100644 --- a/src/fs.cpp +++ b/src/fs.cpp @@ -6,6 +6,7 @@ #include #include "fs.hpp" +#include "output.hpp" using namespace std; @@ -21,7 +22,8 @@ vector cellar::fs::listdir(string path) { result.push_back(item); } catch (const exception& exc) { - cout << "fuck" << endl; + // TODO: better error handling + cellar::output::error("fuck"); } } return result; diff --git a/src/output.cpp b/src/output.cpp new file mode 100644 index 0000000..70c292d --- /dev/null +++ b/src/output.cpp @@ -0,0 +1,14 @@ +#include +#include + +#include "output.hpp" + +void cellar::output::statement(std::string str_message) { + std::cout << "* " << str_message << std::endl; +} +void cellar::output::warning(std::string str_message) { + std::cerr << "* " << str_message << std::endl; +} +void cellar::output::error(std::string str_message) { + std::cerr << "* " << str_message << std::endl; +} diff --git a/src/version.cpp.cog b/src/version.cpp.cog index 6a80c68..4820a07 100644 --- a/src/version.cpp.cog +++ b/src/version.cpp.cog @@ -4,6 +4,7 @@ #include #include "commands.hpp" +#include "output.hpp" #include "version.hpp" using namespace std; @@ -41,6 +42,6 @@ string cellar::version::short_version() { } void print_version(int argc, vector argv) { - cout << short_version() << endl; + cellar::output::statement(short_version()); } cellar::commands::CommandFunction versioncmd = cellar::commands::command_map["version"] = &print_version;