Commit 8563c725 authored by ale's avatar ale

Add limits to backend search methods

parent b50f0ae9
Pipeline #7845 passed with stages
in 1 minute and 48 seconds
...@@ -33,6 +33,7 @@ type SearchResourceRequest struct { ...@@ -33,6 +33,7 @@ type SearchResourceRequest struct {
AdminRequestBase AdminRequestBase
Pattern string `json:"pattern"` Pattern string `json:"pattern"`
Limit int `json:"limit"`
} }
// Validate the request. // Validate the request.
...@@ -50,7 +51,7 @@ type SearchResourceResponse struct { ...@@ -50,7 +51,7 @@ type SearchResourceResponse struct {
// Serve the request. // Serve the request.
func (r *SearchResourceRequest) Serve(rctx *RequestContext) (interface{}, error) { func (r *SearchResourceRequest) Serve(rctx *RequestContext) (interface{}, error) {
results, err := rctx.TX.SearchResource(rctx.Context, r.Pattern) results, err := rctx.TX.SearchResource(rctx.Context, r.Pattern, r.Limit)
if err != nil { if err != nil {
return nil, err return nil, err
} }
......
...@@ -56,7 +56,7 @@ func (b *fakeBackend) GetUser(_ context.Context, username string) (*RawUser, err ...@@ -56,7 +56,7 @@ func (b *fakeBackend) GetUser(_ context.Context, username string) (*RawUser, err
}, nil }, nil
} }
func (b *fakeBackend) SearchUser(_ context.Context, pattern string) ([]string, error) { func (b *fakeBackend) SearchUser(_ context.Context, pattern string, limit int) ([]string, error) {
var out []string var out []string
for username := range b.users { for username := range b.users {
if strings.HasPrefix(username, pattern) { if strings.HasPrefix(username, pattern) {
...@@ -95,7 +95,7 @@ func (b *fakeBackend) FindResource(_ context.Context, req FindResourceRequest) ( ...@@ -95,7 +95,7 @@ func (b *fakeBackend) FindResource(_ context.Context, req FindResourceRequest) (
return nil, nil return nil, nil
} }
func (b *fakeBackend) SearchResource(_ context.Context, pattern string) ([]*RawResource, error) { func (b *fakeBackend) SearchResource(_ context.Context, pattern string, limit int) ([]*RawResource, error) {
var out []*RawResource var out []*RawResource
for id, r := range b.resources { for id, r := range b.resources {
owner := strings.Split(id, "/")[0] owner := strings.Split(id, "/")[0]
......
...@@ -31,6 +31,7 @@ type SearchUserRequest struct { ...@@ -31,6 +31,7 @@ type SearchUserRequest struct {
AdminRequestBase AdminRequestBase
Pattern string `json:"pattern"` Pattern string `json:"pattern"`
Limit int `json:"limit"`
} }
// Validate the request. // Validate the request.
...@@ -48,7 +49,7 @@ type SearchUserResponse struct { ...@@ -48,7 +49,7 @@ type SearchUserResponse struct {
// Serve the request. // Serve the request.
func (r *SearchUserRequest) Serve(rctx *RequestContext) (interface{}, error) { func (r *SearchUserRequest) Serve(rctx *RequestContext) (interface{}, error) {
usernames, err := rctx.TX.SearchUser(rctx.Context, r.Pattern) usernames, err := rctx.TX.SearchUser(rctx.Context, r.Pattern, r.Limit)
if err != nil { if err != nil {
return nil, err return nil, err
} }
......
...@@ -348,10 +348,12 @@ func (tx *backendTX) GetUser(ctx context.Context, username string) (*as.RawUser, ...@@ -348,10 +348,12 @@ func (tx *backendTX) GetUser(ctx context.Context, username string) (*as.RawUser,
return user, nil return user, nil
} }
func (tx *backendTX) SearchUser(ctx context.Context, pattern string) ([]string, error) { func (tx *backendTX) SearchUser(ctx context.Context, pattern string, limit int) ([]string, error) {
// First of all, find the main user object, and just that one. // First of all, find the main user object, and just that one.
vars := templateVars{"pattern": rawVariable(pattern)} vars := templateVars{"pattern": rawVariable(pattern)}
result, err := tx.search(ctx, tx.backend.searchUserQuery.query(vars)) req := tx.backend.searchUserQuery.query(vars)
req.SizeLimit = limit
result, err := tx.search(ctx, req)
if err != nil { if err != nil {
return nil, err return nil, err
} }
...@@ -493,15 +495,17 @@ func (tx *backendTX) HasAnyResource(ctx context.Context, resourceIDs []as.FindRe ...@@ -493,15 +495,17 @@ func (tx *backendTX) HasAnyResource(ctx context.Context, resourceIDs []as.FindRe
return false, nil return false, nil
} }
func (tx *backendTX) searchResourcesByType(ctx context.Context, pattern, resourceType string) ([]*as.RawResource, error) { func (tx *backendTX) searchResourcesByType(ctx context.Context, pattern, resourceType string, limit int) ([]*as.RawResource, error) {
tpl, err := tx.backend.resources.SearchQuery(resourceType) tpl, err := tx.backend.resources.SearchQuery(resourceType)
if err != nil { if err != nil {
return nil, err return nil, err
} }
result, err := tx.search(ctx, tpl.query(templateVars{ req := tpl.query(templateVars{
"resource": rawVariable(pattern), "resource": rawVariable(pattern),
"type": resourceType, "type": resourceType,
})) })
req.SizeLimit = limit
result, err := tx.search(ctx, req)
if err != nil { if err != nil {
if ldap.IsErrorWithCode(err, ldap.LDAPResultNoSuchObject) { if ldap.IsErrorWithCode(err, ldap.LDAPResultNoSuchObject) {
return nil, nil return nil, nil
...@@ -528,7 +532,7 @@ func (tx *backendTX) searchResourcesByType(ctx context.Context, pattern, resourc ...@@ -528,7 +532,7 @@ func (tx *backendTX) searchResourcesByType(ctx context.Context, pattern, resourc
// FindResource fetches a specific resource by type and name. // FindResource fetches a specific resource by type and name.
func (tx *backendTX) FindResource(ctx context.Context, spec as.FindResourceRequest) (*as.RawResource, error) { func (tx *backendTX) FindResource(ctx context.Context, spec as.FindResourceRequest) (*as.RawResource, error) {
result, err := tx.searchResourcesByType(ctx, spec.Name, spec.Type) result, err := tx.searchResourcesByType(ctx, spec.Name, spec.Type, 0)
if err != nil { if err != nil {
return nil, err return nil, err
} }
...@@ -543,11 +547,11 @@ func (tx *backendTX) FindResource(ctx context.Context, spec as.FindResourceReque ...@@ -543,11 +547,11 @@ func (tx *backendTX) FindResource(ctx context.Context, spec as.FindResourceReque
} }
// SearchResource returns all the resources matching the pattern. // SearchResource returns all the resources matching the pattern.
func (tx *backendTX) SearchResource(ctx context.Context, pattern string) ([]*as.RawResource, error) { func (tx *backendTX) SearchResource(ctx context.Context, pattern string, limit int) ([]*as.RawResource, error) {
// Aggregate results for all known resource types. // Aggregate results for all known resource types.
var out []*as.RawResource var out []*as.RawResource
for _, typ := range tx.backend.resources.types { for _, typ := range tx.backend.resources.types {
r, err := tx.searchResourcesByType(ctx, pattern, typ) r, err := tx.searchResourcesByType(ctx, pattern, typ, limit)
if err != nil { if err != nil {
return nil, err return nil, err
} }
......
...@@ -197,7 +197,7 @@ func TestModel_SearchUser(t *testing.T) { ...@@ -197,7 +197,7 @@ func TestModel_SearchUser(t *testing.T) {
stop, b := startServer(t) stop, b := startServer(t)
defer stop() defer stop()
tx, _ := b.NewTransaction() tx, _ := b.NewTransaction()
users, err := tx.SearchUser(context.Background(), "uno") users, err := tx.SearchUser(context.Background(), "uno", 0)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
...@@ -288,7 +288,7 @@ func TestModel_SearchResource(t *testing.T) { ...@@ -288,7 +288,7 @@ func TestModel_SearchResource(t *testing.T) {
for _, pattern := range []string{"uno@investici.org", "uno*"} { for _, pattern := range []string{"uno@investici.org", "uno*"} {
tx, _ := b.NewTransaction() tx, _ := b.NewTransaction()
resources, err := tx.SearchResource(context.Background(), "uno@investici.org") resources, err := tx.SearchResource(context.Background(), "uno@investici.org", 0)
if err != nil { if err != nil {
t.Fatalf("SearchUser(%s): %v", pattern, err) t.Fatalf("SearchUser(%s): %v", pattern, err)
} }
......
...@@ -69,10 +69,10 @@ type TX interface { ...@@ -69,10 +69,10 @@ type TX interface {
// Lightweight user search (backend-specific pattern). // Lightweight user search (backend-specific pattern).
// Returns list of matching usernames. // Returns list of matching usernames.
SearchUser(context.Context, string) ([]string, error) SearchUser(context.Context, string, int) ([]string, error)
// Resource search (backend-specific pattern). // Resource search (backend-specific pattern).
SearchResource(context.Context, string) ([]*RawResource, error) SearchResource(context.Context, string, int) ([]*RawResource, error)
// Resource ACL check (does not necessarily hit the database). // Resource ACL check (does not necessarily hit the database).
CanAccessResource(context.Context, string, *Resource) bool CanAccessResource(context.Context, string, *Resource) bool
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment