Browse Source

Log process IDs of started sub processes

move-only-function
Martchus 1 year ago
parent
commit
aa356944da
  1. 23
      librepomgr/buildactions/buildaction.cpp
  2. 2
      librepomgr/buildactions/buildaction.h
  3. 5
      librepomgr/buildactions/buildactionlivestreaming.cpp
  4. 18
      librepomgr/buildactions/buildactionprivate.h
  5. 10
      librepomgr/buildactions/conductbuild.cpp
  6. 31
      librepomgr/buildactions/customcommand.cpp
  7. 6
      librepomgr/buildactions/repomanagement.cpp
  8. 7
      librepomgr/tests/buildactions.cpp

23
librepomgr/buildactions/buildaction.cpp

@ -409,17 +409,18 @@ void DummyBuildAction::run()
}
// launch subprocess producing a logfile
m_logProcess = m_buildAction->makeBuildProcess(m_workingDirectory + "/foo.log", [this](boost::process::child &&child, ProcessResult &&result) {
CPP_UTILITIES_UNUSED(child)
m_logProcess = nullptr;
m_buildAction->appendOutput("log process exited with code: ", result.exitCode, '\n');
if (!result.error.empty()) {
m_buildAction->appendOutput("log process error: ", result.error, '\n');
}
if (!m_buildAction->isAborted()) {
stop();
}
});
m_logProcess
= m_buildAction->makeBuildProcess("dummy", m_workingDirectory + "/foo.log", [this](boost::process::child &&child, ProcessResult &&result) {
CPP_UTILITIES_UNUSED(child)
m_logProcess = nullptr;
m_buildAction->appendOutput("log process exited with code: ", result.exitCode, '\n');
if (!result.error.empty()) {
m_buildAction->appendOutput("log process error: ", result.error, '\n');
}
if (!m_buildAction->isAborted()) {
stop();
}
});
m_logProcess->launch(scriptPath, "1");
continuePrinting();

2
librepomgr/buildactions/buildaction.h

@ -200,7 +200,7 @@ public:
void setStopHandler(std::function<void(void)> &&stopHandler);
void setConcludeHandler(std::function<void(void)> &&concludeHandler);
std::shared_ptr<BuildProcessSession> findBuildProcess(const std::string &filePath);
std::shared_ptr<BuildProcessSession> makeBuildProcess(std::string &&logFilePath, ProcessHandler &&handler);
std::shared_ptr<BuildProcessSession> makeBuildProcess(std::string &&displayName, std::string &&logFilePath, ProcessHandler &&handler);
void terminateOngoingBuildProcesses();
void streamFile(const WebAPI::Params &params, const std::string &filePath, std::string_view fileMimeType);
void streamOutput(const WebAPI::Params &params, std::size_t offset = 0);

5
librepomgr/buildactions/buildactionlivestreaming.cpp

@ -328,7 +328,7 @@ void BufferSearch::operator()(const BuildProcessSession::BufferType &buffer, std
}
}
std::shared_ptr<BuildProcessSession> BuildAction::makeBuildProcess(std::string &&logFilePath, ProcessHandler &&handler)
std::shared_ptr<BuildProcessSession> BuildAction::makeBuildProcess(std::string &&displayName, std::string &&logFilePath, ProcessHandler &&handler)
{
const auto processesLock = std::lock_guard<std::mutex>(m_processesMutex);
auto &process = m_ongoingProcesses[logFilePath];
@ -342,7 +342,8 @@ std::shared_ptr<BuildProcessSession> BuildAction::makeBuildProcess(std::string &
logfiles.emplace_back(logFilePath);
}
buildLock.unlock();
return process = make_shared<BuildProcessSession>(this, m_setup->building.ioContext, std::move(logFilePath), std::move(handler));
return process
= make_shared<BuildProcessSession>(this, m_setup->building.ioContext, std::move(displayName), std::move(logFilePath), std::move(handler));
}
void BuildAction::terminateOngoingBuildProcesses()

18
librepomgr/buildactions/buildactionprivate.h

@ -8,6 +8,7 @@
#include "../webclient/database.h"
#include <c++utilities/chrono/datetime.h>
#include <c++utilities/io/ansiescapecodes.h>
#include <c++utilities/io/inifile.h>
#include <c++utilities/misc/flagenumclass.h>
@ -21,6 +22,7 @@
#include <boost/asio/posix/stream_descriptor.hpp>
#include <boost/beast/core/file.hpp>
#include <boost/filesystem/path.hpp>
#include <boost/process/extend.hpp>
#ifdef CPP_UTILITIES_DEBUG_BUILD
#include <boost/asio/deadline_timer.hpp>
@ -131,7 +133,8 @@ public:
using BufferPoolType = BufferPool<StorageType>;
using BufferType = BufferPoolType::BufferType;
explicit BuildProcessSession(BuildAction *buildAction, boost::asio::io_context &ioContext, std::string &&logFilePath, Handler &&handler);
explicit BuildProcessSession(
BuildAction *buildAction, boost::asio::io_context &ioContext, std::string &&displayName, std::string &&logFilePath, Handler &&handler);
template <typename... ChildArgs> void launch(ChildArgs &&...childArgs);
void registerWebSession(std::shared_ptr<WebAPI::Session> &&webSession);
void registerNewDataHandler(std::function<void(BufferType, std::size_t)> &&handler);
@ -175,6 +178,7 @@ private:
boost::process::async_pipe m_pipe;
BufferPoolType m_bufferPool;
BufferType m_buffer;
std::string m_displayName;
std::string m_logFilePath;
boost::beast::file m_logFile;
boost::asio::posix::stream_descriptor m_logFileDescriptor;
@ -196,12 +200,13 @@ inline std::size_t BuildProcessSession::DataForWebSession::bytesToSendFromFile()
return m_bytesToSendFromFile.load();
}
inline BuildProcessSession::BuildProcessSession(
BuildAction *buildAction, boost::asio::io_context &ioContext, std::string &&logFilePath, BaseProcessSession::Handler &&handler)
inline BuildProcessSession::BuildProcessSession(BuildAction *buildAction, boost::asio::io_context &ioContext, std::string &&displayName,
std::string &&logFilePath, BaseProcessSession::Handler &&handler)
: BaseProcessSession(ioContext, std::move(handler))
, m_buildAction(buildAction ? buildAction->weak_from_this() : std::weak_ptr<BuildAction>())
, m_pipe(ioContext)
, m_bufferPool(bufferSize)
, m_displayName(displayName)
, m_logFilePath(std::move(logFilePath))
, m_logFileDescriptor(ioContext)
{
@ -222,6 +227,13 @@ template <typename... ChildArgs> void BuildProcessSession::launch(ChildArgs &&..
try {
child = boost::process::child(
m_ioContext, group, std::forward<ChildArgs>(childArgs)..., (boost::process::std_out & boost::process::std_err) > m_pipe,
boost::process::extend::on_success =
[session = shared_from_this()](auto &executor) {
if (const auto buildAction = session->m_buildAction.lock()) {
buildAction->appendOutput(
CppUtilities::EscapeCodes::Phrases::InfoMessage, session->m_displayName, " PID: ", executor.pid, '\n');
}
},
boost::process::on_exit =
[session = shared_from_this()](int exitCode, const std::error_code &errorCode) {
session->result.exitCode = exitCode;

10
librepomgr/buildactions/conductbuild.cpp

@ -742,7 +742,7 @@ InvocationResult ConductBuild::invokeUpdatePkgSums(const BatchProcessingSession:
if (!m_updateChecksums || packageProgress.checksumsUpdated) {
return InvocationResult::Skipped;
}
auto processSession = m_buildAction->makeBuildProcess(packageProgress.buildDirectory + "/updpkgsums.log",
auto processSession = m_buildAction->makeBuildProcess(packageName + " checksum update", packageProgress.buildDirectory + "/updpkgsums.log",
[this, downloadsSession, &packageProgress, &packageName, buildDirectory](boost::process::child &&child, ProcessResult &&result) {
const auto hasError = result.errorCode || result.exitCode != 0;
auto lock = lockToWrite();
@ -789,7 +789,7 @@ InvocationResult ConductBuild::invokeUpdatePkgSums(const BatchProcessingSession:
InvocationResult ConductBuild::invokeMakepkgToMakeSourcePackage(const BatchProcessingSession::SharedPointerType &downloadsSession,
const std::string &packageName, PackageBuildProgress &packageProgress, const std::string &buildDirectory)
{
auto processSession = m_buildAction->makeBuildProcess(packageProgress.buildDirectory + "/download.log",
auto processSession = m_buildAction->makeBuildProcess(packageName + " download", packageProgress.buildDirectory + "/download.log",
[this, downloadsSession, &packageProgress, &packageName](boost::process::child &&child, ProcessResult &&result) {
auto lock = lockToWrite();
if (result.errorCode) {
@ -931,7 +931,7 @@ InvocationResult ConductBuild::invokeMakechrootpkg(
// invoke makechrootpkg to build package
m_buildAction->log()(Phrases::InfoMessage, "Building ", packageName, '\n');
auto processSession = m_buildAction->makeBuildProcess(packageProgress.buildDirectory + "/build.log",
auto processSession = m_buildAction->makeBuildProcess(packageName + " build", packageProgress.buildDirectory + "/build.log",
std::bind(&ConductBuild::handleMakechrootpkgErrorsAndAddPackageToRepo, this, makepkgchrootSession, std::ref(packageName),
std::ref(packageProgress), std::placeholders::_1, std::placeholders::_2));
processSession->registerNewDataHandler(BufferSearch("Updated version: ", "\e\n", "Starting build",
@ -1101,7 +1101,7 @@ void ConductBuild::addPackageToRepo(
}
// add completed package to repository
auto processSession = m_buildAction->makeBuildProcess(packageProgress.buildDirectory + "/repo-add.log",
auto processSession = m_buildAction->makeBuildProcess("repo-add for " + packageName, packageProgress.buildDirectory + "/repo-add.log",
std::bind(&ConductBuild::handleRepoAddErrorsAndMakeNextPackage, this, makepkgchrootSession, std::ref(packageName), std::ref(packageProgress),
std::placeholders::_1, std::placeholders::_2));
processSession->launch(boost::process::start_dir(repoPath), m_repoAddPath, dbFilePath, binaryPackageNames);
@ -1286,7 +1286,7 @@ void ConductBuild::assignNewVersion(const std::string &packageName, PackageBuild
return;
}
auto &newVersion = updatedVersionInfoParts.back();
m_buildAction->log()(Phrases::InfoMessage, "Version of \"", packageName, "\" has been updated to: ", newVersion, '\n');
m_buildAction->appendOutput(Phrases::InfoMessage, "Version of \"", packageName, "\" has been updated to: ", newVersion, '\n');
const auto lock = lockToWrite();
packageProgress.updatedVersion = std::move(newVersion);
}

31
librepomgr/buildactions/customcommand.cpp

@ -55,21 +55,22 @@ void CustomCommand::run()
m_buildAction->appendOutput(Phrases::InfoMessage, "Running custom command: ", command, '\n');
// launch process, pass finish handler
auto process = m_buildAction->makeBuildProcess(m_workingDirectory + "/the.log", [this](boost::process::child &&, ProcessResult &&result) {
if (result.errorCode) {
m_buildAction->appendOutput(Phrases::InfoMessage, "Unable to invoke command: ", result.errorCode.message());
reportError(result.errorCode.message());
return;
}
m_buildAction->appendOutput(
result.exitCode == 0 ? Phrases::InfoMessage : Phrases::ErrorMessage, "Command exited with return code ", result.exitCode);
if (result.exitCode != 0) {
reportError(argsToString("non-zero exit code ", result.exitCode));
return;
}
const auto buildLock = m_setup.building.lockToWrite();
reportSuccess();
});
auto process
= m_buildAction->makeBuildProcess("command", m_workingDirectory + "/the.log", [this](boost::process::child &&, ProcessResult &&result) {
if (result.errorCode) {
m_buildAction->appendOutput(Phrases::InfoMessage, "Unable to invoke command: ", result.errorCode.message());
reportError(result.errorCode.message());
return;
}
m_buildAction->appendOutput(
result.exitCode == 0 ? Phrases::InfoMessage : Phrases::ErrorMessage, "Command exited with return code ", result.exitCode);
if (result.exitCode != 0) {
reportError(argsToString("non-zero exit code ", result.exitCode));
return;
}
const auto buildLock = m_setup.building.lockToWrite();
reportSuccess();
});
process->launch(boost::process::start_dir(m_workingDirectory), boost::process::search_path("bash"), "-ec", command);
}

6
librepomgr/buildactions/repomanagement.cpp

@ -152,7 +152,7 @@ void RemovePackages::run()
}
// remove package from database file
auto repoRemoveProcess = m_buildAction->makeBuildProcess(m_workingDirectory + "/repo-remove.log",
auto repoRemoveProcess = m_buildAction->makeBuildProcess("repo-remove", m_workingDirectory + "/repo-remove.log",
std::bind(&RemovePackages::handleRepoRemoveResult, this, std::placeholders::_1, std::placeholders::_2));
repoRemoveProcess->launch(
boost::process::start_dir(m_destinationRepoDirectory), m_repoRemovePath, m_destinationDatabaseFile, m_result.processedPackages);
@ -268,12 +268,12 @@ void MovePackages::run()
const auto processSession = MultiSession<void>::create(m_setup.building.ioContext, std::bind(&MovePackages::conclude, this));
// add packages to database file of destination repo
auto repoAddProcess = m_buildAction->makeBuildProcess(m_workingDirectory + "/repo-add.log",
auto repoAddProcess = m_buildAction->makeBuildProcess("repo-add", m_workingDirectory + "/repo-add.log",
std::bind(&MovePackages::handleRepoAddResult, this, processSession, std::placeholders::_1, std::placeholders::_2));
repoAddProcess->launch(boost::process::start_dir(m_destinationRepoDirectory), m_repoAddPath, m_destinationDatabaseFile, m_fileNames);
// remove package from database file of source repo
auto repoRemoveProcess = m_buildAction->makeBuildProcess(m_workingDirectory + "/repo-remove.log",
auto repoRemoveProcess = m_buildAction->makeBuildProcess("repo-remove", m_workingDirectory + "/repo-remove.log",
std::bind(&MovePackages::handleRepoRemoveResult, this, processSession, std::placeholders::_1, std::placeholders::_2));
repoRemoveProcess->launch(boost::process::start_dir(m_sourceRepoDirectory), m_repoRemovePath, m_sourceDatabaseFile, m_result.processedPackages);

7
librepomgr/tests/buildactions.cpp

@ -238,6 +238,8 @@ void BuildActionsTests::testProcessSession()
*/
void BuildActionsTests::testBuildActionProcess()
{
m_buildAction = std::make_shared<BuildAction>(0, &m_setup);
const auto scriptPath = testFilePath("scripts/print_some_data.sh");
const auto logFilePath = std::filesystem::path(TestApplication::instance()->workingDirectory()) / "logfile.log";
std::filesystem::create_directory(logFilePath.parent_path());
@ -247,10 +249,10 @@ void BuildActionsTests::testBuildActionProcess()
auto &ioc = m_setup.building.ioContext;
auto session = std::make_shared<BuildProcessSession>(
nullptr, ioc, std::string(logFilePath), [&ioc](boost::process::child &&child, ProcessResult &&result) {
CPP_UTILITIES_UNUSED(child)
m_buildAction.get(), ioc, "test", std::string(logFilePath), [&ioc](boost::process::child &&child, ProcessResult &&result) {
CPPUNIT_ASSERT_EQUAL(std::error_code(), result.errorCode);
CPPUNIT_ASSERT_EQUAL(0, result.exitCode);
CPPUNIT_ASSERT_GREATER(0, child.native_handle());
ioc.stop();
});
session->launch(scriptPath);
@ -261,6 +263,7 @@ void BuildActionsTests::testBuildActionProcess()
CPPUNIT_ASSERT_EQUAL(5001_st, logLines.size());
CPPUNIT_ASSERT_EQUAL("printing some numbers"s, logLines.front());
CPPUNIT_ASSERT_EQUAL("line 5000"s, logLines.back());
TESTUTILS_ASSERT_LIKE_FLAGS("PID logged", ".*test PID\\: [0-9]+.*\n.*"s, std::regex::extended, m_buildAction->output);
}
/*!

Loading…
Cancel
Save