fix: sort tasks logically and consistent across dbms (#1177)
This PR changes the behavoir of sorting tasks. Before, tasks were sorted with null values first. Now, null values are always sorted last which is usually what you want. Partial fix for https://github.com/go-vikunja/frontend/issues/54 Co-authored-by: kolaente <k@knt.li> Reviewed-on: https://kolaente.dev/vikunja/api/pulls/1177
This commit is contained in:
@ -1046,6 +1046,9 @@ func TestTaskCollection_ReadAll(t *testing.T) {
|
||||
a: &user.User{ID: 1},
|
||||
},
|
||||
want: []*Task{
|
||||
// The only tasks with a position set
|
||||
task1,
|
||||
task2,
|
||||
// the other ones don't have a position set
|
||||
task3,
|
||||
task4,
|
||||
@ -1076,9 +1079,51 @@ func TestTaskCollection_ReadAll(t *testing.T) {
|
||||
task31,
|
||||
task32,
|
||||
task33,
|
||||
// The only tasks with a position set
|
||||
task1,
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "order by due date",
|
||||
fields: fields{
|
||||
SortBy: []string{"due_date", "id"},
|
||||
OrderBy: []string{"asc", "desc"},
|
||||
},
|
||||
args: args{
|
||||
a: &user.User{ID: 1},
|
||||
},
|
||||
want: []*Task{
|
||||
// The only tasks with a due date
|
||||
task6,
|
||||
task5,
|
||||
// The other ones don't have a due date
|
||||
task33,
|
||||
task32,
|
||||
task31,
|
||||
task30,
|
||||
task29,
|
||||
task28,
|
||||
task27,
|
||||
task26,
|
||||
task25,
|
||||
task24,
|
||||
task23,
|
||||
task22,
|
||||
task21,
|
||||
task20,
|
||||
task19,
|
||||
task18,
|
||||
task17,
|
||||
task16,
|
||||
task15,
|
||||
task12,
|
||||
task11,
|
||||
task10,
|
||||
task9,
|
||||
task8,
|
||||
task7,
|
||||
task4,
|
||||
task3,
|
||||
task2,
|
||||
task1,
|
||||
},
|
||||
},
|
||||
{
|
||||
|
@ -296,17 +296,20 @@ func getRawTasksForLists(s *xorm.Session, lists []*List, a web.Auth, opts *taskO
|
||||
if err := param.validate(); err != nil {
|
||||
return nil, 0, 0, err
|
||||
}
|
||||
|
||||
// Mysql sorts columns with null values before ones without null value.
|
||||
// Because it does not have support for NULLS FIRST or NULLS LAST we work around this by
|
||||
// first sorting for null (or not null) values and then the order we actually want to.
|
||||
if db.Type() == schemas.MYSQL {
|
||||
orderby += param.sortBy + " IS NULL, "
|
||||
}
|
||||
|
||||
orderby += param.sortBy + " " + param.orderBy.String()
|
||||
|
||||
// Postgres sorts by default entries with null values after ones with values.
|
||||
// Postgres and sqlite allow us to control how columns with null values are sorted.
|
||||
// To make that consistent with the sort order we have and other dbms, we're adding a separate clause here.
|
||||
if db.Type() == schemas.POSTGRES {
|
||||
if param.orderBy == orderAscending {
|
||||
orderby += " NULLS FIRST"
|
||||
}
|
||||
if param.orderBy == orderDescending {
|
||||
orderby += " NULLS LAST"
|
||||
}
|
||||
if db.Type() == schemas.POSTGRES || db.Type() == schemas.SQLITE {
|
||||
orderby += " NULLS LAST"
|
||||
}
|
||||
|
||||
if (i + 1) < len(opts.sortby) {
|
||||
|
Reference in New Issue
Block a user