Skip to content

Commit

Permalink
Fix daemon panic on object.New<interface> uses
Browse files Browse the repository at this point in the history
object.New<interface> should verify the type cast worked, and
raise a new object.ErrWrongType error if not.

The api handlers now emit a "Bad Request" response if they
get a object.ErrWrongType, and "Internal Server Error" is still
used for all other errors.
  • Loading branch information
cvaroqui committed Aug 28, 2024
1 parent edbc42d commit 2c04e4c
Show file tree
Hide file tree
Showing 8 changed files with 55 additions and 11 deletions.
18 changes: 14 additions & 4 deletions core/object/factory.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ import (
"github.com/opensvc/om3/util/plog"
)

var ErrWrongType = errors.New("wrong type provided for interface")

// WithConfigFile sets a non-standard configuration location.
func WithConfigFile(s string) funcopt.O {
return funcopt.F(func(t any) error {
Expand Down Expand Up @@ -87,34 +89,42 @@ func New(p naming.Path, opts ...funcopt.O) (any, error) {
func NewCore(p naming.Path, opts ...funcopt.O) (Core, error) {
if o, err := New(p, opts...); err != nil {
return nil, err
} else if i, ok := o.(Core); ok {
return i, nil
} else {
return o.(Core), nil
return nil, ErrWrongType
}
}

// NewConfigurer returns a Configurer interface from an object path
func NewConfigurer(p naming.Path, opts ...funcopt.O) (Configurer, error) {
if o, err := New(p, opts...); err != nil {
return nil, err
} else if i, ok := o.(Configurer); ok {
return i, nil
} else {
return o.(Configurer), nil
return nil, ErrWrongType
}
}

// NewActor returns a Actor interface from an object path
func NewActor(p naming.Path, opts ...funcopt.O) (Actor, error) {
if o, err := New(p, opts...); err != nil {
return nil, err
} else if i, ok := o.(Actor); ok {
return i, nil
} else {
return o.(Actor), nil
return nil, ErrWrongType
}
}

// NewKeystore returns a Keystore interface from an object path
func NewKeystore(p naming.Path, opts ...funcopt.O) (Keystore, error) {
if o, err := New(p, opts...); err != nil {
return nil, err
} else if i, ok := o.(Keystore); ok {
return i, nil
} else {
return o.(Keystore), nil
return nil, ErrWrongType
}
}
6 changes: 5 additions & 1 deletion daemon/daemonapi/delete_object_kvstore_entry.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,11 @@ func (a *DaemonAPI) DeleteObjectKVStoreEntry(ctx echo.Context, namespace string,

if _, ok := instanceConfigData[a.localhost]; ok {
ks, err := object.NewKeystore(p)
if err != nil {

switch {
case errors.Is(err, object.ErrWrongType):
return JSONProblemf(ctx, http.StatusBadRequest, "NewKeystore", "%s", err)
case err != nil:
return JSONProblemf(ctx, http.StatusInternalServerError, "NewKeystore", "%s", err)
}

Expand Down
7 changes: 6 additions & 1 deletion daemon/daemonapi/get_object_kvstore.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package daemonapi

import (
"errors"
"net/http"

"github.com/labstack/echo/v4"
Expand Down Expand Up @@ -31,7 +32,11 @@ func (a *DaemonAPI) GetObjectKVStore(ctx echo.Context, namespace string, kind na

if _, ok := instanceConfigData[a.localhost]; ok {
ks, err := object.NewKeystore(p)
if err != nil {

switch {
case errors.Is(err, object.ErrWrongType):
return JSONProblemf(ctx, http.StatusBadRequest, "NewKeystore", "%s", err)
case err != nil:
return JSONProblemf(ctx, http.StatusInternalServerError, "NewKeystore", "%s", err)
}

Expand Down
7 changes: 6 additions & 1 deletion daemon/daemonapi/get_object_kvstore_entry.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package daemonapi

import (
"errors"
"net/http"
"unicode/utf8"

Expand Down Expand Up @@ -30,7 +31,11 @@ func (a *DaemonAPI) GetObjectKVStoreEntry(ctx echo.Context, namespace string, ki

if _, ok := instanceConfigData[a.localhost]; ok {
ks, err := object.NewKeystore(p)
if err != nil {

switch {
case errors.Is(err, object.ErrWrongType):
return JSONProblemf(ctx, http.StatusBadRequest, "NewKeystore", "%s", err)
case err != nil:
return JSONProblemf(ctx, http.StatusInternalServerError, "NewKeystore", "%s", err)
}

Expand Down
7 changes: 6 additions & 1 deletion daemon/daemonapi/get_object_kvstore_keys.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package daemonapi

import (
"errors"
"net/http"

"github.com/labstack/echo/v4"
Expand Down Expand Up @@ -30,7 +31,11 @@ func (a *DaemonAPI) GetObjectKVStoreKeys(ctx echo.Context, namespace string, kin

if _, ok := instanceConfigData[a.localhost]; ok {
ks, err := object.NewKeystore(p)
if err != nil {

switch {
case errors.Is(err, object.ErrWrongType):
return JSONProblemf(ctx, http.StatusBadRequest, "NewKeystore", "%s", err)
case err != nil:
return JSONProblemf(ctx, http.StatusInternalServerError, "NewKeystore", "%s", err)
}

Expand Down
7 changes: 6 additions & 1 deletion daemon/daemonapi/patch_object_kvstore.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package daemonapi

import (
"errors"
"net/http"

"github.com/labstack/echo/v4"
Expand Down Expand Up @@ -57,7 +58,11 @@ func (a *DaemonAPI) PatchObjectKVStore(ctx echo.Context, namespace string, kind

if _, ok := instanceConfigData[a.localhost]; ok {
ks, err := object.NewKeystore(p)
if err != nil {

switch {
case errors.Is(err, object.ErrWrongType):
return JSONProblemf(ctx, http.StatusBadRequest, "NewKeystore", "%s", err)
case err != nil:
return JSONProblemf(ctx, http.StatusInternalServerError, "NewKeystore", "%s", err)
}

Expand Down
7 changes: 6 additions & 1 deletion daemon/daemonapi/post_object_kvstore_entry.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,9 +31,14 @@ func (a *DaemonAPI) PostObjectKVStoreEntry(ctx echo.Context, namespace string, k

if _, ok := instanceConfigData[a.localhost]; ok {
ks, err := object.NewKeystore(p)
if err != nil {

switch {
case errors.Is(err, object.ErrWrongType):
return JSONProblemf(ctx, http.StatusBadRequest, "NewKeystore", "%s", err)
case err != nil:
return JSONProblemf(ctx, http.StatusInternalServerError, "NewKeystore", "%s", err)
}

b, err := ioutil.ReadAll(ctx.Request().Body)
if err != nil {
return JSONProblemf(ctx, http.StatusInternalServerError, "ReadAll", "%s: %s", params.Key, err)
Expand Down
7 changes: 6 additions & 1 deletion daemon/daemonapi/put_object_kvstore_entry.go
Original file line number Diff line number Diff line change
Expand Up @@ -32,9 +32,14 @@ func (a *DaemonAPI) PutObjectKVStoreEntry(ctx echo.Context, namespace string, ki

if _, ok := instanceConfigData[a.localhost]; ok {
ks, err := object.NewKeystore(p)
if err != nil {

switch {
case errors.Is(err, object.ErrWrongType):
return JSONProblemf(ctx, http.StatusBadRequest, "NewKeystore", "%s", err)
case err != nil:
return JSONProblemf(ctx, http.StatusInternalServerError, "NewKeystore", "%s", err)
}

keys, err := ks.AllKeys()
if err != nil {
return JSONProblemf(ctx, http.StatusInternalServerError, "AllKeys", "%s", err)
Expand Down

0 comments on commit 2c04e4c

Please sign in to comment.