File storage rewrite (#2676)

* Restructure data layer part 2 (#2599)
* Refactor and separate image model
* Refactor image query builder
* Handle relationships in image query builder
* Remove relationship management methods
* Refactor gallery model/query builder
* Add scenes to gallery model
* Convert scene model
* Refactor scene models
* Remove unused methods
* Add unit tests for gallery
* Add image tests
* Add scene tests
* Convert unnecessary scene value pointers to values
* Convert unnecessary pointer values to values
* Refactor scene partial
* Add scene partial tests
* Refactor ImagePartial
* Add image partial tests
* Refactor gallery partial update
* Add partial gallery update tests
* Use zero/null package for null values
* Add files and scan system
* Add sqlite implementation for files/folders
* Add unit tests for files/folders
* Image refactors
* Update image data layer
* Refactor gallery model and creation
* Refactor scene model
* Refactor scenes
* Don't set title from filename
* Allow galleries to freely add/remove images
* Add multiple scene file support to graphql and UI
* Add multiple file support for images in graphql/UI
* Add multiple file for galleries in graphql/UI
* Remove use of some deprecated fields
* Remove scene path usage
* Remove gallery path usage
* Remove path from image
* Move funscript to video file
* Refactor caption detection
* Migrate existing data
* Add post commit/rollback hook system
* Lint. Comment out import/export tests
* Add WithDatabase read only wrapper
* Prepend tasks to list
* Add 32 pre-migration
* Add warnings in release and migration notes
This commit is contained in:
WithoutPants
2022-07-13 16:30:54 +10:00
parent 30877c75fb
commit 5495d72849
359 changed files with 43690 additions and 16000 deletions

View File

@@ -5,8 +5,10 @@ package mocks
import (
context "context"
models "github.com/stashapp/stash/pkg/models"
file "github.com/stashapp/stash/pkg/file"
mock "github.com/stretchr/testify/mock"
models "github.com/stashapp/stash/pkg/models"
)
// SceneReaderWriter is an autogenerated mock type for the SceneReaderWriter type
@@ -184,27 +186,18 @@ func (_m *SceneReaderWriter) CountMissingOSHash(ctx context.Context) (int, error
return r0, r1
}
// Create provides a mock function with given fields: ctx, newScene
func (_m *SceneReaderWriter) Create(ctx context.Context, newScene models.Scene) (*models.Scene, error) {
ret := _m.Called(ctx, newScene)
// Create provides a mock function with given fields: ctx, newScene, fileIDs
func (_m *SceneReaderWriter) Create(ctx context.Context, newScene *models.Scene, fileIDs []file.ID) error {
ret := _m.Called(ctx, newScene, fileIDs)
var r0 *models.Scene
if rf, ok := ret.Get(0).(func(context.Context, models.Scene) *models.Scene); ok {
r0 = rf(ctx, newScene)
var r0 error
if rf, ok := ret.Get(0).(func(context.Context, *models.Scene, []file.ID) error); ok {
r0 = rf(ctx, newScene, fileIDs)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).(*models.Scene)
}
r0 = ret.Error(0)
}
var r1 error
if rf, ok := ret.Get(1).(func(context.Context, models.Scene) error); ok {
r1 = rf(ctx, newScene)
} else {
r1 = ret.Error(1)
}
return r0, r1
return r0
}
// DecrementOCounter provides a mock function with given fields: ctx, id
@@ -301,15 +294,15 @@ func (_m *SceneReaderWriter) Find(ctx context.Context, id int) (*models.Scene, e
}
// FindByChecksum provides a mock function with given fields: ctx, checksum
func (_m *SceneReaderWriter) FindByChecksum(ctx context.Context, checksum string) (*models.Scene, error) {
func (_m *SceneReaderWriter) FindByChecksum(ctx context.Context, checksum string) ([]*models.Scene, error) {
ret := _m.Called(ctx, checksum)
var r0 *models.Scene
if rf, ok := ret.Get(0).(func(context.Context, string) *models.Scene); ok {
var r0 []*models.Scene
if rf, ok := ret.Get(0).(func(context.Context, string) []*models.Scene); ok {
r0 = rf(ctx, checksum)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).(*models.Scene)
r0 = ret.Get(0).([]*models.Scene)
}
}
@@ -370,15 +363,15 @@ func (_m *SceneReaderWriter) FindByMovieID(ctx context.Context, movieID int) ([]
}
// FindByOSHash provides a mock function with given fields: ctx, oshash
func (_m *SceneReaderWriter) FindByOSHash(ctx context.Context, oshash string) (*models.Scene, error) {
func (_m *SceneReaderWriter) FindByOSHash(ctx context.Context, oshash string) ([]*models.Scene, error) {
ret := _m.Called(ctx, oshash)
var r0 *models.Scene
if rf, ok := ret.Get(0).(func(context.Context, string) *models.Scene); ok {
var r0 []*models.Scene
if rf, ok := ret.Get(0).(func(context.Context, string) []*models.Scene); ok {
r0 = rf(ctx, oshash)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).(*models.Scene)
r0 = ret.Get(0).([]*models.Scene)
}
}
@@ -393,15 +386,15 @@ func (_m *SceneReaderWriter) FindByOSHash(ctx context.Context, oshash string) (*
}
// FindByPath provides a mock function with given fields: ctx, path
func (_m *SceneReaderWriter) FindByPath(ctx context.Context, path string) (*models.Scene, error) {
func (_m *SceneReaderWriter) FindByPath(ctx context.Context, path string) ([]*models.Scene, error) {
ret := _m.Called(ctx, path)
var r0 *models.Scene
if rf, ok := ret.Get(0).(func(context.Context, string) *models.Scene); ok {
var r0 []*models.Scene
if rf, ok := ret.Get(0).(func(context.Context, string) []*models.Scene); ok {
r0 = rf(ctx, path)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).(*models.Scene)
r0 = ret.Get(0).([]*models.Scene)
}
}
@@ -484,29 +477,6 @@ func (_m *SceneReaderWriter) FindMany(ctx context.Context, ids []int) ([]*models
return r0, r1
}
// GetCaptions provides a mock function with given fields: ctx, sceneID
func (_m *SceneReaderWriter) GetCaptions(ctx context.Context, sceneID int) ([]*models.SceneCaption, error) {
ret := _m.Called(ctx, sceneID)
var r0 []*models.SceneCaption
if rf, ok := ret.Get(0).(func(context.Context, int) []*models.SceneCaption); ok {
r0 = rf(ctx, sceneID)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).([]*models.SceneCaption)
}
}
var r1 error
if rf, ok := ret.Get(1).(func(context.Context, int) error); ok {
r1 = rf(ctx, sceneID)
} else {
r1 = ret.Error(1)
}
return r0, r1
}
// GetCover provides a mock function with given fields: ctx, sceneID
func (_m *SceneReaderWriter) GetCover(ctx context.Context, sceneID int) ([]byte, error) {
ret := _m.Called(ctx, sceneID)
@@ -530,121 +500,6 @@ func (_m *SceneReaderWriter) GetCover(ctx context.Context, sceneID int) ([]byte,
return r0, r1
}
// GetGalleryIDs provides a mock function with given fields: ctx, sceneID
func (_m *SceneReaderWriter) GetGalleryIDs(ctx context.Context, sceneID int) ([]int, error) {
ret := _m.Called(ctx, sceneID)
var r0 []int
if rf, ok := ret.Get(0).(func(context.Context, int) []int); ok {
r0 = rf(ctx, sceneID)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).([]int)
}
}
var r1 error
if rf, ok := ret.Get(1).(func(context.Context, int) error); ok {
r1 = rf(ctx, sceneID)
} else {
r1 = ret.Error(1)
}
return r0, r1
}
// GetMovies provides a mock function with given fields: ctx, sceneID
func (_m *SceneReaderWriter) GetMovies(ctx context.Context, sceneID int) ([]models.MoviesScenes, error) {
ret := _m.Called(ctx, sceneID)
var r0 []models.MoviesScenes
if rf, ok := ret.Get(0).(func(context.Context, int) []models.MoviesScenes); ok {
r0 = rf(ctx, sceneID)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).([]models.MoviesScenes)
}
}
var r1 error
if rf, ok := ret.Get(1).(func(context.Context, int) error); ok {
r1 = rf(ctx, sceneID)
} else {
r1 = ret.Error(1)
}
return r0, r1
}
// GetPerformerIDs provides a mock function with given fields: ctx, sceneID
func (_m *SceneReaderWriter) GetPerformerIDs(ctx context.Context, sceneID int) ([]int, error) {
ret := _m.Called(ctx, sceneID)
var r0 []int
if rf, ok := ret.Get(0).(func(context.Context, int) []int); ok {
r0 = rf(ctx, sceneID)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).([]int)
}
}
var r1 error
if rf, ok := ret.Get(1).(func(context.Context, int) error); ok {
r1 = rf(ctx, sceneID)
} else {
r1 = ret.Error(1)
}
return r0, r1
}
// GetStashIDs provides a mock function with given fields: ctx, sceneID
func (_m *SceneReaderWriter) GetStashIDs(ctx context.Context, sceneID int) ([]*models.StashID, error) {
ret := _m.Called(ctx, sceneID)
var r0 []*models.StashID
if rf, ok := ret.Get(0).(func(context.Context, int) []*models.StashID); ok {
r0 = rf(ctx, sceneID)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).([]*models.StashID)
}
}
var r1 error
if rf, ok := ret.Get(1).(func(context.Context, int) error); ok {
r1 = rf(ctx, sceneID)
} else {
r1 = ret.Error(1)
}
return r0, r1
}
// GetTagIDs provides a mock function with given fields: ctx, sceneID
func (_m *SceneReaderWriter) GetTagIDs(ctx context.Context, sceneID int) ([]int, error) {
ret := _m.Called(ctx, sceneID)
var r0 []int
if rf, ok := ret.Get(0).(func(context.Context, int) []int); ok {
r0 = rf(ctx, sceneID)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).([]int)
}
}
var r1 error
if rf, ok := ret.Get(1).(func(context.Context, int) error); ok {
r1 = rf(ctx, sceneID)
} else {
r1 = ret.Error(1)
}
return r0, r1
}
// IncrementOCounter provides a mock function with given fields: ctx, id
func (_m *SceneReaderWriter) IncrementOCounter(ctx context.Context, id int) (int, error) {
ret := _m.Called(ctx, id)
@@ -732,35 +587,12 @@ func (_m *SceneReaderWriter) Size(ctx context.Context) (float64, error) {
}
// Update provides a mock function with given fields: ctx, updatedScene
func (_m *SceneReaderWriter) Update(ctx context.Context, updatedScene models.ScenePartial) (*models.Scene, error) {
func (_m *SceneReaderWriter) Update(ctx context.Context, updatedScene *models.Scene) error {
ret := _m.Called(ctx, updatedScene)
var r0 *models.Scene
if rf, ok := ret.Get(0).(func(context.Context, models.ScenePartial) *models.Scene); ok {
r0 = rf(ctx, updatedScene)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).(*models.Scene)
}
}
var r1 error
if rf, ok := ret.Get(1).(func(context.Context, models.ScenePartial) error); ok {
r1 = rf(ctx, updatedScene)
} else {
r1 = ret.Error(1)
}
return r0, r1
}
// UpdateCaptions provides a mock function with given fields: ctx, id, captions
func (_m *SceneReaderWriter) UpdateCaptions(ctx context.Context, id int, captions []*models.SceneCaption) error {
ret := _m.Called(ctx, id, captions)
var r0 error
if rf, ok := ret.Get(0).(func(context.Context, int, []*models.SceneCaption) error); ok {
r0 = rf(ctx, id, captions)
if rf, ok := ret.Get(0).(func(context.Context, *models.Scene) error); ok {
r0 = rf(ctx, updatedScene)
} else {
r0 = ret.Error(0)
}
@@ -782,27 +614,13 @@ func (_m *SceneReaderWriter) UpdateCover(ctx context.Context, sceneID int, cover
return r0
}
// UpdateFileModTime provides a mock function with given fields: ctx, id, modTime
func (_m *SceneReaderWriter) UpdateFileModTime(ctx context.Context, id int, modTime models.NullSQLiteTimestamp) error {
ret := _m.Called(ctx, id, modTime)
var r0 error
if rf, ok := ret.Get(0).(func(context.Context, int, models.NullSQLiteTimestamp) error); ok {
r0 = rf(ctx, id, modTime)
} else {
r0 = ret.Error(0)
}
return r0
}
// UpdateFull provides a mock function with given fields: ctx, updatedScene
func (_m *SceneReaderWriter) UpdateFull(ctx context.Context, updatedScene models.Scene) (*models.Scene, error) {
ret := _m.Called(ctx, updatedScene)
// UpdatePartial provides a mock function with given fields: ctx, id, updatedScene
func (_m *SceneReaderWriter) UpdatePartial(ctx context.Context, id int, updatedScene models.ScenePartial) (*models.Scene, error) {
ret := _m.Called(ctx, id, updatedScene)
var r0 *models.Scene
if rf, ok := ret.Get(0).(func(context.Context, models.Scene) *models.Scene); ok {
r0 = rf(ctx, updatedScene)
if rf, ok := ret.Get(0).(func(context.Context, int, models.ScenePartial) *models.Scene); ok {
r0 = rf(ctx, id, updatedScene)
} else {
if ret.Get(0) != nil {
r0 = ret.Get(0).(*models.Scene)
@@ -810,8 +628,8 @@ func (_m *SceneReaderWriter) UpdateFull(ctx context.Context, updatedScene models
}
var r1 error
if rf, ok := ret.Get(1).(func(context.Context, models.Scene) error); ok {
r1 = rf(ctx, updatedScene)
if rf, ok := ret.Get(1).(func(context.Context, int, models.ScenePartial) error); ok {
r1 = rf(ctx, id, updatedScene)
} else {
r1 = ret.Error(1)
}
@@ -819,76 +637,6 @@ func (_m *SceneReaderWriter) UpdateFull(ctx context.Context, updatedScene models
return r0, r1
}
// UpdateGalleries provides a mock function with given fields: ctx, sceneID, galleryIDs
func (_m *SceneReaderWriter) UpdateGalleries(ctx context.Context, sceneID int, galleryIDs []int) error {
ret := _m.Called(ctx, sceneID, galleryIDs)
var r0 error
if rf, ok := ret.Get(0).(func(context.Context, int, []int) error); ok {
r0 = rf(ctx, sceneID, galleryIDs)
} else {
r0 = ret.Error(0)
}
return r0
}
// UpdateMovies provides a mock function with given fields: ctx, sceneID, movies
func (_m *SceneReaderWriter) UpdateMovies(ctx context.Context, sceneID int, movies []models.MoviesScenes) error {
ret := _m.Called(ctx, sceneID, movies)
var r0 error
if rf, ok := ret.Get(0).(func(context.Context, int, []models.MoviesScenes) error); ok {
r0 = rf(ctx, sceneID, movies)
} else {
r0 = ret.Error(0)
}
return r0
}
// UpdatePerformers provides a mock function with given fields: ctx, sceneID, performerIDs
func (_m *SceneReaderWriter) UpdatePerformers(ctx context.Context, sceneID int, performerIDs []int) error {
ret := _m.Called(ctx, sceneID, performerIDs)
var r0 error
if rf, ok := ret.Get(0).(func(context.Context, int, []int) error); ok {
r0 = rf(ctx, sceneID, performerIDs)
} else {
r0 = ret.Error(0)
}
return r0
}
// UpdateStashIDs provides a mock function with given fields: ctx, sceneID, stashIDs
func (_m *SceneReaderWriter) UpdateStashIDs(ctx context.Context, sceneID int, stashIDs []models.StashID) error {
ret := _m.Called(ctx, sceneID, stashIDs)
var r0 error
if rf, ok := ret.Get(0).(func(context.Context, int, []models.StashID) error); ok {
r0 = rf(ctx, sceneID, stashIDs)
} else {
r0 = ret.Error(0)
}
return r0
}
// UpdateTags provides a mock function with given fields: ctx, sceneID, tagIDs
func (_m *SceneReaderWriter) UpdateTags(ctx context.Context, sceneID int, tagIDs []int) error {
ret := _m.Called(ctx, sceneID, tagIDs)
var r0 error
if rf, ok := ret.Get(0).(func(context.Context, int, []int) error); ok {
r0 = rf(ctx, sceneID, tagIDs)
} else {
r0 = ret.Error(0)
}
return r0
}
// Wall provides a mock function with given fields: ctx, q
func (_m *SceneReaderWriter) Wall(ctx context.Context, q *string) ([]*models.Scene, error) {
ret := _m.Called(ctx, q)