mirror of
https://github.com/navidrome/navidrome.git
synced 2025-04-06 05:57:35 +03:00
SQL/Orm AlbumRepository complete
This commit is contained in:
parent
56273dd4d9
commit
b9815fc653
9 changed files with 196 additions and 19 deletions
102
persistence/db_sql/album_repository.go
Normal file
102
persistence/db_sql/album_repository.go
Normal file
|
@ -0,0 +1,102 @@
|
|||
package db_sql
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"github.com/astaxie/beego/orm"
|
||||
"github.com/cloudsonic/sonic-server/domain"
|
||||
)
|
||||
|
||||
type Album struct {
|
||||
ID string `orm:"pk;column(id)"`
|
||||
Name string `orm:"index"`
|
||||
ArtistID string `orm:"column(artist_id);index"`
|
||||
CoverArtPath string ``
|
||||
CoverArtId string ``
|
||||
Artist string `orm:"index"`
|
||||
AlbumArtist string ``
|
||||
Year int `orm:"index"`
|
||||
Compilation bool ``
|
||||
Starred bool `orm:"index"`
|
||||
PlayCount int `orm:"index"`
|
||||
PlayDate time.Time `orm:"null;index"`
|
||||
SongCount int ``
|
||||
Duration int ``
|
||||
Rating int `orm:"index"`
|
||||
Genre string ``
|
||||
StarredAt time.Time `orm:"null"`
|
||||
CreatedAt time.Time `orm:"null"`
|
||||
UpdatedAt time.Time `orm:"null"`
|
||||
}
|
||||
|
||||
type albumRepository struct {
|
||||
sqlRepository
|
||||
}
|
||||
|
||||
func NewAlbumRepository() domain.AlbumRepository {
|
||||
r := &albumRepository{}
|
||||
r.entityName = "album"
|
||||
return r
|
||||
}
|
||||
|
||||
func (r *albumRepository) Put(a *domain.Album) error {
|
||||
ta := Album(*a)
|
||||
return r.put(a.ID, &ta)
|
||||
}
|
||||
|
||||
func (r *albumRepository) Get(id string) (*domain.Album, error) {
|
||||
ta := Album{ID: id}
|
||||
err := Db().Read(&ta)
|
||||
if err == orm.ErrNoRows {
|
||||
return nil, domain.ErrNotFound
|
||||
}
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
a := domain.Album(ta)
|
||||
return &a, err
|
||||
}
|
||||
|
||||
func (r *albumRepository) FindByArtist(artistId string) (domain.Albums, error) {
|
||||
var albums []Album
|
||||
_, err := r.newQuery(Db()).Filter("artist_id", artistId).OrderBy("year", "name").All(&albums)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return r.toAlbums(albums)
|
||||
}
|
||||
|
||||
func (r *albumRepository) GetAll(options ...domain.QueryOptions) (domain.Albums, error) {
|
||||
var all []Album
|
||||
_, err := r.newQuery(Db(), options...).All(&all)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return r.toAlbums(all)
|
||||
}
|
||||
|
||||
func (r *albumRepository) toAlbums(all []Album) (domain.Albums, error) {
|
||||
result := make(domain.Albums, len(all))
|
||||
for i, a := range all {
|
||||
result[i] = domain.Album(a)
|
||||
}
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (r *albumRepository) PurgeInactive(activeList domain.Albums) ([]string, error) {
|
||||
return r.purgeInactive(activeList, func(item interface{}) string {
|
||||
return item.(domain.Album).ID
|
||||
})
|
||||
}
|
||||
|
||||
func (r *albumRepository) GetStarred(options ...domain.QueryOptions) (domain.Albums, error) {
|
||||
var starred []Album
|
||||
_, err := r.newQuery(Db(), options...).Filter("starred", true).All(&starred)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return r.toAlbums(starred)
|
||||
}
|
||||
|
||||
var _ domain.AlbumRepository = (*albumRepository)(nil)
|
||||
var _ = domain.Album(Album{})
|
67
persistence/db_sql/album_repository_test.go
Normal file
67
persistence/db_sql/album_repository_test.go
Normal file
|
@ -0,0 +1,67 @@
|
|||
package db_sql
|
||||
|
||||
import (
|
||||
"github.com/cloudsonic/sonic-server/domain"
|
||||
. "github.com/onsi/ginkgo"
|
||||
. "github.com/onsi/gomega"
|
||||
)
|
||||
|
||||
var _ = Describe("AlbumRepository", func() {
|
||||
var repo domain.AlbumRepository
|
||||
|
||||
BeforeEach(func() {
|
||||
repo = NewAlbumRepository()
|
||||
})
|
||||
|
||||
Describe("GetAll", func() {
|
||||
It("returns all records", func() {
|
||||
Expect(repo.GetAll()).To(Equal(testAlbums))
|
||||
})
|
||||
|
||||
It("returns all records sorted", func() {
|
||||
Expect(repo.GetAll(domain.QueryOptions{SortBy: "Name"})).To(Equal(domain.Albums{
|
||||
{ID: "2", Name: "Abbey Road", Artist: "The Beatles", ArtistID: "1"},
|
||||
{ID: "3", Name: "Radioactivity", Artist: "Kraftwerk", ArtistID: "2", Starred: true},
|
||||
{ID: "1", Name: "Sgt Peppers", Artist: "The Beatles", ArtistID: "1"},
|
||||
}))
|
||||
})
|
||||
|
||||
It("returns all records sorted desc", func() {
|
||||
Expect(repo.GetAll(domain.QueryOptions{SortBy: "Name", Desc: true})).To(Equal(domain.Albums{
|
||||
{ID: "1", Name: "Sgt Peppers", Artist: "The Beatles", ArtistID: "1"},
|
||||
{ID: "3", Name: "Radioactivity", Artist: "Kraftwerk", ArtistID: "2", Starred: true},
|
||||
{ID: "2", Name: "Abbey Road", Artist: "The Beatles", ArtistID: "1"},
|
||||
}))
|
||||
})
|
||||
|
||||
It("paginates the result", func() {
|
||||
Expect(repo.GetAll(domain.QueryOptions{Offset: 1, Size: 1})).To(Equal(domain.Albums{
|
||||
{ID: "2", Name: "Abbey Road", Artist: "The Beatles", ArtistID: "1"},
|
||||
}))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("GetAllIds", func() {
|
||||
It("returns all records", func() {
|
||||
Expect(repo.GetAllIds()).To(Equal([]string{"1", "2", "3"}))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("GetStarred", func() {
|
||||
It("returns all starred records", func() {
|
||||
Expect(repo.GetStarred(domain.QueryOptions{})).To(Equal(domain.Albums{
|
||||
{ID: "3", Name: "Radioactivity", Artist: "Kraftwerk", ArtistID: "2", Starred: true},
|
||||
}))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("FindByArtist", func() {
|
||||
It("returns all records from a given ArtistID", func() {
|
||||
Expect(repo.FindByArtist("1")).To(Equal(domain.Albums{
|
||||
{ID: "2", Name: "Abbey Road", Artist: "The Beatles", ArtistID: "1"},
|
||||
{ID: "1", Name: "Sgt Peppers", Artist: "The Beatles", ArtistID: "1"},
|
||||
}))
|
||||
})
|
||||
})
|
||||
|
||||
})
|
|
@ -27,7 +27,7 @@ var _ = Describe("ArtistRepository", func() {
|
|||
Expect(err).To(MatchError(domain.ErrNotFound))
|
||||
})
|
||||
|
||||
FDescribe("PurgeInactive", func() {
|
||||
Describe("PurgeInactive", func() {
|
||||
BeforeEach(func() {
|
||||
for _, a := range testArtists {
|
||||
repo.Put(&a)
|
||||
|
|
|
@ -5,7 +5,6 @@ import (
|
|||
|
||||
"github.com/astaxie/beego/orm"
|
||||
"github.com/cloudsonic/sonic-server/domain"
|
||||
"github.com/cloudsonic/sonic-server/persistence"
|
||||
)
|
||||
|
||||
type MediaFile struct {
|
||||
|
@ -90,21 +89,6 @@ func (r *mediaFileRepository) GetStarred(options ...domain.QueryOptions) (domain
|
|||
return r.toMediaFiles(starred)
|
||||
}
|
||||
|
||||
func (r *mediaFileRepository) GetAllIds() ([]string, error) {
|
||||
qs := r.newQuery(Db())
|
||||
var values []orm.Params
|
||||
num, err := qs.Values(&values, "id")
|
||||
if num == 0 {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
result := persistence.CollectValue(values, func(item interface{}) string {
|
||||
return item.(orm.Params)["ID"].(string)
|
||||
})
|
||||
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (r *mediaFileRepository) PurgeInactive(activeList domain.MediaFiles) ([]string, error) {
|
||||
return r.purgeInactive(activeList, func(item interface{}) string {
|
||||
return item.(domain.MediaFile).ID
|
||||
|
|
|
@ -55,6 +55,7 @@ func WithTx(block func(orm.Ormer) error) error {
|
|||
func initORM(dbPath string) error {
|
||||
orm.Debug = true
|
||||
orm.RegisterModel(new(Artist))
|
||||
orm.RegisterModel(new(Album))
|
||||
orm.RegisterModel(new(MediaFile))
|
||||
err := orm.RegisterDataBase("default", "sqlite3", dbPath)
|
||||
if err != nil {
|
||||
|
|
|
@ -38,6 +38,22 @@ func (r *sqlRepository) Exists(id string) (bool, error) {
|
|||
return c == 1, err
|
||||
}
|
||||
|
||||
// TODO This is used to generate random lists. Can be optimized in SQL: https://stackoverflow.com/a/19419
|
||||
func (r *sqlRepository) GetAllIds() ([]string, error) {
|
||||
qs := r.newQuery(Db())
|
||||
var values []orm.Params
|
||||
num, err := qs.Values(&values, "id")
|
||||
if num == 0 {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
result := persistence.CollectValue(values, func(item interface{}) string {
|
||||
return item.(orm.Params)["ID"].(string)
|
||||
})
|
||||
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (r *sqlRepository) put(id string, a interface{}) error {
|
||||
return WithTx(func(o orm.Ormer) error {
|
||||
c, err := r.newQuery(o).Filter("id", id).Count()
|
||||
|
|
|
@ -38,5 +38,12 @@ var _ = Describe("Initialize test DB", func() {
|
|||
for _, a := range testArtists {
|
||||
artistRepo.Put(&a)
|
||||
}
|
||||
albumRepository := NewAlbumRepository()
|
||||
for _, a := range testAlbums {
|
||||
err := albumRepository.Put(&a)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
}
|
||||
})
|
||||
})
|
||||
|
|
|
@ -9,8 +9,8 @@ import (
|
|||
var Set = wire.NewSet(
|
||||
NewArtistRepository,
|
||||
NewMediaFileRepository,
|
||||
NewAlbumRepository,
|
||||
db_ledis.NewPropertyRepository,
|
||||
db_ledis.NewAlbumRepository,
|
||||
db_ledis.NewArtistIndexRepository,
|
||||
db_ledis.NewPlaylistRepository,
|
||||
db_ledis.NewCheckSumRepository,
|
||||
|
|
|
@ -63,7 +63,7 @@ func CreateSubsonicAPIRouter(p persistence.ProviderIdentifier) *api.Router {
|
|||
}
|
||||
|
||||
func createSQLProvider() *Provider {
|
||||
albumRepository := db_ledis.NewAlbumRepository()
|
||||
albumRepository := db_sql.NewAlbumRepository()
|
||||
artistRepository := db_sql.NewArtistRepository()
|
||||
checkSumRepository := db_ledis.NewCheckSumRepository()
|
||||
artistIndexRepository := db_ledis.NewArtistIndexRepository()
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue