Add modified time to TrackData
This commit is contained in:
@@ -7,6 +7,7 @@
|
||||
#include "database.hpp"
|
||||
|
||||
#include <stdint.h>
|
||||
#include <sys/_stdint.h>
|
||||
|
||||
#include <algorithm>
|
||||
#include <cstdint>
|
||||
@@ -200,13 +201,16 @@ auto Database::Update() -> std::future<void> {
|
||||
// Stage 2: search for newly added files.
|
||||
ESP_LOGI(kTag, "scanning for new tracks");
|
||||
uint64_t num_processed = 0;
|
||||
file_gatherer_.FindFiles("", [&](const std::pmr::string& path) {
|
||||
file_gatherer_.FindFiles("", [&](const std::pmr::string& path,
|
||||
const FILINFO& info) {
|
||||
num_processed++;
|
||||
events::Ui().Dispatch(event::UpdateProgress{
|
||||
.stage = event::UpdateProgress::Stage::kScanningForNewTracks,
|
||||
.val = num_processed,
|
||||
});
|
||||
|
||||
std::pair<uint16_t, uint16_t> modified{info.fdate, info.ftime};
|
||||
|
||||
std::shared_ptr<TrackTags> tags = tag_parser_.ReadAndParseTags(path);
|
||||
if (!tags || tags->encoding() == Container::kUnsupported) {
|
||||
// No parseable tags; skip this fiile.
|
||||
@@ -228,7 +232,8 @@ auto Database::Update() -> std::future<void> {
|
||||
TrackId id = dbMintNewTrackId();
|
||||
ESP_LOGI(kTag, "recording new 0x%lx", id);
|
||||
|
||||
auto data = std::make_shared<TrackData>(id, path, hash);
|
||||
auto data = std::make_shared<TrackData>(id, path, hash, modified);
|
||||
|
||||
dbPutTrackData(*data);
|
||||
dbPutHash(hash, id);
|
||||
auto t = std::make_shared<Track>(data, tags);
|
||||
@@ -239,7 +244,8 @@ auto Database::Update() -> std::future<void> {
|
||||
std::shared_ptr<TrackData> existing_data = dbGetTrackData(*existing_hash);
|
||||
if (!existing_data) {
|
||||
// We found a hash that matches, but there's no data record? Weird.
|
||||
auto new_data = std::make_shared<TrackData>(*existing_hash, path, hash);
|
||||
auto new_data =
|
||||
std::make_shared<TrackData>(*existing_hash, path, hash, modified);
|
||||
dbPutTrackData(*new_data);
|
||||
auto t = std::make_shared<Track>(new_data, tags);
|
||||
dbCreateIndexesForTrack(*t);
|
||||
|
||||
@@ -22,7 +22,7 @@ static_assert(sizeof(TCHAR) == sizeof(char), "TCHAR must be CHAR");
|
||||
|
||||
auto FileGathererImpl::FindFiles(
|
||||
const std::pmr::string& root,
|
||||
std::function<void(const std::pmr::string&)> cb) -> void {
|
||||
std::function<void(const std::pmr::string&, const FILINFO&)> cb) -> void {
|
||||
std::pmr::deque<std::pmr::string> to_explore(&memory::kSpiRamResource);
|
||||
to_explore.push_back(root);
|
||||
|
||||
@@ -65,7 +65,7 @@ auto FileGathererImpl::FindFiles(
|
||||
} else {
|
||||
// This is a file! Let the callback know about it.
|
||||
// std::invoke(cb, full_path.str(), info);
|
||||
std::invoke(cb, full_path);
|
||||
std::invoke(cb, full_path, info);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,15 +19,17 @@ class IFileGatherer {
|
||||
public:
|
||||
virtual ~IFileGatherer(){};
|
||||
|
||||
virtual auto FindFiles(const std::pmr::string& root,
|
||||
std::function<void(const std::pmr::string&)> cb)
|
||||
virtual auto FindFiles(
|
||||
const std::pmr::string& root,
|
||||
std::function<void(const std::pmr::string&, const FILINFO&)> cb)
|
||||
-> void = 0;
|
||||
};
|
||||
|
||||
class FileGathererImpl : public IFileGatherer {
|
||||
public:
|
||||
virtual auto FindFiles(const std::pmr::string& root,
|
||||
std::function<void(const std::pmr::string&)> cb)
|
||||
virtual auto FindFiles(
|
||||
const std::pmr::string& root,
|
||||
std::function<void(const std::pmr::string&, const FILINFO&)> cb)
|
||||
-> void override;
|
||||
};
|
||||
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
#pragma once
|
||||
|
||||
#include <stdint.h>
|
||||
#include <sys/_stdint.h>
|
||||
|
||||
#include <map>
|
||||
#include <memory>
|
||||
@@ -118,23 +119,30 @@ class TrackData {
|
||||
const std::pmr::string filepath_;
|
||||
const uint64_t tags_hash_;
|
||||
const bool is_tombstoned_;
|
||||
const std::pair<uint16_t, uint16_t> modified_at_;
|
||||
|
||||
public:
|
||||
/* Constructor used when adding new tracks to the database. */
|
||||
TrackData(TrackId id, const std::pmr::string& path, uint64_t hash)
|
||||
TrackData(TrackId id,
|
||||
const std::pmr::string& path,
|
||||
uint64_t hash,
|
||||
std::pair<uint16_t, uint16_t> modified_at)
|
||||
: id_(id),
|
||||
filepath_(path, &memory::kSpiRamResource),
|
||||
tags_hash_(hash),
|
||||
is_tombstoned_(false) {}
|
||||
is_tombstoned_(false),
|
||||
modified_at_(modified_at) {}
|
||||
|
||||
TrackData(TrackId id,
|
||||
const std::pmr::string& path,
|
||||
uint64_t hash,
|
||||
bool is_tombstoned)
|
||||
bool is_tombstoned,
|
||||
std::pair<uint16_t, uint16_t> modified_at)
|
||||
: id_(id),
|
||||
filepath_(path, &memory::kSpiRamResource),
|
||||
tags_hash_(hash),
|
||||
is_tombstoned_(is_tombstoned) {}
|
||||
is_tombstoned_(is_tombstoned),
|
||||
modified_at_(modified_at) {}
|
||||
|
||||
TrackData(TrackData&& other) = delete;
|
||||
TrackData& operator=(TrackData& other) = delete;
|
||||
@@ -145,6 +153,9 @@ class TrackData {
|
||||
auto filepath() const -> std::pmr::string { return filepath_; }
|
||||
auto tags_hash() const -> uint64_t { return tags_hash_; }
|
||||
auto is_tombstoned() const -> bool { return is_tombstoned_; }
|
||||
auto modified_at() const -> std::pair<uint16_t, uint16_t> {
|
||||
return modified_at_;
|
||||
}
|
||||
|
||||
auto UpdateHash(uint64_t new_hash) const -> TrackData;
|
||||
|
||||
|
||||
@@ -67,6 +67,8 @@ auto EncodeDataValue(const TrackData& track) -> std::string {
|
||||
cppbor::Tstr{track.filepath()},
|
||||
cppbor::Uint{track.tags_hash()},
|
||||
cppbor::Bool{track.is_tombstoned()},
|
||||
cppbor::Uint{track.modified_at().first},
|
||||
cppbor::Uint{track.modified_at().second},
|
||||
};
|
||||
return val.toString();
|
||||
}
|
||||
@@ -78,18 +80,24 @@ auto ParseDataValue(const leveldb::Slice& slice) -> std::shared_ptr<TrackData> {
|
||||
return nullptr;
|
||||
}
|
||||
auto vals = item->asArray();
|
||||
if (vals->size() != 4 || vals->get(0)->type() != cppbor::UINT ||
|
||||
if (vals->size() != 6 || vals->get(0)->type() != cppbor::UINT ||
|
||||
vals->get(1)->type() != cppbor::TSTR ||
|
||||
vals->get(2)->type() != cppbor::UINT ||
|
||||
vals->get(3)->type() != cppbor::SIMPLE) {
|
||||
vals->get(3)->type() != cppbor::SIMPLE ||
|
||||
vals->get(4)->type() != cppbor::UINT ||
|
||||
vals->get(5)->type() != cppbor::UINT) {
|
||||
return {};
|
||||
}
|
||||
TrackId id = vals->get(0)->asUint()->unsignedValue();
|
||||
auto path = vals->get(1)->asViewTstr()->view();
|
||||
uint64_t hash = vals->get(2)->asUint()->unsignedValue();
|
||||
bool tombstoned = vals->get(3)->asBool()->value();
|
||||
return std::make_shared<TrackData>(
|
||||
id, std::pmr::string{path.data(), path.size()}, hash, tombstoned);
|
||||
auto modified_at = std::make_pair<uint16_t, uint16_t>(
|
||||
vals->get(4)->asUint()->unsignedValue(),
|
||||
vals->get(5)->asUint()->unsignedValue());
|
||||
return std::make_shared<TrackData>(id,
|
||||
std::pmr::string{path.data(), path.size()},
|
||||
hash, tombstoned, modified_at);
|
||||
}
|
||||
|
||||
/* 'H/ 0xBEEF' */
|
||||
|
||||
@@ -53,15 +53,15 @@ auto TrackTags::Hash() const -> uint64_t {
|
||||
}
|
||||
|
||||
auto TrackData::UpdateHash(uint64_t new_hash) const -> TrackData {
|
||||
return TrackData(id_, filepath_, new_hash, is_tombstoned_);
|
||||
return TrackData(id_, filepath_, new_hash, is_tombstoned_, modified_at_);
|
||||
}
|
||||
|
||||
auto TrackData::Entomb() const -> TrackData {
|
||||
return TrackData(id_, filepath_, tags_hash_, true);
|
||||
return TrackData(id_, filepath_, tags_hash_, true, modified_at_);
|
||||
}
|
||||
|
||||
auto TrackData::Exhume(const std::pmr::string& new_path) const -> TrackData {
|
||||
return TrackData(id_, new_path, tags_hash_, false);
|
||||
return TrackData(id_, new_path, tags_hash_, false, modified_at_);
|
||||
}
|
||||
|
||||
auto Track::TitleOrFilename() const -> std::pmr::string {
|
||||
|
||||
@@ -55,6 +55,7 @@ void Running::entry() {
|
||||
|
||||
ESP_LOGI(kTag, "opening database");
|
||||
sFileGatherer = new database::FileGathererImpl();
|
||||
database::Database::Destroy();
|
||||
auto database_res =
|
||||
database::Database::Open(*sFileGatherer, sServices->tag_parser());
|
||||
if (database_res.has_error()) {
|
||||
|
||||
Reference in New Issue
Block a user