diff --git a/api/v1/pinning.go b/api/v1/pinning.go index 4d58ea7c..e8e477d8 100644 --- a/api/v1/pinning.go +++ b/api/v1/pinning.go @@ -10,14 +10,15 @@ import ( "github.com/application-research/estuary/pinner" - "github.com/application-research/estuary/model" - pinningstatus "github.com/application-research/estuary/pinner/status" - "github.com/application-research/estuary/util" "github.com/ipfs/go-cid" "github.com/labstack/echo/v4" "github.com/libp2p/go-libp2p/core/peer" "golang.org/x/xerrors" "gorm.io/gorm" + + "github.com/application-research/estuary/model" + pinningstatus "github.com/application-research/estuary/pinner/status" + "github.com/application-research/estuary/util" ) const ( @@ -176,62 +177,42 @@ func filterForStatusQuery(q *gorm.DB, statuses map[pinningstatus.PinningStatus]b return q, nil // if no status filter or all statuses are specified, return all pins } - pinned := statuses[pinningstatus.PinningStatusPinned] - failed := statuses[pinningstatus.PinningStatusFailed] - pinning := statuses[pinningstatus.PinningStatusPinning] - queued := statuses[pinningstatus.PinningStatusQueued] - - if len(statuses) == 1 { - switch { - case pinned: - return q.Where("active and not failed and not pinning"), nil - case failed: - return q.Where("failed and not active and not pinning"), nil - case pinning: - return q.Where("pinning and not active and not failed"), nil - default: - return q.Where("not active and not pinning and not failed"), nil - } - } - - if len(statuses) == 2 { - if pinned && failed { - return q.Where("(active or failed) and not pinning"), nil - } - - if pinned && queued { - return q.Where("active and not failed and not pinning"), nil - } - - if pinned && pinning { - return q.Where("(active or pinning) and not failed"), nil - } - - if pinning && failed { - return q.Where("(pinning or failed) and not active"), nil - } - - if pinning && queued { - return q.Where("pinning and not active and not failed"), nil - } - - if failed && queued { - return q.Where("failed and not active and not pinning"), nil + whereSet := false + for status, ok := range statuses { + if ok { + switch status { + case pinningstatus.PinningStatusPinned: + if whereSet { + q = q.Or("active") + } else { + q = q.Where("active") + whereSet = true + } + case pinningstatus.PinningStatusFailed: + if whereSet { + q = q.Or("failed") + } else { + q = q.Where("failed") + whereSet = true + } + case pinningstatus.PinningStatusPinning: + if whereSet { + q = q.Or("pinning") + } else { + q = q.Where("pinning") + whereSet = true + } + case pinningstatus.PinningStatusQueued: + if whereSet { + q = q.Or("not active and not pinning and not failed") + } else { + q = q.Where("not active and not pinning and not failed") + whereSet = true + } + } } } - - if !statuses[pinningstatus.PinningStatusFailed] { - return q.Where("not failed and (active or pinning)"), nil - } - - if !statuses[pinningstatus.PinningStatusPinned] { - return q.Where("not active and (failed or pinning"), nil - } - - if !statuses[pinningstatus.PinningStatusPinning] { - return q.Where("not pinning and (active or failed"), nil - } - return q.Where("active or pinning or failed"), nil + return q, nil } // handleAddPin godoc diff --git a/api/v1/pinning_test.go b/api/v1/pinning_test.go index 7826137f..3d991427 100644 --- a/api/v1/pinning_test.go +++ b/api/v1/pinning_test.go @@ -6,8 +6,9 @@ import ( "gorm.io/driver/sqlite" "gorm.io/gorm" - pinningstatus "github.com/application-research/estuary/pinner/status" "github.com/stretchr/testify/assert" + + pinningstatus "github.com/application-research/estuary/pinner/status" ) type Conts struct { @@ -33,7 +34,16 @@ func TestStatusFilterQuery(t *testing.T) { resp, err = filterForStatusQuery(db, s) assert.NoError(err) - assert.Equal("SELECT * FROM `conts` WHERE failed and not active and not pinning", + assert.Equal("SELECT * FROM `conts` WHERE failed", + resp.Find([]Conts{}).Statement.SQL.String()) + + s = map[pinningstatus.PinningStatus]bool{ + pinningstatus.PinningStatusQueued: true, + } + + resp, err = filterForStatusQuery(db, s) + assert.NoError(err) + assert.Equal(" SELECT * FROM `conts` WHERE not active and not pinning and not failed", resp.Find([]Conts{}).Statement.SQL.String()) s = map[pinningstatus.PinningStatus]bool{ @@ -43,7 +53,7 @@ func TestStatusFilterQuery(t *testing.T) { resp, err = filterForStatusQuery(db, s) assert.NoError(err) - assert.Equal("SELECT * FROM `conts` WHERE (active or failed) and not pinning", + assert.Equal("SELECT * FROM `conts` WHERE failed OR active", resp.Find([]Conts{}).Statement.SQL.String()) s = map[pinningstatus.PinningStatus]bool{ @@ -53,16 +63,40 @@ func TestStatusFilterQuery(t *testing.T) { resp, err = filterForStatusQuery(db, s) assert.NoError(err) - assert.Equal("SELECT * FROM `conts` WHERE (active or pinning) and not failed", + assert.Equal("SELECT * FROM `conts` WHERE pinning OR active", + resp.Find([]Conts{}).Statement.SQL.String()) + + s = map[pinningstatus.PinningStatus]bool{ + pinningstatus.PinningStatusPinning: true, + pinningstatus.PinningStatusQueued: true, + } + + resp, err = filterForStatusQuery(db, s) + assert.NoError(err) + assert.Equal("SELECT * FROM `conts` WHERE pinning OR (not active and not pinning and not failed)", resp.Find([]Conts{}).Statement.SQL.String()) s = map[pinningstatus.PinningStatus]bool{ pinningstatus.PinningStatusPinning: true, pinningstatus.PinningStatusQueued: true, + pinningstatus.PinningStatusFailed: true, } resp, err = filterForStatusQuery(db, s) assert.NoError(err) - assert.Equal("SELECT * FROM `conts` WHERE pinning and not active and not failed", + assert.Equal("SELECT * FROM `conts` WHERE pinning OR (not active and not pinning and not failed) OR failed", resp.Find([]Conts{}).Statement.SQL.String()) + + s = map[pinningstatus.PinningStatus]bool{ + pinningstatus.PinningStatusPinning: true, + pinningstatus.PinningStatusQueued: true, + pinningstatus.PinningStatusFailed: true, + pinningstatus.PinningStatusPinned: true, + } + + resp, err = filterForStatusQuery(db, s) + assert.NoError(err) + assert.Equal(" SELECT * FROM `conts`", + resp.Find([]Conts{}).Statement.SQL.String()) + }