137 lines
4.3 KiB
C++
137 lines
4.3 KiB
C++
#include "server_env.hpp"
|
|
#include <boost/property_tree/ptree.hpp>
|
|
#include <boost/property_tree/ini_parser.hpp>
|
|
#include <boost/filesystem.hpp>
|
|
#include <cstdlib>
|
|
#include <iostream>
|
|
|
|
namespace dropshell {
|
|
|
|
// Helper function to trim whitespace from both ends of a string
|
|
static std::string trim(const std::string& str) {
|
|
const std::string whitespace = " \t";
|
|
const auto strBegin = str.find_first_not_of(whitespace);
|
|
if (strBegin == std::string::npos) {
|
|
return ""; // empty string
|
|
}
|
|
const auto strEnd = str.find_last_not_of(whitespace);
|
|
const auto strRange = strEnd - strBegin + 1;
|
|
return str.substr(strBegin, strRange);
|
|
}
|
|
|
|
// Helper function to print the contents of a file to screen
|
|
static void print_file(const std::string& path) {
|
|
std::cout << "Contents of " << path << ":" << std::endl;
|
|
std::ifstream file(path);
|
|
std::string line;
|
|
while (std::getline(file, line)) {
|
|
std::cout << " " << line << std::endl;
|
|
}
|
|
}
|
|
|
|
|
|
bool server_env::is_valid() {
|
|
return mValid;
|
|
}
|
|
|
|
server_env::server_env(const std::string& path) : mValid(false) {
|
|
// Construct the full path to _server.env
|
|
boost::filesystem::path env_path = boost::filesystem::path(path) / "_server.env";
|
|
|
|
// Check if file exists
|
|
if (!boost::filesystem::exists(env_path)) {
|
|
throw std::runtime_error("Server environment file not found: " + env_path.string());
|
|
}
|
|
|
|
try {
|
|
// Read the environment file
|
|
std::ifstream file(env_path.string());
|
|
std::string line;
|
|
|
|
while (std::getline(file, line)) {
|
|
// Skip empty lines and comments
|
|
if (line.empty() || line[0] == '#') {
|
|
continue;
|
|
}
|
|
|
|
// Find the position of the equals sign
|
|
size_t pos = line.find('=');
|
|
if (pos != std::string::npos) {
|
|
std::string key = line.substr(0, pos);
|
|
std::string value = line.substr(pos + 1);
|
|
|
|
// Trim whitespace using the helper function
|
|
key = trim(key);
|
|
value = trim(value);
|
|
|
|
// Handle ${USER} replacement
|
|
size_t user_pos;
|
|
while ((user_pos = value.find("${USER}")) != std::string::npos) {
|
|
const char* user = std::getenv("USER");
|
|
if (user) {
|
|
value.replace(user_pos, 7, user);
|
|
}
|
|
}
|
|
|
|
variables[key] = value;
|
|
}
|
|
}
|
|
|
|
// Verify required variables exist
|
|
for (const auto& var : {"SSH_HOST", "SSH_USER", "SSH_PORT", "DROPSHELL_DIR"}) {
|
|
if (variables.find(var) == variables.end()) {
|
|
// print the contents of the _server.env file to screen:
|
|
print_file(env_path.string());
|
|
// print variables identified in the file:
|
|
std::cout << "Variables identified in the file:" << std::endl;
|
|
for (const auto& var : variables) {
|
|
std::cout << " " << var.first << std::endl;
|
|
}
|
|
throw std::runtime_error("Missing required variable: " + std::string(var));
|
|
}
|
|
}
|
|
mValid = true;
|
|
|
|
} catch (const boost::property_tree::ini_parser_error& e) {
|
|
throw std::runtime_error("Failed to parse server environment file: " + std::string(e.what()));
|
|
}
|
|
}
|
|
|
|
std::string server_env::get_variable(const std::string& name) {
|
|
auto it = variables.find(name);
|
|
if (it == variables.end()) {
|
|
return "";
|
|
}
|
|
|
|
std::string value = it->second;
|
|
|
|
// Replace ${USER} with actual username
|
|
const char* username = std::getenv("USER");
|
|
if (username) {
|
|
std::string user_var = "${USER}";
|
|
size_t pos = value.find(user_var);
|
|
if (pos != std::string::npos) {
|
|
value.replace(pos, user_var.length(), username);
|
|
}
|
|
}
|
|
|
|
return value;
|
|
}
|
|
|
|
std::string server_env::get_SSH_HOST() {
|
|
return get_variable("SSH_HOST");
|
|
}
|
|
|
|
std::string server_env::get_SSH_USER() {
|
|
return get_variable("SSH_USER");
|
|
}
|
|
|
|
std::string server_env::get_SSH_PORT() {
|
|
return get_variable("SSH_PORT");
|
|
}
|
|
|
|
std::string server_env::get_DROPSHELL_DIR() {
|
|
return get_variable("DROPSHELL_DIR");
|
|
}
|
|
|
|
} // namespace dropshell
|