summaryrefslogtreecommitdiff
path: root/src/database/include/song.hpp
blob: 79b2160ac48fc918044e09fadae3b0146287a472 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
#pragma once

#include <stdint.h>
#include <cstdint>
#include <optional>
#include <string>

#include "leveldb/db.h"
#include "span.hpp"

namespace database {

typedef uint32_t SongId;

enum Encoding { ENC_UNSUPPORTED, ENC_MP3 };

struct SongTags {
  Encoding encoding;
  std::optional<std::string> title;
  std::optional<std::string> artist;
  std::optional<std::string> album;
  auto Hash() const -> uint64_t;
};

auto ReadAndParseTags(const std::string& path, SongTags* out) -> bool;

class SongData {
 private:
  const SongId id_;
  const std::string filepath_;
  const uint64_t tags_hash_;
  const uint32_t play_count_;
  const bool is_tombstoned_;

 public:
  SongData(SongId id, const std::string& path, uint64_t hash)
      : id_(id),
        filepath_(path),
        tags_hash_(hash),
        play_count_(0),
        is_tombstoned_(false) {}
  SongData(SongId id,
           const std::string& path,
           uint64_t hash,
           uint32_t play_count,
           bool is_tombstoned)
      : id_(id),
        filepath_(path),
        tags_hash_(hash),
        play_count_(play_count),
        is_tombstoned_(is_tombstoned) {}

  auto id() const -> SongId { return id_; }
  auto filepath() const -> std::string { return filepath_; }
  auto play_count() const -> uint32_t { return play_count_; }
  auto tags_hash() const -> uint64_t { return tags_hash_; }
  auto is_tombstoned() const -> bool { return is_tombstoned_; }

  auto UpdateHash(uint64_t new_hash) const -> SongData;
  auto Entomb() const -> SongData;
  auto Exhume(const std::string& new_path) const -> SongData;
};

class Song {
 public:
  Song(SongData data, SongTags tags) : data_(data), tags_(tags) {}

  auto data() -> const SongData& { return data_; }
  auto tags() -> const SongTags& { return tags_; }

 private:
  const SongData data_;
  const SongTags tags_;
};

}  // namespace database