fix: prevent moving a list into a pseudo namespace
This commit is contained in:
parent
8d10130d4c
commit
3ccc6365a6
4 changed files with 62 additions and 10 deletions
|
@ -4,8 +4,8 @@ title: "Errors"
|
||||||
draft: false
|
draft: false
|
||||||
type: "doc"
|
type: "doc"
|
||||||
menu:
|
menu:
|
||||||
sidebar:
|
sidebar:
|
||||||
parent: "usage"
|
parent: "usage"
|
||||||
---
|
---
|
||||||
|
|
||||||
# Errors
|
# Errors
|
||||||
|
@ -52,14 +52,15 @@ This document describes the different errors Vikunja can return.
|
||||||
|
|
||||||
## List
|
## List
|
||||||
|
|
||||||
| ErrorCode | HTTP Status Code | Description |
|
| ErrorCode | HTTP Status Code | Description |
|
||||||
|-----------|------------------|-------------|
|
|-----------|------------------|-------------------------------------------------------------------------------------------------------------------------------|
|
||||||
| 3001 | 404 | The list does not exist. |
|
| 3001 | 404 | The list does not exist. |
|
||||||
| 3004 | 403 | The user needs to have read permissions on that list to perform that action. |
|
| 3004 | 403 | The user needs to have read permissions on that list to perform that action. |
|
||||||
| 3005 | 400 | The list title cannot be empty. |
|
| 3005 | 400 | The list title cannot be empty. |
|
||||||
| 3006 | 404 | The list share does not exist. |
|
| 3006 | 404 | The list share does not exist. |
|
||||||
| 3007 | 400 | A list with this identifier already exists. |
|
| 3007 | 400 | A list with this identifier already exists. |
|
||||||
| 3008 | 412 | The list is archived and can therefore only be accessed read only. This is also true for all tasks associated with this list. |
|
| 3008 | 412 | The list is archived and can therefore only be accessed read only. This is also true for all tasks associated with this list. |
|
||||||
|
| 3009 | 412 | The list cannot belong to a dynamically generated namespace like "Favorites". |
|
||||||
|
|
||||||
## Task
|
## Task
|
||||||
|
|
||||||
|
|
|
@ -237,7 +237,7 @@ type ErrListIsArchived struct {
|
||||||
ListID int64
|
ListID int64
|
||||||
}
|
}
|
||||||
|
|
||||||
// IsErrListIsArchived checks if an error is a .
|
// IsErrListIsArchived checks if an error is a list is archived error.
|
||||||
func IsErrListIsArchived(err error) bool {
|
func IsErrListIsArchived(err error) bool {
|
||||||
_, ok := err.(ErrListIsArchived)
|
_, ok := err.(ErrListIsArchived)
|
||||||
return ok
|
return ok
|
||||||
|
@ -255,6 +255,34 @@ func (err ErrListIsArchived) HTTPError() web.HTTPError {
|
||||||
return web.HTTPError{HTTPCode: http.StatusPreconditionFailed, Code: ErrCodeListIsArchived, Message: "This list is archived. Editing or creating new tasks is not possible."}
|
return web.HTTPError{HTTPCode: http.StatusPreconditionFailed, Code: ErrCodeListIsArchived, Message: "This list is archived. Editing or creating new tasks is not possible."}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ErrListCannotBelongToAPseudoNamespace represents an error where a list cannot belong to a pseudo namespace
|
||||||
|
type ErrListCannotBelongToAPseudoNamespace struct {
|
||||||
|
ListID int64
|
||||||
|
NamespaceID int64
|
||||||
|
}
|
||||||
|
|
||||||
|
// IsErrListCannotBelongToAPseudoNamespace checks if an error is a list is archived error.
|
||||||
|
func IsErrListCannotBelongToAPseudoNamespace(err error) bool {
|
||||||
|
_, ok := err.(*ErrListCannotBelongToAPseudoNamespace)
|
||||||
|
return ok
|
||||||
|
}
|
||||||
|
|
||||||
|
func (err *ErrListCannotBelongToAPseudoNamespace) Error() string {
|
||||||
|
return fmt.Sprintf("List cannot belong to a pseudo namespace [ListID: %d, NamespaceID: %d]", err.ListID, err.NamespaceID)
|
||||||
|
}
|
||||||
|
|
||||||
|
// ErrCodeListCannotBelongToAPseudoNamespace holds the unique world-error code of this error
|
||||||
|
const ErrCodeListCannotBelongToAPseudoNamespace = 3009
|
||||||
|
|
||||||
|
// HTTPError holds the http error description
|
||||||
|
func (err *ErrListCannotBelongToAPseudoNamespace) HTTPError() web.HTTPError {
|
||||||
|
return web.HTTPError{
|
||||||
|
HTTPCode: http.StatusPreconditionFailed,
|
||||||
|
Code: ErrCodeListCannotBelongToAPseudoNamespace,
|
||||||
|
Message: "This list cannot belong a dynamically generated namespace.",
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// ================
|
// ================
|
||||||
// List task errors
|
// List task errors
|
||||||
// ================
|
// ================
|
||||||
|
|
|
@ -543,6 +543,10 @@ func (l *List) CheckIsArchived(s *xorm.Session) (err error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func checkListBeforeUpdateOrDelete(s *xorm.Session, list *List) error {
|
func checkListBeforeUpdateOrDelete(s *xorm.Session, list *List) error {
|
||||||
|
if list.NamespaceID < 0 {
|
||||||
|
return &ErrListCannotBelongToAPseudoNamespace{ListID: list.ID, NamespaceID: list.NamespaceID}
|
||||||
|
}
|
||||||
|
|
||||||
// Check if the namespace exists
|
// Check if the namespace exists
|
||||||
if list.NamespaceID > 0 {
|
if list.NamespaceID > 0 {
|
||||||
_, err := GetNamespaceByID(s, list.NamespaceID)
|
_, err := GetNamespaceByID(s, list.NamespaceID)
|
||||||
|
|
|
@ -221,6 +221,25 @@ func TestList_CreateOrUpdate(t *testing.T) {
|
||||||
assert.False(t, can) // namespace is not writeable by us
|
assert.False(t, can) // namespace is not writeable by us
|
||||||
_ = s.Close()
|
_ = s.Close()
|
||||||
})
|
})
|
||||||
|
t.Run("pseudo namespace", func(t *testing.T) {
|
||||||
|
usr := &user.User{
|
||||||
|
ID: 6,
|
||||||
|
Username: "user6",
|
||||||
|
Email: "user6@example.com",
|
||||||
|
}
|
||||||
|
|
||||||
|
db.LoadAndAssertFixtures(t)
|
||||||
|
s := db.NewSession()
|
||||||
|
list := List{
|
||||||
|
ID: 6,
|
||||||
|
Title: "Test6",
|
||||||
|
Description: "Lorem Ipsum",
|
||||||
|
NamespaceID: -1,
|
||||||
|
}
|
||||||
|
err := list.Update(s, usr)
|
||||||
|
assert.Error(t, err)
|
||||||
|
assert.True(t, IsErrListCannotBelongToAPseudoNamespace(err))
|
||||||
|
})
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue