#pragma once #include "Model.h" namespace timbre_core { // Persistence is represented only by this small interface. Implementations // may use a file system on the final product, but the domain layer remains // portable and has no filesystem dependency. class StateRepository { public: virtual ~StateRepository() = default; // Canonical names used by TimbreService. virtual bool load(AppState& destination) { return read(destination); } virtual bool commit(const AppState& source) { return save(source); } // Compatibility hooks for small repositories that naturally use read/write // terminology. Overriding either pair is sufficient; the defaults above // bridge the two naming conventions without recursion. virtual bool read(AppState& destination) { (void)destination; return false; } virtual bool write(const AppState& source) { (void)source; return false; } virtual bool save(const AppState& source) { return write(source); } bool loadState(AppState& destination) { return load(destination); } bool commitState(const AppState& source) { return commit(source); } }; class MemoryStateRepository final : public StateRepository { public: bool load(AppState& destination) override { if (!loadSucceeds_ || !hasValue_) { return false; } destination = value_; return true; } bool commit(const AppState& source) override { ++commitAttempts_; if (!commitSucceeds_) { return false; } value_ = source; hasValue_ = true; ++commitCount_; return true; } void seed(const AppState& state) { value_ = state; hasValue_ = true; } void setCommitSucceeds(bool succeeds) noexcept { commitSucceeds_ = succeeds; } void setLoadSucceeds(bool succeeds) noexcept { loadSucceeds_ = succeeds; } std::size_t commitAttempts() const noexcept { return commitAttempts_; } std::size_t commitCount() const noexcept { return commitCount_; } private: AppState value_{}; bool hasValue_ = false; bool loadSucceeds_ = true; bool commitSucceeds_ = true; std::size_t commitAttempts_ = 0; std::size_t commitCount_ = 0; }; } // namespace timbre_core