mirror of
https://github.com/navidrome/navidrome.git
synced 2025-04-03 20:47:35 +03:00
Added a new layer: engine (equivalent to use cases in Clean Architecture). Should make testing things easier
This commit is contained in:
parent
56e9ad3def
commit
91c660c746
6 changed files with 91 additions and 39 deletions
|
@ -1,23 +1,23 @@
|
|||
package api
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"github.com/astaxie/beego"
|
||||
"github.com/deluan/gosonic/api/responses"
|
||||
"github.com/deluan/gosonic/consts"
|
||||
"github.com/deluan/gosonic/domain"
|
||||
"github.com/deluan/gosonic/engine"
|
||||
"github.com/deluan/gosonic/utils"
|
||||
"github.com/karlkfi/inject"
|
||||
"strconv"
|
||||
)
|
||||
|
||||
type GetIndexesController struct {
|
||||
BaseAPIController
|
||||
repo domain.ArtistIndexRepository
|
||||
properties domain.PropertyRepository
|
||||
browser engine.Browser
|
||||
}
|
||||
|
||||
func (c *GetIndexesController) Prepare() {
|
||||
inject.ExtractAssignable(utils.Graph, &c.repo)
|
||||
inject.ExtractAssignable(utils.Graph, &c.browser)
|
||||
inject.ExtractAssignable(utils.Graph, &c.properties)
|
||||
}
|
||||
|
||||
|
@ -25,40 +25,28 @@ func (c *GetIndexesController) Prepare() {
|
|||
func (c *GetIndexesController) Get() {
|
||||
var err error
|
||||
|
||||
ifModifiedSince := c.Input().Get("ifModifiedSince")
|
||||
if ifModifiedSince == "" {
|
||||
ifModifiedSince = "0"
|
||||
}
|
||||
var ifModifiedSince int64
|
||||
c.Ctx.Input.Bind(&ifModifiedSince, "ifModifiedSince")
|
||||
|
||||
res := responses.Indexes{}
|
||||
res.IgnoredArticles = beego.AppConfig.String("ignoredArticles")
|
||||
|
||||
res.LastModified, err = c.properties.DefaultGet(consts.LastScan, "-1")
|
||||
indexes, lastModified, err := c.browser.Indexes(utils.ToTime(ifModifiedSince))
|
||||
if err != nil {
|
||||
beego.Error("Error retrieving LastScan property:", err)
|
||||
beego.Error("Error retrieving Indexes:", err)
|
||||
c.SendError(responses.ERROR_GENERIC, "Internal Error")
|
||||
}
|
||||
|
||||
i, _ := strconv.Atoi(ifModifiedSince)
|
||||
l, _ := strconv.Atoi(res.LastModified)
|
||||
res := responses.Indexes{
|
||||
IgnoredArticles: beego.AppConfig.String("ignoredArticles"),
|
||||
LastModified: fmt.Sprint(utils.ToMillis(lastModified)),
|
||||
}
|
||||
|
||||
if l > i {
|
||||
indexes, err := c.repo.GetAll()
|
||||
if err != nil {
|
||||
beego.Error("Error retrieving Indexes:", err)
|
||||
c.SendError(responses.ERROR_GENERIC, "Internal Error")
|
||||
res.Index = make([]responses.Index, len(indexes))
|
||||
for i, idx := range indexes {
|
||||
res.Index[i].Name = idx.Id
|
||||
res.Index[i].Artists = make([]responses.Artist, len(idx.Artists))
|
||||
for j, a := range idx.Artists {
|
||||
res.Index[i].Artists[j].Id = a.ArtistId
|
||||
res.Index[i].Artists[j].Name = a.Artist
|
||||
}
|
||||
|
||||
res.Index = make([]responses.Index, len(indexes))
|
||||
for i, idx := range indexes {
|
||||
res.Index[i].Name = idx.Id
|
||||
res.Index[i].Artists = make([]responses.Artist, len(idx.Artists))
|
||||
for j, a := range idx.Artists {
|
||||
res.Index[i].Artists[j].Id = a.ArtistId
|
||||
res.Index[i].Artists[j].Name = a.Artist
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
response := c.NewEmpty()
|
||||
|
|
|
@ -2,22 +2,22 @@ package api
|
|||
|
||||
import (
|
||||
"github.com/deluan/gosonic/api/responses"
|
||||
"github.com/deluan/gosonic/domain"
|
||||
"github.com/deluan/gosonic/engine"
|
||||
"github.com/deluan/gosonic/utils"
|
||||
"github.com/karlkfi/inject"
|
||||
)
|
||||
|
||||
type GetMusicFoldersController struct {
|
||||
BaseAPIController
|
||||
repo domain.MediaFolderRepository
|
||||
browser engine.Browser
|
||||
}
|
||||
|
||||
func (c *GetMusicFoldersController) Prepare() {
|
||||
inject.ExtractAssignable(utils.Graph, &c.repo)
|
||||
inject.ExtractAssignable(utils.Graph, &c.browser)
|
||||
}
|
||||
|
||||
func (c *GetMusicFoldersController) Get() {
|
||||
mediaFolderList, _ := c.repo.GetAll()
|
||||
mediaFolderList, _ := c.browser.MediaFolders()
|
||||
folders := make([]responses.MusicFolder, len(mediaFolderList))
|
||||
for i, f := range mediaFolderList {
|
||||
folders[i].Id = f.Id
|
||||
|
|
|
@ -2,15 +2,20 @@ package conf
|
|||
|
||||
import (
|
||||
"github.com/deluan/gosonic/domain"
|
||||
"github.com/deluan/gosonic/engine"
|
||||
"github.com/deluan/gosonic/persistence"
|
||||
"github.com/deluan/gosonic/utils"
|
||||
)
|
||||
|
||||
func init() {
|
||||
utils.DefineSingleton(new(domain.ArtistIndexRepository), persistence.NewArtistIndexRepository)
|
||||
utils.DefineSingleton(new(domain.PropertyRepository), persistence.NewPropertyRepository)
|
||||
utils.DefineSingleton(new(domain.MediaFolderRepository), persistence.NewMediaFolderRepository)
|
||||
// Persistence
|
||||
ir := utils.DefineSingleton(new(domain.ArtistIndexRepository), persistence.NewArtistIndexRepository)
|
||||
pr := utils.DefineSingleton(new(domain.PropertyRepository), persistence.NewPropertyRepository)
|
||||
mfr := utils.DefineSingleton(new(domain.MediaFolderRepository), persistence.NewMediaFolderRepository)
|
||||
utils.DefineSingleton(new(domain.ArtistRepository), persistence.NewArtistRepository)
|
||||
utils.DefineSingleton(new(domain.AlbumRepository), persistence.NewAlbumRepository)
|
||||
utils.DefineSingleton(new(domain.MediaFileRepository), persistence.NewMediaFileRepository)
|
||||
|
||||
// Engine (Use cases)
|
||||
utils.DefineSingleton(new(engine.Browser), engine.NewBrowser, pr, mfr, ir)
|
||||
}
|
||||
|
|
47
engine/browser.go
Normal file
47
engine/browser.go
Normal file
|
@ -0,0 +1,47 @@
|
|||
package engine
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"github.com/deluan/gosonic/consts"
|
||||
"github.com/deluan/gosonic/domain"
|
||||
"github.com/deluan/gosonic/utils"
|
||||
"strconv"
|
||||
"time"
|
||||
)
|
||||
|
||||
type Browser interface {
|
||||
MediaFolders() (domain.MediaFolders, error)
|
||||
Indexes(ifModifiedSince time.Time) (domain.ArtistIndexes, time.Time, error)
|
||||
}
|
||||
|
||||
func NewBrowser(propRepo domain.PropertyRepository, folderRepo domain.MediaFolderRepository, indexRepo domain.ArtistIndexRepository) Browser {
|
||||
return browser{propRepo, folderRepo, indexRepo}
|
||||
}
|
||||
|
||||
type browser struct {
|
||||
propRepo domain.PropertyRepository
|
||||
folderRepo domain.MediaFolderRepository
|
||||
indexRepo domain.ArtistIndexRepository
|
||||
}
|
||||
|
||||
func (b browser) MediaFolders() (domain.MediaFolders, error) {
|
||||
return b.folderRepo.GetAll()
|
||||
}
|
||||
|
||||
func (b browser) Indexes(ifModifiedSince time.Time) (domain.ArtistIndexes, time.Time, error) {
|
||||
l, err := b.propRepo.DefaultGet(consts.LastScan, "-1")
|
||||
ms, _ := strconv.ParseInt(l, 10, 64)
|
||||
lastModified := utils.ToTime(ms)
|
||||
|
||||
if err != nil {
|
||||
return domain.ArtistIndexes{}, time.Time{}, errors.New(fmt.Sprintf("Error retrieving LastScan property: %v", err))
|
||||
}
|
||||
|
||||
if lastModified.After(ifModifiedSince) {
|
||||
indexes, err := b.indexRepo.GetAll()
|
||||
return indexes, lastModified, err
|
||||
}
|
||||
|
||||
return domain.ArtistIndexes{}, lastModified, nil
|
||||
}
|
|
@ -11,7 +11,7 @@ var (
|
|||
definitions map[reflect.Type]interface{}
|
||||
)
|
||||
|
||||
func DefineSingleton(ptr interface{}, constructor interface{}, args ...interface{}) {
|
||||
func DefineSingleton(ptr interface{}, constructor interface{}, args ...interface{}) interface{} {
|
||||
typ := reflect.TypeOf(ptr)
|
||||
provider := inject.NewProvider(constructor, args...)
|
||||
|
||||
|
@ -21,6 +21,7 @@ func DefineSingleton(ptr interface{}, constructor interface{}, args ...interface
|
|||
definitions[typ] = ptr
|
||||
}
|
||||
Graph.Define(ptr, provider)
|
||||
return ptr
|
||||
}
|
||||
|
||||
func init() {
|
||||
|
|
11
utils/time.go
Normal file
11
utils/time.go
Normal file
|
@ -0,0 +1,11 @@
|
|||
package utils
|
||||
|
||||
import "time"
|
||||
|
||||
func ToTime(millis int64) time.Time {
|
||||
return time.Unix(0, millis*int64(time.Millisecond))
|
||||
}
|
||||
|
||||
func ToMillis(t time.Time) int64 {
|
||||
return t.UnixNano() / int64(time.Millisecond)
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue