rules: handle interfering rule violations

We collect errors of all rule enforcers, handling errors in all of them
should an error occur. This is to roll back state consistently.
This commit is contained in:
bitromortac 2024-05-31 10:20:42 +02:00
parent 772b62689f
commit 8f2ab273bb
No known key found for this signature in database
GPG key ID: 1965063FC13BEBE2

View file

@ -2,6 +2,7 @@ package firewall
import (
"context"
"errors"
"fmt"
"github.com/lightninglabs/lightning-terminal/firewalldb"
@ -236,14 +237,12 @@ func (r *RuleEnforcer) handleRequest(ctx context.Context,
return nil, fmt.Errorf("error parsing proto: %v", err)
}
var errs []error
for _, rule := range rules {
newRequest, err := rule.HandleRequest(ctx, ri.URI, msg)
if err != nil {
st := status.Errorf(
codes.ResourceExhausted, "rule violation: %v",
err,
)
return nil, st
errs = append(errs, err)
continue
}
if newRequest != nil {
@ -251,6 +250,24 @@ func (r *RuleEnforcer) handleRequest(ctx context.Context,
}
}
// Should we have encountered any errors for rules in the request, we
// need to roll back any pending state changes.
if len(errs) > 0 {
for _, rule := range rules {
// We call HandleErrorResponse to undo any persisted
// state changes.
_, err := rule.HandleErrorResponse(ctx, ri.URI, nil)
if err != nil {
log.Errorf("Error rolling back request: %v",
err)
}
}
// We join any errors to report all rule violations.
return nil, status.Errorf(codes.ResourceExhausted,
"rule violation: %s", errors.Join(errs...))
}
return nil, nil
}