1
0
Fork 0
mirror of https://github.com/Eggbertx/gochan.git synced 2025-08-19 20:56:23 -07:00
gochan/pkg/gcsql/appeals_test.go

192 lines
5 KiB
Go

package gcsql
import (
"database/sql/driver"
"fmt"
"strconv"
"testing"
"github.com/DATA-DOG/go-sqlmock"
"github.com/gochan-org/gochan/pkg/config"
"github.com/stretchr/testify/assert"
)
var (
testCasesGetAppeals = []testCaseGetAppeals{
{
name: "single appeal, no results",
args: argsGetAppeals{1, 1},
expectReturn: nil,
},
{
name: "single appeal, with result",
args: argsGetAppeals{1, 1},
expectReturn: []IPBanAppeal{
{ID: 1},
},
},
{
name: "all appeals, no results",
args: argsGetAppeals{0, 1},
expectReturn: nil,
},
{
name: "all appeals, with results",
args: argsGetAppeals{0, 10},
expectReturn: []IPBanAppeal{{}, {}, {}},
},
}
testCasesApproveAppeals = []testCaseApproveAppeals{
{
name: "approve nonexistent appeal",
args: argsApproveAppeal{1, 1},
},
}
)
type testCaseGetAppeals struct {
name string
args argsGetAppeals
expectReturn []IPBanAppeal
}
type testCaseApproveAppeals struct {
name string
args argsApproveAppeal
}
type argsGetAppeals struct {
banID int
limit int
}
type argsApproveAppeal struct {
appealID int
staffID int
}
func testRunnerGetAppeals(t *testing.T, tC *testCaseGetAppeals, driver string) {
t.Helper()
db, mock, err := sqlmock.New()
if !assert.NoError(t, err) {
return
}
if !assert.NoError(t, SetTestingDB(driver, "gochan", "", db)) {
return
}
query := `SELECT id, staff_id, ip_ban_id, appeal_text, staff_response, is_denied FROM ip_ban_appeals`
if tC.args.banID > 0 {
switch driver {
case "mysql":
query += ` WHERE ip_ban_id = \?`
case "sqlite3":
fallthrough
case "postgres":
query += ` WHERE ip_ban_id = \$1`
}
}
if tC.args.limit > 0 {
query += " LIMIT " + strconv.Itoa(tC.args.limit)
}
expectQuery := mock.ExpectPrepare(query).ExpectQuery()
if tC.args.banID > 0 {
expectQuery.WithArgs(tC.args.banID)
}
expectedRows := sqlmock.NewRows([]string{"id", "staff_id", "ip_ban_id", "appeal_text", "staff_response", "is_denied"})
if len(tC.expectReturn) > 0 {
for _, expectedBan := range tC.expectReturn {
expectedRows.AddRow(
expectedBan.ID, expectedBan.StaffID, expectedBan.IPBanID, expectedBan.AppealText,
expectedBan.StaffResponse, expectedBan.IsDenied,
)
}
}
expectQuery.WillReturnRows(expectedRows)
got, err := GetAppeals(tC.args.banID, tC.args.limit)
if !assert.NoError(t, err) {
return
}
assert.NoError(t, mock.ExpectationsWereMet())
assert.LessOrEqual(t, len(got), tC.args.limit)
assert.Equal(t, tC.expectReturn, got)
if tC.args.banID > 0 && tC.expectReturn != nil {
assert.Equal(t, tC.args.banID, tC.expectReturn[0].ID)
}
assert.NoError(t, mock.ExpectationsWereMet())
closeMock(t, mock)
}
func TestGetAppeals(t *testing.T) {
for _, tC := range testCasesGetAppeals {
for _, driver := range testingDBDrivers {
t.Run(fmt.Sprintf("%s (%s)", tC.name, driver), func(t *testing.T) {
config.SetTestDBConfig(driver, "localhost", "gochan", "gochan", "gochan", "")
testRunnerGetAppeals(t, &tC, driver)
})
}
}
}
func testRunnerApproveAppeal(t *testing.T, tC *testCaseApproveAppeals, sqlDriver string) {
t.Helper()
db, mock, err := sqlmock.New()
if !assert.NoError(t, err) {
return
}
if !assert.NoError(t, SetTestingDB(sqlDriver, "gochan", "", db)) {
return
}
deactivateQuery := `UPDATE ip_ban SET is_active = FALSE WHERE id = \(\s+` +
`SELECT ip_ban_id FROM ip_ban_appeals WHERE id = `
deactivateAppealQuery := `INSERT INTO ip_ban_audit\s*\(\s*ip_ban_id, timestamp, ` +
`staff_id, is_active, is_thread_ban, permanent, staff_note, message, can_appeal\)\s*VALUES\(\(` +
`SELECT ip_ban_id FROM ip_ban_appeals WHERE id = `
deleteAppealQuery := `DELETE FROM ip_ban_appeals WHERE id = `
switch sqlDriver {
case "mysql":
deactivateQuery += `\?\)`
deactivateAppealQuery += `\?\),\s*CURRENT_TIMESTAMP, \?, FALSE, FALSE, FALSE, '', '', TRUE\)`
deleteAppealQuery += `\?`
case "sqlite3":
fallthrough
case "postgres":
deactivateQuery += `\$1\)`
deactivateAppealQuery += `\$1\),\s+CURRENT_TIMESTAMP, \$2, FALSE, FALSE, FALSE, '', '', TRUE\)`
deleteAppealQuery += `\$1`
}
mock.ExpectBegin()
mock.ExpectPrepare(deactivateQuery).ExpectExec().
WithArgs(tC.args.appealID).WillReturnResult(driver.ResultNoRows)
mock.ExpectPrepare(deactivateAppealQuery).ExpectExec().
WithArgs(tC.args.appealID, tC.args.staffID).
WillReturnResult(driver.ResultNoRows)
mock.ExpectPrepare(deleteAppealQuery).ExpectExec().
WithArgs(tC.args.appealID).
WillReturnResult(driver.ResultNoRows)
mock.ExpectCommit()
assert.NoError(t, ApproveAppeal(tC.args.appealID, tC.args.staffID))
assert.NoError(t, mock.ExpectationsWereMet())
closeMock(t, mock)
}
func TestApproveAppeal(t *testing.T) {
for _, tC := range testCasesApproveAppeals {
for _, sqlDriver := range testingDBDrivers {
t.Run(fmt.Sprintf("%s (%s)", tC.name, sqlDriver), func(t *testing.T) {
config.SetTestDBConfig(sqlDriver, "localhost", "gochan", "gochan", "gochan", "")
testRunnerApproveAppeal(t, &tC, sqlDriver)
})
}
}
}