// package_rollback.cpp — see package_rollback.h. The rollback delete below runs under
// the ONE carve-out from prune's exclusive file-deletion authority, stated at
// src/shell/persist/prune_fs.cpp:5-11. That discriminator has two clauses and this
// journal makes only the FIRST structural: "did this call create it" is guaranteed by
// recording exclusively-created paths, but "did anything ever reference it" is a
// claim about the caller's ordering — hence markIndexCommitted(), which the import
// verb must fire at the index commit so a later rollback() refuses instead of
// deleting indexed files.

#include "shell/package/package_rollback.h"

#include <filesystem>

#include "shell/package/package_path.h"

namespace reasampler {

namespace fs = std::filesystem;

bool LandedFileJournal::writeLandedFile(const std::string& destPath,
                                        const PayloadBuffer& payload) {
    if (indexCommitted_) return false;

    std::error_code ec;
    const fs::path resolved = fs::absolute(utf8Path(destPath), ec);
    if (ec) return false;
    const std::string absPath = pathToUtf8(resolved);

    if (!writeFileExclusive(absPath, payload)) return false;
    paths_.push_back(absPath);
    return true;
}

RollbackResult LandedFileJournal::rollback() {
    RollbackResult result;
    if (indexCommitted_) {
        result.refused = true;
        return result;
    }
    for (const std::string& path : paths_) {
        std::error_code ec;
        const bool removed = fs::remove(utf8Path(path), ec);
        if (removed)  ++result.deletedCount;
        else if (ec)  ++result.failedCount;
        else          ++result.alreadyAbsentCount;  // no error, nothing there
    }
    paths_.clear();
    return result;
}

}  // namespace reasampler
