Skip to content

chore: Optimize parial rego execution byte allocations #6144

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 9 commits into from
Feb 10, 2023

Conversation

Emyrk
Copy link
Member

@Emyrk Emyrk commented Feb 9, 2023

Preventing some allocations by reusing the same prepared partial query. Unfortunately the bulk of the work happens when the inputs are passed in, which cannot be done in advance.

The unit tests that are most affected by this change are Owner role users. Since the partial execution results in a single empty query. Meaning most of the memory allocations happens before the input is passed in.

Before

cpu: Intel(R) Core(TM) i7-6770HQ CPU @ 2.60GHz
BenchmarkRBACFilter/PrepareOnly-NoRoles-8                     91          15761998 ns/op         2693954 B/op      76514 allocs/op
BenchmarkRBACFilter/PrepareOnly-Admin-8                       76          15272378 ns/op         3154366 B/op      93904 allocs/op
BenchmarkRBACFilter/PrepareOnly-OrgAdmin-8                    61          23254933 ns/op         4741804 B/op     133793 allocs/op
BenchmarkRBACFilter/PrepareOnly-OrgMember-8                   51          21488792 ns/op         4609187 B/op     130032 allocs/op
BenchmarkRBACFilter/PrepareOnly-ManyRoles-8                   46          25034282 ns/op         5267128 B/op     147494 allocs/op
BenchmarkRBACFilter/PrepareOnly-AdminWithScope-8              78          13232737 ns/op         2932466 B/op      85865 allocs/op

After

cpu: Intel(R) Core(TM) i7-6770HQ CPU @ 2.60GHz
BenchmarkRBACFilter/PrepareOnly-NoRoles-8                    205           6279153 ns/op         1048482 B/op      29024 allocs/op
BenchmarkRBACFilter/PrepareOnly-Admin-8                      130           8191177 ns/op         1495304 B/op      46161 allocs/op
BenchmarkRBACFilter/PrepareOnly-OrgAdmin-8                    82          13969795 ns/op         3081619 B/op      86025 allocs/op
BenchmarkRBACFilter/PrepareOnly-OrgMember-8                   86          14498713 ns/op         2944946 B/op      82249 allocs/op
BenchmarkRBACFilter/PrepareOnly-ManyRoles-8                   72          25139446 ns/op         3588279 B/op      99513 allocs/op
BenchmarkRBACFilter/PrepareOnly-AdminWithScope-8             150           7135444 ns/op         1276023 B/op      38142 allocs/op

EMPTY POLICY

This is an illustration if input has 0 impact on the output prepared queries. I did this to illustrate the speedup of the Partial() call on the rego policy.

You can see the difference if you use an empty policy.rego so that the inputs do not really affect the output. This shows that the impact of inputs is a magnitude larger than the compilation of the original policy.

Before

cpu: Intel(R) Core(TM) i7-6770HQ CPU @ 2.60GHz
BenchmarkRBACFilter/PrepareOnly-NoRoles-8                   1681            667725 ns/op          172588 B/op       3580 allocs/op
BenchmarkRBACFilter/PrepareOnly-Admin-8                     1701            754506 ns/op          186134 B/op       3998 allocs/op
BenchmarkRBACFilter/PrepareOnly-OrgAdmin-8                  1872            672738 ns/op          184188 B/op       3924 allocs/op
BenchmarkRBACFilter/PrepareOnly-OrgMember-8                 1552            673768 ns/op          186339 B/op       3993 allocs/op
BenchmarkRBACFilter/PrepareOnly-ManyRoles-8                 1669            695561 ns/op          198783 B/op       4318 allocs/op
BenchmarkRBACFilter/PrepareOnly-AdminWithScope-8            1740            686103 ns/op          186142 B/op       3998 allocs/op

After

cpu: Intel(R) Core(TM) i7-6770HQ CPU @ 2.60GHz
BenchmarkRBACFilter/PrepareOnly-NoRoles-8                   4116            247152 ns/op           47435 B/op        665 allocs/op
BenchmarkRBACFilter/PrepareOnly-Admin-8                     3962            271590 ns/op           61014 B/op       1083 allocs/op
BenchmarkRBACFilter/PrepareOnly-OrgAdmin-8                  5521            255080 ns/op           59069 B/op       1009 allocs/op
BenchmarkRBACFilter/PrepareOnly-OrgMember-8                 3532            290196 ns/op           61221 B/op       1078 allocs/op
BenchmarkRBACFilter/PrepareOnly-ManyRoles-8                 3758            305439 ns/op           73677 B/op       1403 allocs/op
BenchmarkRBACFilter/PrepareOnly-AdminWithScope-8            3994            286214 ns/op           61014 B/op       1083 allocs/op

@Emyrk Emyrk marked this pull request as ready for review February 9, 2023 20:27
@Emyrk Emyrk requested review from johnstcn and kylecarbs February 9, 2023 20:28
Emyrk added 3 commits February 9, 2023 15:37
This reverts commit 0ef4b5c.
This addition made a unit test fail with a supporting statemetn
@@ -166,6 +168,21 @@ func NewAuthorizer(registry prometheus.Registerer) *RegoAuthorizer {
if err != nil {
panic(xerrors.Errorf("compile rego: %w", err))
}

partialQuery, err = rego.New(
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

review: this is inside queryOnce.Do()

}),
rego.Query("data.authz.allow = true"),
rego.Module("policy.rego", policy),
).PrepareForPartial(context.Background())
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

review: I wondered whether it would make sense to pass through a higher-level context here (e.g. NewAuthorizer(ctx, registry)) but the place we call NewAuthorizer doesn't appear to have any application-level context already available.

@Emyrk Emyrk merged commit 32fbd10 into main Feb 10, 2023
@Emyrk Emyrk deleted the stevenmasley/rego_prepare_less_alloc branch February 10, 2023 14:39
@github-actions github-actions bot locked and limited conversation to collaborators Feb 10, 2023
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants