pepr 0.46.0-nightly.1 → 0.46.0-nightly.10
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cli.js +1 -1
- package/dist/controller.js +1 -1
- package/dist/lib/assets/defaultTestObjects.d.ts +3 -0
- package/dist/lib/assets/defaultTestObjects.d.ts.map +1 -0
- package/dist/lib/filter/adjudicators/admissionRequest.d.ts +9 -0
- package/dist/lib/filter/adjudicators/admissionRequest.d.ts.map +1 -0
- package/dist/lib/filter/adjudicators/binding.d.ts +31 -0
- package/dist/lib/filter/adjudicators/binding.d.ts.map +1 -0
- package/dist/lib/filter/adjudicators/kubernetesObject.d.ts +22 -0
- package/dist/lib/filter/adjudicators/kubernetesObject.d.ts.map +1 -0
- package/dist/lib/filter/adjudicators/mismatch.d.ts +16 -0
- package/dist/lib/filter/adjudicators/mismatch.d.ts.map +1 -0
- package/dist/lib/filter/adjudicators/postCollection.d.ts +10 -0
- package/dist/lib/filter/adjudicators/postCollection.d.ts.map +1 -0
- package/dist/lib/filter/filter.d.ts.map +1 -1
- package/dist/lib.js +196 -152
- package/dist/lib.js.map +4 -4
- package/package.json +4 -5
- package/src/lib/assets/defaultTestObjects.ts +533 -0
- package/src/lib/filter/adjudicators/admissionRequest.ts +25 -0
- package/src/lib/filter/adjudicators/binding.ts +85 -0
- package/src/lib/filter/adjudicators/kubernetesObject.ts +90 -0
- package/src/lib/filter/adjudicators/mismatch.ts +129 -0
- package/src/lib/filter/adjudicators/postCollection.ts +77 -0
- package/src/lib/filter/filter.ts +22 -24
- package/src/lib/processors/watch-processor.ts +1 -1
- package/dist/lib/filter/adjudicators/adjudicators.d.ts +0 -74
- package/dist/lib/filter/adjudicators/adjudicators.d.ts.map +0 -1
- package/src/lib/filter/adjudicators/adjudicators.ts +0 -334
|
@@ -1,334 +0,0 @@
|
|
|
1
|
-
// SPDX-License-Identifier: Apache-2.0
|
|
2
|
-
// SPDX-FileCopyrightText: 2023-Present The Pepr Authors
|
|
3
|
-
|
|
4
|
-
import { Event, Operation } from "../../enums";
|
|
5
|
-
import { AdmissionRequest, Binding, FinalizeAction, WatchLogAction, MutateAction, ValidateAction } from "../../types";
|
|
6
|
-
import {
|
|
7
|
-
__,
|
|
8
|
-
allPass,
|
|
9
|
-
any,
|
|
10
|
-
anyPass,
|
|
11
|
-
complement,
|
|
12
|
-
curry,
|
|
13
|
-
defaultTo,
|
|
14
|
-
difference,
|
|
15
|
-
equals,
|
|
16
|
-
gt,
|
|
17
|
-
length,
|
|
18
|
-
not,
|
|
19
|
-
nthArg,
|
|
20
|
-
pipe,
|
|
21
|
-
} from "ramda";
|
|
22
|
-
import { GenericClass, KubernetesObject } from "kubernetes-fluent-client";
|
|
23
|
-
|
|
24
|
-
/*
|
|
25
|
-
Naming scheme:
|
|
26
|
-
- AdmissionRequest - "declares" / "neglects"
|
|
27
|
-
- KubernetesObject - "carries" / "missing"
|
|
28
|
-
- Binding - "defines" / "ignores"
|
|
29
|
-
*/
|
|
30
|
-
|
|
31
|
-
/*
|
|
32
|
-
AdmissionRequest collectors
|
|
33
|
-
*/
|
|
34
|
-
export const declaredOperation = pipe(
|
|
35
|
-
(request: AdmissionRequest<KubernetesObject>): Operation => request?.operation,
|
|
36
|
-
defaultTo(""),
|
|
37
|
-
);
|
|
38
|
-
export const declaredGroup = pipe(
|
|
39
|
-
(request: AdmissionRequest<KubernetesObject>): string => request?.kind?.group,
|
|
40
|
-
defaultTo(""),
|
|
41
|
-
);
|
|
42
|
-
export const declaredVersion = pipe(
|
|
43
|
-
(request: AdmissionRequest<KubernetesObject>): string | undefined => request?.kind?.version,
|
|
44
|
-
defaultTo(""),
|
|
45
|
-
);
|
|
46
|
-
export const declaredKind = pipe(
|
|
47
|
-
(request: AdmissionRequest<KubernetesObject>): string => request?.kind?.kind,
|
|
48
|
-
defaultTo(""),
|
|
49
|
-
);
|
|
50
|
-
export const declaredUid = pipe((request: AdmissionRequest<KubernetesObject>): string => request?.uid, defaultTo(""));
|
|
51
|
-
|
|
52
|
-
/*
|
|
53
|
-
KubernetesObject collectors
|
|
54
|
-
*/
|
|
55
|
-
export const carriesDeletionTimestamp = pipe(
|
|
56
|
-
kubernetesObject => !!kubernetesObject.metadata?.deletionTimestamp,
|
|
57
|
-
defaultTo(false),
|
|
58
|
-
);
|
|
59
|
-
export const missingDeletionTimestamp = complement(carriesDeletionTimestamp);
|
|
60
|
-
|
|
61
|
-
export const carriedKind = pipe(
|
|
62
|
-
(kubernetesObject: KubernetesObject): string | undefined => kubernetesObject?.kind,
|
|
63
|
-
defaultTo("not set"),
|
|
64
|
-
);
|
|
65
|
-
export const carriedVersion = pipe(
|
|
66
|
-
(kubernetesObject: KubernetesObject): string | undefined => kubernetesObject?.metadata?.resourceVersion,
|
|
67
|
-
defaultTo("not set"),
|
|
68
|
-
);
|
|
69
|
-
export const carriedName = pipe(
|
|
70
|
-
(kubernetesObject: KubernetesObject): string | undefined => kubernetesObject?.metadata?.name,
|
|
71
|
-
defaultTo(""),
|
|
72
|
-
);
|
|
73
|
-
export const carriesName = pipe(carriedName, equals(""), not);
|
|
74
|
-
export const missingName = complement(carriesName);
|
|
75
|
-
|
|
76
|
-
export const carriedNamespace = pipe(
|
|
77
|
-
(kubernetesObject: KubernetesObject): string | undefined => kubernetesObject?.metadata?.namespace,
|
|
78
|
-
defaultTo(""),
|
|
79
|
-
);
|
|
80
|
-
|
|
81
|
-
export const carriesNamespace = pipe(carriedNamespace, equals(""), not);
|
|
82
|
-
|
|
83
|
-
export const carriedAnnotations = pipe(
|
|
84
|
-
(kubernetesObject: KubernetesObject): { [key: string]: string } | undefined =>
|
|
85
|
-
kubernetesObject?.metadata?.annotations,
|
|
86
|
-
defaultTo({}),
|
|
87
|
-
);
|
|
88
|
-
export const carriesAnnotations = pipe(carriedAnnotations, equals({}), not);
|
|
89
|
-
|
|
90
|
-
export const carriedLabels = pipe(
|
|
91
|
-
(kubernetesObject: KubernetesObject): { [key: string]: string } | undefined => kubernetesObject?.metadata?.labels,
|
|
92
|
-
defaultTo({}),
|
|
93
|
-
);
|
|
94
|
-
export const carriesLabels = pipe(carriedLabels, equals({}), not);
|
|
95
|
-
|
|
96
|
-
/*
|
|
97
|
-
Binding collectors
|
|
98
|
-
*/
|
|
99
|
-
|
|
100
|
-
export const definesDeletionTimestamp = pipe(
|
|
101
|
-
(binding: Binding): boolean => binding?.filters?.deletionTimestamp ?? false,
|
|
102
|
-
defaultTo(false),
|
|
103
|
-
);
|
|
104
|
-
export const ignoresDeletionTimestamp = complement(definesDeletionTimestamp);
|
|
105
|
-
|
|
106
|
-
export const definedName = pipe((binding: Binding): string => {
|
|
107
|
-
return binding.filters.name;
|
|
108
|
-
}, defaultTo(""));
|
|
109
|
-
export const definesName = pipe(definedName, equals(""), not);
|
|
110
|
-
export const ignoresName = complement(definesName);
|
|
111
|
-
|
|
112
|
-
export const definedNameRegex = pipe(
|
|
113
|
-
(binding: Partial<Binding>): string | undefined => binding.filters?.regexName,
|
|
114
|
-
defaultTo(""),
|
|
115
|
-
);
|
|
116
|
-
export const definesNameRegex = pipe(definedNameRegex, equals(""), not);
|
|
117
|
-
|
|
118
|
-
export const definedNamespaces = pipe(binding => binding?.filters?.namespaces, defaultTo([]));
|
|
119
|
-
export const definesNamespaces = pipe(definedNamespaces, equals([]), not);
|
|
120
|
-
|
|
121
|
-
export const definedNamespaceRegexes = pipe(binding => binding?.filters?.regexNamespaces, defaultTo([]));
|
|
122
|
-
export const definesNamespaceRegexes = pipe(definedNamespaceRegexes, equals([]), not);
|
|
123
|
-
|
|
124
|
-
export const definedAnnotations = pipe((binding: Partial<Binding>) => binding?.filters?.annotations, defaultTo({}));
|
|
125
|
-
export const definesAnnotations = pipe(definedAnnotations, equals({}), not);
|
|
126
|
-
|
|
127
|
-
export const definedLabels = pipe((binding: Partial<Binding>) => binding?.filters?.labels, defaultTo({}));
|
|
128
|
-
export const definesLabels = pipe(definedLabels, equals({}), not);
|
|
129
|
-
|
|
130
|
-
export const definedEvent = (binding: Binding): Event => {
|
|
131
|
-
return binding.event;
|
|
132
|
-
};
|
|
133
|
-
|
|
134
|
-
export const definesDelete = pipe(definedEvent, equals(Event.DELETE));
|
|
135
|
-
|
|
136
|
-
export const definedGroup = pipe((binding): string => binding?.kind?.group, defaultTo(""));
|
|
137
|
-
export const definesGroup = pipe(definedGroup, equals(""), not);
|
|
138
|
-
|
|
139
|
-
export const definedVersion = pipe(
|
|
140
|
-
(binding: Partial<Binding>): string | undefined => binding?.kind?.version,
|
|
141
|
-
defaultTo(""),
|
|
142
|
-
);
|
|
143
|
-
export const definesVersion = pipe(definedVersion, equals(""), not);
|
|
144
|
-
|
|
145
|
-
export const definedKind = pipe((binding): string => binding?.kind?.kind, defaultTo(""));
|
|
146
|
-
export const definesKind = pipe(definedKind, equals(""), not);
|
|
147
|
-
|
|
148
|
-
export const definedCategory = (binding: Partial<Binding>): string => {
|
|
149
|
-
// Ordering matters, finalize is a "watch"
|
|
150
|
-
// prettier-ignore
|
|
151
|
-
return binding.isFinalize ? "Finalize" :
|
|
152
|
-
binding.isWatch ? "Watch" :
|
|
153
|
-
binding.isMutate ? "Mutate" :
|
|
154
|
-
binding.isValidate ? "Validate" :
|
|
155
|
-
"";
|
|
156
|
-
};
|
|
157
|
-
export type DefinedCallbackReturnType =
|
|
158
|
-
| FinalizeAction<GenericClass, InstanceType<GenericClass>>
|
|
159
|
-
| WatchLogAction<GenericClass, InstanceType<GenericClass>>
|
|
160
|
-
| MutateAction<GenericClass, InstanceType<GenericClass>>
|
|
161
|
-
| ValidateAction<GenericClass, InstanceType<GenericClass>>
|
|
162
|
-
| null
|
|
163
|
-
| undefined;
|
|
164
|
-
|
|
165
|
-
export const definedCallback = (binding: Partial<Binding>): DefinedCallbackReturnType => {
|
|
166
|
-
// Ordering matters, finalize is a "watch"
|
|
167
|
-
// prettier-ignore
|
|
168
|
-
return binding.isFinalize ? binding.finalizeCallback :
|
|
169
|
-
binding.isWatch ? binding.watchCallback :
|
|
170
|
-
binding.isMutate ? binding.mutateCallback :
|
|
171
|
-
binding.isValidate ? binding.validateCallback :
|
|
172
|
-
null;
|
|
173
|
-
};
|
|
174
|
-
export const definedCallbackName = pipe(definedCallback, defaultTo({ name: "" }), callback => callback.name);
|
|
175
|
-
|
|
176
|
-
/*
|
|
177
|
-
post-collection comparitors
|
|
178
|
-
*/
|
|
179
|
-
export const mismatchedDeletionTimestamp = allPass([
|
|
180
|
-
pipe(nthArg(0), definesDeletionTimestamp),
|
|
181
|
-
pipe(nthArg(1), missingDeletionTimestamp),
|
|
182
|
-
]);
|
|
183
|
-
|
|
184
|
-
export const mismatchedName = allPass([
|
|
185
|
-
pipe(nthArg(0), definesName),
|
|
186
|
-
pipe((binding, kubernetesObject) => definedName(binding) !== carriedName(kubernetesObject)),
|
|
187
|
-
]);
|
|
188
|
-
|
|
189
|
-
export const mismatchedNameRegex = allPass([
|
|
190
|
-
pipe(nthArg(0), definesNameRegex),
|
|
191
|
-
pipe((binding, kubernetesObject) => new RegExp(definedNameRegex(binding)).test(carriedName(kubernetesObject)), not),
|
|
192
|
-
]);
|
|
193
|
-
|
|
194
|
-
export const bindsToKind = curry(
|
|
195
|
-
allPass([pipe(nthArg(0), definedKind, equals(""), not), pipe((binding, kind) => definedKind(binding) === kind)]),
|
|
196
|
-
);
|
|
197
|
-
export const bindsToNamespace = curry(pipe(bindsToKind(__, "Namespace")));
|
|
198
|
-
export const misboundNamespace = allPass([bindsToNamespace, definesNamespaces]);
|
|
199
|
-
|
|
200
|
-
export const mismatchedNamespace = allPass([
|
|
201
|
-
pipe(nthArg(0), definesNamespaces),
|
|
202
|
-
pipe((binding, kubernetesObject) => definedNamespaces(binding).includes(carriedNamespace(kubernetesObject)), not),
|
|
203
|
-
]);
|
|
204
|
-
|
|
205
|
-
export const mismatchedNamespaceRegex = allPass([
|
|
206
|
-
pipe(nthArg(0), definesNamespaceRegexes),
|
|
207
|
-
pipe((binding, kubernetesObject) =>
|
|
208
|
-
pipe(
|
|
209
|
-
any((regEx: string) => new RegExp(regEx).test(carriedNamespace(kubernetesObject))),
|
|
210
|
-
not,
|
|
211
|
-
)(definedNamespaceRegexes(binding)),
|
|
212
|
-
),
|
|
213
|
-
]);
|
|
214
|
-
|
|
215
|
-
export const metasMismatch = pipe(
|
|
216
|
-
(defined, carried) => {
|
|
217
|
-
const result = { defined, carried, unalike: {} };
|
|
218
|
-
|
|
219
|
-
result.unalike = Object.entries(result.defined)
|
|
220
|
-
.map(([key, value]) => {
|
|
221
|
-
const keyMissing = !Object.hasOwn(result.carried, key);
|
|
222
|
-
const noValue = !value;
|
|
223
|
-
const valMissing = !result.carried[key];
|
|
224
|
-
const valDiffers = result.carried[key] !== result.defined[key];
|
|
225
|
-
|
|
226
|
-
// prettier-ignore
|
|
227
|
-
return (
|
|
228
|
-
keyMissing ? { [key]: value } :
|
|
229
|
-
noValue ? {} :
|
|
230
|
-
valMissing ? { [key]: value } :
|
|
231
|
-
valDiffers ? { [key]: value } :
|
|
232
|
-
{}
|
|
233
|
-
)
|
|
234
|
-
})
|
|
235
|
-
.reduce((acc, cur) => ({ ...acc, ...cur }), {});
|
|
236
|
-
|
|
237
|
-
return result.unalike;
|
|
238
|
-
},
|
|
239
|
-
unalike => Object.keys(unalike).length > 0,
|
|
240
|
-
);
|
|
241
|
-
|
|
242
|
-
export const mismatchedAnnotations = allPass([
|
|
243
|
-
pipe(nthArg(0), definesAnnotations),
|
|
244
|
-
pipe((binding, kubernetesObject) => metasMismatch(definedAnnotations(binding), carriedAnnotations(kubernetesObject))),
|
|
245
|
-
]);
|
|
246
|
-
|
|
247
|
-
export const mismatchedLabels = allPass([
|
|
248
|
-
pipe(nthArg(0), definesLabels),
|
|
249
|
-
pipe((binding, kubernetesObject) => metasMismatch(definedLabels(binding), carriedLabels(kubernetesObject))),
|
|
250
|
-
]);
|
|
251
|
-
|
|
252
|
-
/*
|
|
253
|
-
* If the object does not have a namespace, and it is not a namespace,
|
|
254
|
-
* then we must return false because it cannot be uncarryable
|
|
255
|
-
*/
|
|
256
|
-
export const uncarryableNamespace = allPass([
|
|
257
|
-
pipe(nthArg(0), length, gt(__, 0)),
|
|
258
|
-
pipe((namespaceSelector, kubernetesObject) => {
|
|
259
|
-
if (kubernetesObject?.kind === "Namespace") {
|
|
260
|
-
return namespaceSelector.includes(kubernetesObject?.metadata?.name);
|
|
261
|
-
}
|
|
262
|
-
if (carriesNamespace(kubernetesObject)) {
|
|
263
|
-
return namespaceSelector.includes(carriedNamespace(kubernetesObject));
|
|
264
|
-
}
|
|
265
|
-
return true;
|
|
266
|
-
}, not),
|
|
267
|
-
]);
|
|
268
|
-
|
|
269
|
-
export const missingCarriableNamespace = allPass([
|
|
270
|
-
pipe(nthArg(0), length, gt(__, 0)),
|
|
271
|
-
pipe((namespaceSelector: string[], kubernetesObject: KubernetesObject): boolean =>
|
|
272
|
-
kubernetesObject.kind === "Namespace"
|
|
273
|
-
? !namespaceSelector.includes(kubernetesObject.metadata!.name!)
|
|
274
|
-
: !carriesNamespace(kubernetesObject),
|
|
275
|
-
),
|
|
276
|
-
]);
|
|
277
|
-
|
|
278
|
-
/*
|
|
279
|
-
* If the object does not have a namespace, and it is not a namespace,
|
|
280
|
-
* then we must return false because it cannot be ignored
|
|
281
|
-
*/
|
|
282
|
-
export const carriesIgnoredNamespace = allPass([
|
|
283
|
-
pipe(nthArg(0), length, gt(__, 0)),
|
|
284
|
-
pipe((namespaceSelector, kubernetesObject) => {
|
|
285
|
-
if (kubernetesObject?.kind === "Namespace") {
|
|
286
|
-
return namespaceSelector.includes(kubernetesObject?.metadata?.name);
|
|
287
|
-
}
|
|
288
|
-
if (carriesNamespace(kubernetesObject)) {
|
|
289
|
-
return namespaceSelector.includes(carriedNamespace(kubernetesObject));
|
|
290
|
-
}
|
|
291
|
-
|
|
292
|
-
return false;
|
|
293
|
-
}),
|
|
294
|
-
]);
|
|
295
|
-
|
|
296
|
-
export const unbindableNamespaces = allPass([
|
|
297
|
-
pipe(nthArg(0), length, gt(__, 0)),
|
|
298
|
-
pipe(nthArg(1), definesNamespaces),
|
|
299
|
-
pipe(
|
|
300
|
-
(namespaceSelector, binding) => difference(definedNamespaces(binding), namespaceSelector),
|
|
301
|
-
length,
|
|
302
|
-
equals(0),
|
|
303
|
-
not,
|
|
304
|
-
),
|
|
305
|
-
]);
|
|
306
|
-
|
|
307
|
-
export const misboundDeleteWithDeletionTimestamp = allPass([definesDelete, definesDeletionTimestamp]);
|
|
308
|
-
|
|
309
|
-
export const operationMatchesEvent = anyPass([
|
|
310
|
-
pipe(nthArg(1), equals(Event.ANY)),
|
|
311
|
-
pipe((operation: Operation, event: Event): boolean => operation.valueOf() === event.valueOf()),
|
|
312
|
-
pipe((operation: Operation, event: Event): boolean => (operation ? event.includes(operation) : false)),
|
|
313
|
-
]);
|
|
314
|
-
|
|
315
|
-
export const mismatchedEvent = pipe(
|
|
316
|
-
(binding: Binding, request: AdmissionRequest): boolean =>
|
|
317
|
-
operationMatchesEvent(declaredOperation(request), definedEvent(binding)),
|
|
318
|
-
not,
|
|
319
|
-
);
|
|
320
|
-
|
|
321
|
-
export const mismatchedGroup = allPass([
|
|
322
|
-
pipe(nthArg(0), definesGroup),
|
|
323
|
-
pipe((binding, request) => definedGroup(binding) !== declaredGroup(request)),
|
|
324
|
-
]);
|
|
325
|
-
|
|
326
|
-
export const mismatchedVersion = allPass([
|
|
327
|
-
pipe(nthArg(0), definesVersion),
|
|
328
|
-
pipe((binding, request) => definedVersion(binding) !== declaredVersion(request)),
|
|
329
|
-
]);
|
|
330
|
-
|
|
331
|
-
export const mismatchedKind = allPass([
|
|
332
|
-
pipe(nthArg(0), definesKind),
|
|
333
|
-
pipe((binding, request) => definedKind(binding) !== declaredKind(request)),
|
|
334
|
-
]);
|