autobrr/internal/database/release_test.go
Kyle Sanderson 6a94ecacca
refactor(http): auth handlers (#1311)
* fix(auth): implement invalid cookie handling

* that escalated quickly

* refactor(http): auth handlers

* add tests for auth handler
* refactor methods

* chore(tests): add header and build tag

* add build tag integration

* chore(tests): run in ci

---------

Co-authored-by: ze0s <ze0s@riseup.net>
2023-12-28 02:04:25 +01:00

637 lines
21 KiB
Go

// Copyright (c) 2021 - 2023, Ludvig Lundgren and the autobrr contributors.
// SPDX-License-Identifier: GPL-2.0-or-later
//go:build integration
package database
import (
"context"
"fmt"
"testing"
"time"
"github.com/autobrr/autobrr/internal/domain"
"github.com/stretchr/testify/assert"
)
func getMockRelease() *domain.Release {
return &domain.Release{
FilterStatus: domain.ReleaseStatusFilterApproved,
Rejections: []string{"test", "not-a-match"},
Indexer: "BTN",
FilterName: "ExampleFilter",
Protocol: domain.ReleaseProtocolTorrent,
Implementation: domain.ReleaseImplementationIRC,
Timestamp: time.Now(),
InfoURL: "https://example.com/info",
DownloadURL: "https://example.com/download",
GroupID: "group123",
TorrentID: "torrent123",
TorrentName: "Example.Torrent.Name",
Size: 123456789,
Title: "Example Title",
Category: "Movie",
Season: 1,
Episode: 2,
Year: 2023,
Resolution: "1080p",
Source: "BluRay",
Codec: []string{"H.264", "AAC"},
Container: "MKV",
HDR: []string{"HDR10", "Dolby Vision"},
Group: "ExampleGroup",
Proper: true,
Repack: false,
Website: "https://example.com",
Type: "Movie",
Origin: "P2P",
Tags: []string{"Action", "Adventure"},
Uploader: "john_doe",
PreTime: "10m",
FilterID: 1,
}
}
func getMockReleaseActionStatus() *domain.ReleaseActionStatus {
return &domain.ReleaseActionStatus{
ID: 0,
Status: domain.ReleasePushStatusApproved,
Action: "okay",
ActionID: 10,
Type: domain.ActionTypeTest,
Client: "qbitorrent",
Filter: "Test filter",
FilterID: 0,
Rejections: []string{"one rejection", "two rejections"},
ReleaseID: 0,
Timestamp: time.Now(),
}
}
func TestReleaseRepo_Store(t *testing.T) {
for dbType, db := range testDBs {
log := setupLoggerForTest()
downloadClientRepo := NewDownloadClientRepo(log, db)
filterRepo := NewFilterRepo(log, db)
actionRepo := NewActionRepo(log, db, downloadClientRepo)
repo := NewReleaseRepo(log, db)
mockData := getMockRelease()
releaseActionMockData := getMockReleaseActionStatus()
actionMockData := getMockAction()
t.Run(fmt.Sprintf("StoreReleaseActionStatus_Succeeds [%s]", dbType), func(t *testing.T) {
// Setup
createdClient, err := downloadClientRepo.Store(context.Background(), getMockDownloadClient())
assert.NoError(t, err)
assert.NotNil(t, createdClient)
err = filterRepo.Store(context.Background(), getMockFilter())
assert.NoError(t, err)
createdFilters, err := filterRepo.ListFilters(context.Background())
assert.NoError(t, err)
assert.NotNil(t, createdFilters)
actionMockData.FilterID = createdFilters[0].ID
actionMockData.ClientID = int32(createdClient.ID)
mockData.FilterID = createdFilters[0].ID
// Execute
err = repo.Store(context.Background(), mockData)
assert.NoError(t, err)
createdAction, err := actionRepo.Store(context.Background(), actionMockData)
assert.NoError(t, err)
releaseActionMockData.ReleaseID = mockData.ID
releaseActionMockData.ActionID = int64(createdAction.ID)
releaseActionMockData.FilterID = int64(createdFilters[0].ID)
err = repo.StoreReleaseActionStatus(context.Background(), releaseActionMockData)
assert.NoError(t, err)
// Verify
assert.NotEqual(t, int64(0), mockData.ID)
// Cleanup
_ = repo.Delete(context.Background(), &domain.DeleteReleaseRequest{OlderThan: 0})
_ = actionRepo.Delete(context.Background(), &domain.DeleteActionRequest{ActionId: createdAction.ID})
_ = filterRepo.Delete(context.Background(), createdFilters[0].ID)
_ = downloadClientRepo.Delete(context.Background(), createdClient.ID)
})
}
}
func TestReleaseRepo_StoreReleaseActionStatus(t *testing.T) {
for dbType, db := range testDBs {
log := setupLoggerForTest()
downloadClientRepo := NewDownloadClientRepo(log, db)
filterRepo := NewFilterRepo(log, db)
actionRepo := NewActionRepo(log, db, downloadClientRepo)
repo := NewReleaseRepo(log, db)
mockData := getMockRelease()
releaseActionMockData := getMockReleaseActionStatus()
actionMockData := getMockAction()
t.Run(fmt.Sprintf("StoreReleaseActionStatus_Succeeds [%s]", dbType), func(t *testing.T) {
// Setup
createdClient, err := downloadClientRepo.Store(context.Background(), getMockDownloadClient())
assert.NoError(t, err)
assert.NotNil(t, createdClient)
err = filterRepo.Store(context.Background(), getMockFilter())
assert.NoError(t, err)
createdFilters, err := filterRepo.ListFilters(context.Background())
assert.NoError(t, err)
assert.NotNil(t, createdFilters)
actionMockData.FilterID = createdFilters[0].ID
actionMockData.ClientID = int32(createdClient.ID)
mockData.FilterID = createdFilters[0].ID
// Execute
err = repo.Store(context.Background(), mockData)
assert.NoError(t, err)
createdAction, err := actionRepo.Store(context.Background(), actionMockData)
assert.NoError(t, err)
releaseActionMockData.ReleaseID = mockData.ID
releaseActionMockData.ActionID = int64(createdAction.ID)
releaseActionMockData.FilterID = int64(createdFilters[0].ID)
err = repo.StoreReleaseActionStatus(context.Background(), releaseActionMockData)
assert.NoError(t, err)
// Verify
assert.NotEqual(t, int64(0), releaseActionMockData.ID)
// Cleanup
_ = repo.Delete(context.Background(), &domain.DeleteReleaseRequest{OlderThan: 0})
_ = actionRepo.Delete(context.Background(), &domain.DeleteActionRequest{ActionId: createdAction.ID})
_ = filterRepo.Delete(context.Background(), createdFilters[0].ID)
_ = downloadClientRepo.Delete(context.Background(), createdClient.ID)
})
}
}
func TestReleaseRepo_Find(t *testing.T) {
for dbType, db := range testDBs {
log := setupLoggerForTest()
downloadClientRepo := NewDownloadClientRepo(log, db)
filterRepo := NewFilterRepo(log, db)
//actionRepo := NewActionRepo(log, db, downloadClientRepo)
repo := NewReleaseRepo(log, db)
mockData := getMockRelease()
//releaseActionMockData := getMockReleaseActionStatus()
actionMockData := getMockAction()
t.Run(fmt.Sprintf("FindReleases_Succeeds [%s]", dbType), func(t *testing.T) {
// Setup
createdClient, err := downloadClientRepo.Store(context.Background(), getMockDownloadClient())
assert.NoError(t, err)
assert.NotNil(t, createdClient)
err = filterRepo.Store(context.Background(), getMockFilter())
assert.NoError(t, err)
createdFilters, err := filterRepo.ListFilters(context.Background())
assert.NoError(t, err)
assert.NotNil(t, createdFilters)
actionMockData.FilterID = createdFilters[0].ID
actionMockData.ClientID = int32(createdClient.ID)
mockData.FilterID = createdFilters[0].ID
// Execute
err = repo.Store(context.Background(), mockData)
assert.NoError(t, err)
// Search with query params
queryParams := domain.ReleaseQueryParams{
Limit: 10,
Offset: 0,
Sort: map[string]string{
"Timestamp": "asc",
},
Search: "",
}
releases, nextCursor, total, err := repo.Find(context.Background(), queryParams)
// Verify
assert.NotNil(t, releases)
assert.NotEqual(t, int64(0), total)
assert.True(t, nextCursor >= 0)
// Cleanup
_ = repo.Delete(context.Background(), &domain.DeleteReleaseRequest{OlderThan: 0})
_ = filterRepo.Delete(context.Background(), createdFilters[0].ID)
_ = downloadClientRepo.Delete(context.Background(), createdClient.ID)
})
}
}
func TestReleaseRepo_FindRecent(t *testing.T) {
for dbType, db := range testDBs {
log := setupLoggerForTest()
downloadClientRepo := NewDownloadClientRepo(log, db)
filterRepo := NewFilterRepo(log, db)
//actionRepo := NewActionRepo(log, db, downloadClientRepo)
repo := NewReleaseRepo(log, db)
mockData := getMockRelease()
//releaseActionMockData := getMockReleaseActionStatus()
actionMockData := getMockAction()
t.Run(fmt.Sprintf("FindRecent_Succeeds [%s]", dbType), func(t *testing.T) {
// Setup
createdClient, err := downloadClientRepo.Store(context.Background(), getMockDownloadClient())
assert.NoError(t, err)
assert.NotNil(t, createdClient)
err = filterRepo.Store(context.Background(), getMockFilter())
assert.NoError(t, err)
createdFilters, err := filterRepo.ListFilters(context.Background())
assert.NoError(t, err)
assert.NotNil(t, createdFilters)
actionMockData.FilterID = createdFilters[0].ID
actionMockData.ClientID = int32(createdClient.ID)
mockData.FilterID = createdFilters[0].ID
// Execute
err = repo.Store(context.Background(), mockData)
assert.NoError(t, err)
releases, err := repo.FindRecent(context.Background())
// Verify
assert.NotNil(t, releases)
assert.Lenf(t, releases, 1, "Expected 1 release, got %d", len(releases))
// Cleanup
_ = repo.Delete(context.Background(), &domain.DeleteReleaseRequest{OlderThan: 0})
_ = filterRepo.Delete(context.Background(), createdFilters[0].ID)
_ = downloadClientRepo.Delete(context.Background(), createdClient.ID)
})
}
}
func TestReleaseRepo_GetIndexerOptions(t *testing.T) {
for dbType, db := range testDBs {
log := setupLoggerForTest()
downloadClientRepo := NewDownloadClientRepo(log, db)
filterRepo := NewFilterRepo(log, db)
actionRepo := NewActionRepo(log, db, downloadClientRepo)
repo := NewReleaseRepo(log, db)
mockData := getMockRelease()
releaseActionMockData := getMockReleaseActionStatus()
actionMockData := getMockAction()
t.Run(fmt.Sprintf("GetIndexerOptions_Succeeds [%s]", dbType), func(t *testing.T) {
// Setup
createdClient, err := downloadClientRepo.Store(context.Background(), getMockDownloadClient())
assert.NoError(t, err)
assert.NotNil(t, createdClient)
err = filterRepo.Store(context.Background(), getMockFilter())
assert.NoError(t, err)
createdFilters, err := filterRepo.ListFilters(context.Background())
assert.NoError(t, err)
assert.NotNil(t, createdFilters)
actionMockData.FilterID = createdFilters[0].ID
actionMockData.ClientID = int32(createdClient.ID)
mockData.FilterID = createdFilters[0].ID
err = repo.Store(context.Background(), mockData)
assert.NoError(t, err)
createdAction, err := actionRepo.Store(context.Background(), actionMockData)
assert.NoError(t, err)
releaseActionMockData.ReleaseID = mockData.ID
releaseActionMockData.ActionID = int64(createdAction.ID)
releaseActionMockData.FilterID = int64(createdFilters[0].ID)
err = repo.StoreReleaseActionStatus(context.Background(), releaseActionMockData)
assert.NoError(t, err)
// Execute
options, err := repo.GetIndexerOptions(context.Background())
// Verify
assert.NotNil(t, options)
assert.Len(t, options, 1)
// Cleanup
_ = repo.Delete(context.Background(), &domain.DeleteReleaseRequest{OlderThan: 0})
_ = actionRepo.Delete(context.Background(), &domain.DeleteActionRequest{ActionId: createdAction.ID})
_ = filterRepo.Delete(context.Background(), createdFilters[0].ID)
_ = downloadClientRepo.Delete(context.Background(), createdClient.ID)
})
}
}
func TestReleaseRepo_GetActionStatusByReleaseID(t *testing.T) {
for dbType, db := range testDBs {
log := setupLoggerForTest()
downloadClientRepo := NewDownloadClientRepo(log, db)
filterRepo := NewFilterRepo(log, db)
actionRepo := NewActionRepo(log, db, downloadClientRepo)
repo := NewReleaseRepo(log, db)
mockData := getMockRelease()
releaseActionMockData := getMockReleaseActionStatus()
actionMockData := getMockAction()
t.Run(fmt.Sprintf("GetActionStatusByReleaseID_Succeeds [%s]", dbType), func(t *testing.T) {
// Setup
createdClient, err := downloadClientRepo.Store(context.Background(), getMockDownloadClient())
assert.NoError(t, err)
assert.NotNil(t, createdClient)
err = filterRepo.Store(context.Background(), getMockFilter())
assert.NoError(t, err)
createdFilters, err := filterRepo.ListFilters(context.Background())
assert.NoError(t, err)
assert.NotNil(t, createdFilters)
actionMockData.FilterID = createdFilters[0].ID
actionMockData.ClientID = int32(createdClient.ID)
mockData.FilterID = createdFilters[0].ID
err = repo.Store(context.Background(), mockData)
assert.NoError(t, err)
createdAction, err := actionRepo.Store(context.Background(), actionMockData)
assert.NoError(t, err)
releaseActionMockData.ReleaseID = mockData.ID
releaseActionMockData.ActionID = int64(createdAction.ID)
releaseActionMockData.FilterID = int64(createdFilters[0].ID)
err = repo.StoreReleaseActionStatus(context.Background(), releaseActionMockData)
assert.NoError(t, err)
// Execute
actionStatus, err := repo.GetActionStatus(context.Background(), &domain.GetReleaseActionStatusRequest{Id: int(releaseActionMockData.ID)})
// Verify
assert.NoError(t, err)
assert.NotNil(t, actionStatus)
assert.Equal(t, releaseActionMockData.ID, actionStatus.ID)
// Cleanup
_ = repo.Delete(context.Background(), &domain.DeleteReleaseRequest{OlderThan: 0})
_ = actionRepo.Delete(context.Background(), &domain.DeleteActionRequest{ActionId: createdAction.ID})
_ = filterRepo.Delete(context.Background(), createdFilters[0].ID)
_ = downloadClientRepo.Delete(context.Background(), createdClient.ID)
})
}
}
func TestReleaseRepo_Get(t *testing.T) {
for dbType, db := range testDBs {
log := setupLoggerForTest()
downloadClientRepo := NewDownloadClientRepo(log, db)
filterRepo := NewFilterRepo(log, db)
actionRepo := NewActionRepo(log, db, downloadClientRepo)
repo := NewReleaseRepo(log, db)
mockData := getMockRelease()
releaseActionMockData := getMockReleaseActionStatus()
actionMockData := getMockAction()
t.Run(fmt.Sprintf("Get_Succeeds [%s]", dbType), func(t *testing.T) {
// Setup
createdClient, err := downloadClientRepo.Store(context.Background(), getMockDownloadClient())
assert.NoError(t, err)
assert.NotNil(t, createdClient)
err = filterRepo.Store(context.Background(), getMockFilter())
assert.NoError(t, err)
createdFilters, err := filterRepo.ListFilters(context.Background())
assert.NoError(t, err)
assert.NotNil(t, createdFilters)
actionMockData.FilterID = createdFilters[0].ID
actionMockData.ClientID = int32(createdClient.ID)
mockData.FilterID = createdFilters[0].ID
err = repo.Store(context.Background(), mockData)
assert.NoError(t, err)
createdAction, err := actionRepo.Store(context.Background(), actionMockData)
assert.NoError(t, err)
releaseActionMockData.ReleaseID = mockData.ID
releaseActionMockData.ActionID = int64(createdAction.ID)
releaseActionMockData.FilterID = int64(createdFilters[0].ID)
err = repo.StoreReleaseActionStatus(context.Background(), releaseActionMockData)
assert.NoError(t, err)
// Execute
release, err := repo.Get(context.Background(), &domain.GetReleaseRequest{Id: int(mockData.ID)})
// Verify
assert.NoError(t, err)
assert.NotNil(t, release)
assert.Equal(t, mockData.ID, release.ID)
// Cleanup
_ = repo.Delete(context.Background(), &domain.DeleteReleaseRequest{OlderThan: 0})
_ = actionRepo.Delete(context.Background(), &domain.DeleteActionRequest{ActionId: createdAction.ID})
_ = filterRepo.Delete(context.Background(), createdFilters[0].ID)
_ = downloadClientRepo.Delete(context.Background(), createdClient.ID)
})
}
}
func TestReleaseRepo_Stats(t *testing.T) {
for dbType, db := range testDBs {
log := setupLoggerForTest()
downloadClientRepo := NewDownloadClientRepo(log, db)
filterRepo := NewFilterRepo(log, db)
actionRepo := NewActionRepo(log, db, downloadClientRepo)
repo := NewReleaseRepo(log, db)
mockData := getMockRelease()
releaseActionMockData := getMockReleaseActionStatus()
actionMockData := getMockAction()
t.Run(fmt.Sprintf("Stats_Succeeds [%s]", dbType), func(t *testing.T) {
// Setup
createdClient, err := downloadClientRepo.Store(context.Background(), getMockDownloadClient())
assert.NoError(t, err)
assert.NotNil(t, createdClient)
err = filterRepo.Store(context.Background(), getMockFilter())
assert.NoError(t, err)
createdFilters, err := filterRepo.ListFilters(context.Background())
assert.NoError(t, err)
assert.NotNil(t, createdFilters)
actionMockData.FilterID = createdFilters[0].ID
actionMockData.ClientID = int32(createdClient.ID)
mockData.FilterID = createdFilters[0].ID
err = repo.Store(context.Background(), mockData)
assert.NoError(t, err)
createdAction, err := actionRepo.Store(context.Background(), actionMockData)
assert.NoError(t, err)
releaseActionMockData.ReleaseID = mockData.ID
releaseActionMockData.ActionID = int64(createdAction.ID)
releaseActionMockData.FilterID = int64(createdFilters[0].ID)
err = repo.StoreReleaseActionStatus(context.Background(), releaseActionMockData)
assert.NoError(t, err)
// Execute
stats, err := repo.Stats(context.Background())
// Verify
assert.NoError(t, err)
assert.NotNil(t, stats)
assert.Equal(t, int64(1), stats.PushApprovedCount)
// Cleanup
_ = repo.Delete(context.Background(), &domain.DeleteReleaseRequest{OlderThan: 0})
_ = actionRepo.Delete(context.Background(), &domain.DeleteActionRequest{ActionId: createdAction.ID})
_ = filterRepo.Delete(context.Background(), createdFilters[0].ID)
_ = downloadClientRepo.Delete(context.Background(), createdClient.ID)
})
}
}
func TestReleaseRepo_Delete(t *testing.T) {
for dbType, db := range testDBs {
log := setupLoggerForTest()
downloadClientRepo := NewDownloadClientRepo(log, db)
filterRepo := NewFilterRepo(log, db)
actionRepo := NewActionRepo(log, db, downloadClientRepo)
repo := NewReleaseRepo(log, db)
mockData := getMockRelease()
releaseActionMockData := getMockReleaseActionStatus()
actionMockData := getMockAction()
t.Run(fmt.Sprintf("Delete_Succeeds [%s]", dbType), func(t *testing.T) {
// Setup
createdClient, err := downloadClientRepo.Store(context.Background(), getMockDownloadClient())
assert.NoError(t, err)
assert.NotNil(t, createdClient)
err = filterRepo.Store(context.Background(), getMockFilter())
assert.NoError(t, err)
createdFilters, err := filterRepo.ListFilters(context.Background())
assert.NoError(t, err)
assert.NotNil(t, createdFilters)
actionMockData.FilterID = createdFilters[0].ID
actionMockData.ClientID = int32(createdClient.ID)
mockData.FilterID = createdFilters[0].ID
err = repo.Store(context.Background(), mockData)
assert.NoError(t, err)
createdAction, err := actionRepo.Store(context.Background(), actionMockData)
assert.NoError(t, err)
releaseActionMockData.ReleaseID = mockData.ID
releaseActionMockData.ActionID = int64(createdAction.ID)
releaseActionMockData.FilterID = int64(createdFilters[0].ID)
err = repo.StoreReleaseActionStatus(context.Background(), releaseActionMockData)
assert.NoError(t, err)
// Execute
err = repo.Delete(context.Background(), &domain.DeleteReleaseRequest{OlderThan: 0})
// Verify
assert.NoError(t, err)
// Cleanup
_ = actionRepo.Delete(context.Background(), &domain.DeleteActionRequest{ActionId: createdAction.ID})
_ = filterRepo.Delete(context.Background(), createdFilters[0].ID)
_ = downloadClientRepo.Delete(context.Background(), createdClient.ID)
})
}
}
func TestReleaseRepo_CanDownloadShow(t *testing.T) {
for dbType, db := range testDBs {
log := setupLoggerForTest()
downloadClientRepo := NewDownloadClientRepo(log, db)
filterRepo := NewFilterRepo(log, db)
actionRepo := NewActionRepo(log, db, downloadClientRepo)
repo := NewReleaseRepo(log, db)
mockData := getMockRelease()
releaseActionMockData := getMockReleaseActionStatus()
actionMockData := getMockAction()
t.Run(fmt.Sprintf("Delete_Succeeds [%s]", dbType), func(t *testing.T) {
// Setup
createdClient, err := downloadClientRepo.Store(context.Background(), getMockDownloadClient())
assert.NoError(t, err)
assert.NotNil(t, createdClient)
err = filterRepo.Store(context.Background(), getMockFilter())
assert.NoError(t, err)
createdFilters, err := filterRepo.ListFilters(context.Background())
assert.NoError(t, err)
assert.NotNil(t, createdFilters)
actionMockData.FilterID = createdFilters[0].ID
actionMockData.ClientID = int32(createdClient.ID)
mockData.FilterID = createdFilters[0].ID
err = repo.Store(context.Background(), mockData)
assert.NoError(t, err)
createdAction, err := actionRepo.Store(context.Background(), actionMockData)
assert.NoError(t, err)
releaseActionMockData.ReleaseID = mockData.ID
releaseActionMockData.ActionID = int64(createdAction.ID)
releaseActionMockData.FilterID = int64(createdFilters[0].ID)
err = repo.StoreReleaseActionStatus(context.Background(), releaseActionMockData)
assert.NoError(t, err)
// Execute
canDownload, err := repo.CanDownloadShow(context.Background(), "Example.Torrent.Name", 1, 2)
// Verify
assert.NoError(t, err)
assert.True(t, canDownload)
// Cleanup
_ = repo.Delete(context.Background(), &domain.DeleteReleaseRequest{OlderThan: 0})
_ = actionRepo.Delete(context.Background(), &domain.DeleteActionRequest{ActionId: createdAction.ID})
_ = filterRepo.Delete(context.Background(), createdFilters[0].ID)
_ = downloadClientRepo.Delete(context.Background(), createdClient.ID)
})
}
}