design: Draft out library changes
I added in an update_all() button and combined two identical database structures. Hopefully this will help to clean up the code. I also added in wording for how to use the idle queue to scan paths. Signed-off-by: Anna Schumaker <schumaker.anna@gmail.com>
This commit is contained in:
parent
114c22bb12
commit
e484653d71
85
design.txt
85
design.txt
|
@ -546,9 +546,6 @@ Library: (lib/library.cpp)
|
|||
storing content. The library will exist in a library namespace to
|
||||
to make functions and classes more unique.
|
||||
|
||||
When a library : Track is created, it should be added to the "Library"
|
||||
group if it is NOT a member of the banned songs group.
|
||||
|
||||
- Databases:
|
||||
enum DB_Type {
|
||||
DB_ALBUM,
|
||||
|
@ -561,28 +558,20 @@ Library: (lib/library.cpp)
|
|||
- Album:
|
||||
class library :: Album : public DatabaseEntry {
|
||||
public:
|
||||
/* primary_key = "$year$name" */
|
||||
string name;
|
||||
string name_lc;
|
||||
string name_lower;
|
||||
unsigned int year;
|
||||
unsigned int artist_id;
|
||||
};
|
||||
|
||||
File << artist_id << year << name
|
||||
|
||||
- Artist:
|
||||
class library :: Artist : public DatabaseEntry {
|
||||
- Artist and Genre:
|
||||
class library :: AGInfo : public DatabaseEntry {
|
||||
public:
|
||||
string name;
|
||||
string name_lc;
|
||||
};
|
||||
|
||||
File << name
|
||||
|
||||
- Genre:
|
||||
class library :: Genre : public DatabaseEntry {
|
||||
public:
|
||||
string name;
|
||||
string name_lc;
|
||||
string name; /* primary key */
|
||||
string name_lower;
|
||||
};
|
||||
|
||||
File << name
|
||||
|
@ -590,7 +579,7 @@ Library: (lib/library.cpp)
|
|||
- Library:
|
||||
class library :: Library : public DatabaseEntry {
|
||||
public:
|
||||
string root_path;
|
||||
string root_path; /* primary_key */
|
||||
unsigned int count;
|
||||
bool enabled;
|
||||
};
|
||||
|
@ -603,6 +592,7 @@ Library: (lib/library.cpp)
|
|||
|
||||
class library :: Track : public DatabaseEntry {
|
||||
public:
|
||||
/* primary_key = library.root_path + "/" + filepath */
|
||||
unsigned int library_id;
|
||||
unsigned int artist_id;
|
||||
unsigned int album_id;
|
||||
|
@ -615,50 +605,47 @@ Library: (lib/library.cpp)
|
|||
unsigned int play_count;
|
||||
unsigned int length;
|
||||
|
||||
bool banned;
|
||||
string title;
|
||||
string title_lc;
|
||||
string length_str;
|
||||
string title;
|
||||
string title_lower;
|
||||
string filepath;
|
||||
};
|
||||
|
||||
File << library_id << artist_id << album_id << genre_id << track << last_year
|
||||
File << last_month << last_day << play_count << length << banned << endl
|
||||
File << library_id << artist_id << album_id << genre_id;
|
||||
File << track << last_year << last_month << last_day << play_count;
|
||||
File << length << length_str << endl
|
||||
File << title << endl;
|
||||
File << filepath << endl;
|
||||
|
||||
- Song:
|
||||
struct Song {
|
||||
library :: Album *album;
|
||||
library :: Artist *artist;
|
||||
library :: Genre *genre;
|
||||
library :: AGInfo *artist;
|
||||
library :: AGInfo *genre;
|
||||
library :: Library *library;
|
||||
library :: Track *track;
|
||||
};
|
||||
|
||||
- Databases:
|
||||
Database<library :: Album> album_db(album.db);
|
||||
Database<library :: Artist> artist_db(artist.db);
|
||||
Database<library :: Genre> genre_db(genre.db);
|
||||
Database<library :: AGInfo> artist_db(artist.db);
|
||||
Database<library :: AGInfo> genre_db(genre.db);
|
||||
Database<library :: Library> library_db(library.db);
|
||||
Database<library :: Track> track_db(track.db);
|
||||
|
||||
- Updating algorithm:
|
||||
1) For each track currently in the library, check if the track exists
|
||||
in the filesystem and mark the track invalid if it does not.
|
||||
2) For each file in the scan directory, check if the track exists in
|
||||
the track is already in the track_db.
|
||||
2a) If the file is in the db, do nothing.
|
||||
2b) Else, add track to the library and the filter index.
|
||||
3) Save all databases
|
||||
1) Use a single IdleTask to loop over each track in the library, check
|
||||
if the track still exists in the filesystem and remove it from
|
||||
library_db if not.
|
||||
2) For each directory in the scan directory, create an IdleTask to
|
||||
scan the next level of directories.
|
||||
3) For each file in the scan directory, check if the file already
|
||||
exists in the track_db and add it to the database if not. Save
|
||||
each database after adding files.
|
||||
|
||||
The taglib library should be used for finding artist, album, etc. tags
|
||||
for each track.
|
||||
|
||||
Use idle tasks for step 2 to break up tagging new files into chunks.
|
||||
This way the user will still be able to use Ocarina and scanning can
|
||||
happen while idle.
|
||||
|
||||
- Importing
|
||||
Ocarina 5.11 stores library files in ~/.ocarina/library/. Importing
|
||||
involves reading each file and adding them to the database. If the file
|
||||
|
@ -696,7 +683,7 @@ Library: (lib/library.cpp)
|
|||
void library :: init();
|
||||
Initialize databases and read files from disk. While reading
|
||||
the library:
|
||||
- Update the count of treacks in each library path
|
||||
- Update the count of tracks in each library path
|
||||
- Find the lowercase text of artist, album, genre, track
|
||||
|
||||
void library :: add_path(string dir);
|
||||
|
@ -708,29 +695,35 @@ Library: (lib/library.cpp)
|
|||
|
||||
void library :: del_path(unsigned int lib_id);
|
||||
Invalidate a library_db row and all tracks owned by that path
|
||||
if lib_id is not valid, throw -EEXIST.
|
||||
|
||||
void library :: update_path(lib_id);
|
||||
Update the given library_db row, if valid.
|
||||
Update the given library_db row.
|
||||
If lib_id is not valid, throw -EEXIST.
|
||||
|
||||
void library :: update_all();
|
||||
Update all library paths.
|
||||
|
||||
struct Song library :: lookup(track_id);
|
||||
Fill out a Song structure for the provided track_id. Throw
|
||||
-EEXIST if there is no track mapping to track_id.
|
||||
Fill out a Song structure for the provided track_id.
|
||||
Throw -EEXIST if there is no track mapping to track_id.
|
||||
|
||||
struct library :: Library *library :: get_path_info(unsigned int id);
|
||||
Return the library path with index id. Throw -EEXIST if there
|
||||
is no such path.
|
||||
Return the library path with index id.
|
||||
Throw -EEXIST if there is no such path.
|
||||
|
||||
void library :: import();
|
||||
Call this function to import an Ocarina 5.11 style library,
|
||||
following the "Importing" section above.
|
||||
|
||||
#ifdef CONFIG_DEBUG
|
||||
#ifdef CONFIG_TEST
|
||||
void library :: print_db(DB_Type);
|
||||
Print the database corresponding to DB_Type
|
||||
|
||||
void library :: reset();
|
||||
Clear all databases, returning the library to an empty state.
|
||||
endif /* CONFIG_DEBUG */
|
||||
endif /* CONFIG_TEST */
|
||||
|
||||
|
||||
|
||||
|
||||
|
|
|
@ -19,9 +19,6 @@ Library: (lib/library.cpp)
|
|||
storing content. The library will exist in a library namespace to
|
||||
to make functions and classes more unique.
|
||||
|
||||
When a library : Track is created, it should be added to the "Library"
|
||||
group if it is NOT a member of the banned songs group.
|
||||
|
||||
- Databases:
|
||||
enum DB_Type {
|
||||
DB_ALBUM,
|
||||
|
@ -34,28 +31,20 @@ Library: (lib/library.cpp)
|
|||
- Album:
|
||||
class library :: Album : public DatabaseEntry {
|
||||
public:
|
||||
/* primary_key = "$year$name" */
|
||||
string name;
|
||||
string name_lc;
|
||||
string name_lower;
|
||||
unsigned int year;
|
||||
unsigned int artist_id;
|
||||
};
|
||||
|
||||
File << artist_id << year << name
|
||||
|
||||
- Artist:
|
||||
class library :: Artist : public DatabaseEntry {
|
||||
- Artist and Genre:
|
||||
class library :: AGInfo : public DatabaseEntry {
|
||||
public:
|
||||
string name;
|
||||
string name_lc;
|
||||
};
|
||||
|
||||
File << name
|
||||
|
||||
- Genre:
|
||||
class library :: Genre : public DatabaseEntry {
|
||||
public:
|
||||
string name;
|
||||
string name_lc;
|
||||
string name; /* primary key */
|
||||
string name_lower;
|
||||
};
|
||||
|
||||
File << name
|
||||
|
@ -63,7 +52,7 @@ Library: (lib/library.cpp)
|
|||
- Library:
|
||||
class library :: Library : public DatabaseEntry {
|
||||
public:
|
||||
string root_path;
|
||||
string root_path; /* primary_key */
|
||||
unsigned int count;
|
||||
bool enabled;
|
||||
};
|
||||
|
@ -76,6 +65,7 @@ Library: (lib/library.cpp)
|
|||
|
||||
class library :: Track : public DatabaseEntry {
|
||||
public:
|
||||
/* primary_key = library.root_path + "/" + filepath */
|
||||
unsigned int library_id;
|
||||
unsigned int artist_id;
|
||||
unsigned int album_id;
|
||||
|
@ -88,50 +78,47 @@ Library: (lib/library.cpp)
|
|||
unsigned int play_count;
|
||||
unsigned int length;
|
||||
|
||||
bool banned;
|
||||
string title;
|
||||
string title_lc;
|
||||
string length_str;
|
||||
string title;
|
||||
string title_lower;
|
||||
string filepath;
|
||||
};
|
||||
|
||||
File << library_id << artist_id << album_id << genre_id << track << last_year
|
||||
File << last_month << last_day << play_count << length << banned << endl
|
||||
File << library_id << artist_id << album_id << genre_id;
|
||||
File << track << last_year << last_month << last_day << play_count;
|
||||
File << length << length_str << endl
|
||||
File << title << endl;
|
||||
File << filepath << endl;
|
||||
|
||||
- Song:
|
||||
struct Song {
|
||||
library :: Album *album;
|
||||
library :: Artist *artist;
|
||||
library :: Genre *genre;
|
||||
library :: AGInfo *artist;
|
||||
library :: AGInfo *genre;
|
||||
library :: Library *library;
|
||||
library :: Track *track;
|
||||
};
|
||||
|
||||
- Databases:
|
||||
Database<library :: Album> album_db(album.db);
|
||||
Database<library :: Artist> artist_db(artist.db);
|
||||
Database<library :: Genre> genre_db(genre.db);
|
||||
Database<library :: AGInfo> artist_db(artist.db);
|
||||
Database<library :: AGInfo> genre_db(genre.db);
|
||||
Database<library :: Library> library_db(library.db);
|
||||
Database<library :: Track> track_db(track.db);
|
||||
|
||||
- Updating algorithm:
|
||||
1) For each track currently in the library, check if the track exists
|
||||
in the filesystem and mark the track invalid if it does not.
|
||||
2) For each file in the scan directory, check if the track exists in
|
||||
the track is already in the track_db.
|
||||
2a) If the file is in the db, do nothing.
|
||||
2b) Else, add track to the library and the filter index.
|
||||
3) Save all databases
|
||||
1) Use a single IdleTask to loop over each track in the library, check
|
||||
if the track still exists in the filesystem and remove it from
|
||||
library_db if not.
|
||||
2) For each directory in the scan directory, create an IdleTask to
|
||||
scan the next level of directories.
|
||||
3) For each file in the scan directory, check if the file already
|
||||
exists in the track_db and add it to the database if not. Save
|
||||
each database after adding files.
|
||||
|
||||
The taglib library should be used for finding artist, album, etc. tags
|
||||
for each track.
|
||||
|
||||
Use idle tasks for step 2 to break up tagging new files into chunks.
|
||||
This way the user will still be able to use Ocarina and scanning can
|
||||
happen while idle.
|
||||
|
||||
- Importing
|
||||
Ocarina 5.11 stores library files in ~/.ocarina/library/. Importing
|
||||
involves reading each file and adding them to the database. If the file
|
||||
|
@ -169,7 +156,7 @@ Library: (lib/library.cpp)
|
|||
void library :: init();
|
||||
Initialize databases and read files from disk. While reading
|
||||
the library:
|
||||
- Update the count of treacks in each library path
|
||||
- Update the count of tracks in each library path
|
||||
- Find the lowercase text of artist, album, genre, track
|
||||
|
||||
void library :: add_path(string dir);
|
||||
|
@ -181,26 +168,32 @@ Library: (lib/library.cpp)
|
|||
|
||||
void library :: del_path(unsigned int lib_id);
|
||||
Invalidate a library_db row and all tracks owned by that path
|
||||
if lib_id is not valid, throw -EEXIST.
|
||||
|
||||
void library :: update_path(lib_id);
|
||||
Update the given library_db row, if valid.
|
||||
Update the given library_db row.
|
||||
If lib_id is not valid, throw -EEXIST.
|
||||
|
||||
void library :: update_all();
|
||||
Update all library paths.
|
||||
|
||||
struct Song library :: lookup(track_id);
|
||||
Fill out a Song structure for the provided track_id. Throw
|
||||
-EEXIST if there is no track mapping to track_id.
|
||||
Fill out a Song structure for the provided track_id.
|
||||
Throw -EEXIST if there is no track mapping to track_id.
|
||||
|
||||
struct library :: Library *library :: get_path_info(unsigned int id);
|
||||
Return the library path with index id. Throw -EEXIST if there
|
||||
is no such path.
|
||||
Return the library path with index id.
|
||||
Throw -EEXIST if there is no such path.
|
||||
|
||||
void library :: import();
|
||||
Call this function to import an Ocarina 5.11 style library,
|
||||
following the "Importing" section above.
|
||||
|
||||
#ifdef CONFIG_DEBUG
|
||||
#ifdef CONFIG_TEST
|
||||
void library :: print_db(DB_Type);
|
||||
Print the database corresponding to DB_Type
|
||||
|
||||
void library :: reset();
|
||||
Clear all databases, returning the library to an empty state.
|
||||
endif /* CONFIG_DEBUG */
|
||||
endif /* CONFIG_TEST */
|
||||
|
||||
|
|
Loading…
Reference in New Issue