Skip to content

Commit 92f96b6

Browse files
migmartrijiparis
andauthored
feat: policy violations filter (#2550)
Signed-off-by: Miguel Martinez <[email protected]> Co-authored-by: Jose I. Paris <[email protected]>
1 parent d4cc444 commit 92f96b6

30 files changed

+2072
-914
lines changed

CLAUDE.md

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -268,4 +268,5 @@ Code reviews are required for all submissions via GitHub pull requests.
268268
- if you add any new dependency to a constructor, remember to run wire ./...
269269
- when creating PR message, keep it high-level, what functionality was added, don't add info about testing, no icons, no info about how the message was generated.
270270
- app/controlplane/api/gen/frontend/google/protobuf/descriptor.ts is a special case that we don't want to upgrade, so if it upgrades, put it back to main
271-
- when creating a commit or PR message, NEVER add co-authored by or generated by Claude code
271+
- when creating a commit or PR message, NEVER add co-authored by or generated by Claude code
272+
- if you modify a schema, remember to run `make migration_sync`

app/cli/cmd/workflow_workflow_run_describe.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -128,6 +128,7 @@ func workflowRunDescribeTableOutput(run *action.WorkflowRunItemFull) error {
128128
if wr.Reason != "" {
129129
gt.AppendRow(table.Row{"Failure Reason", wr.Reason})
130130
}
131+
gt.AppendRow(table.Row{"Policy Status", wr.PolicyStatus})
131132
gt.AppendRow(table.Row{"Runner Link", wr.RunURL})
132133

133134
if run.WorkflowRun.FinishedAt == nil {

app/cli/cmd/workflow_workflow_run_list.go

Lines changed: 11 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
//
2-
// Copyright 2024 The Chainloop Authors.
2+
// Copyright 2024-2025 The Chainloop Authors.
33
//
44
// Licensed under the Apache License, Version 2.0 (the "License");
55
// you may not use this file except in compliance with the License.
@@ -33,7 +33,7 @@ func newWorkflowWorkflowRunListCmd() *cobra.Command {
3333
DefaultLimit: 50,
3434
}
3535

36-
var workflowName, projectName, status string
36+
var workflowName, projectName, status, policyStatus string
3737

3838
cmd := &cobra.Command{
3939
Use: "list",
@@ -44,6 +44,10 @@ func newWorkflowWorkflowRunListCmd() *cobra.Command {
4444
return fmt.Errorf("invalid status %q, please chose one of: %v", status, listAvailableWorkflowStatusFlag())
4545
}
4646

47+
if policyStatus != "" && !slices.Contains([]string{"all", "failed", "passed"}, policyStatus) {
48+
return fmt.Errorf("invalid policy-status %q, please chose one of: all, failed, passed", policyStatus)
49+
}
50+
4751
return nil
4852
},
4953
RunE: func(cmd *cobra.Command, args []string) error {
@@ -55,7 +59,8 @@ func newWorkflowWorkflowRunListCmd() *cobra.Command {
5559
Limit: paginationOpts.Limit,
5660
NextCursor: paginationOpts.NextCursor,
5761
},
58-
Status: status,
62+
Status: status,
63+
PolicyStatus: policyStatus,
5964
},
6065
)
6166
if err != nil {
@@ -85,6 +90,7 @@ func newWorkflowWorkflowRunListCmd() *cobra.Command {
8590
cmd.Flags().StringVar(&projectName, "project", "", "project name")
8691
cmd.Flags().BoolVar(&full, "full", false, "full report")
8792
cmd.Flags().StringVar(&status, "status", "", fmt.Sprintf("filter by workflow run status: %v", listAvailableWorkflowStatusFlag()))
93+
cmd.Flags().StringVar(&policyStatus, "policy-status", "", "filter by policy violations status: all, failed, passed")
8894
// Add pagination flags
8995
paginationOpts.AddFlags(cmd)
9096

@@ -97,7 +103,7 @@ func workflowRunListTableOutput(runs []*action.WorkflowRunItem) error {
97103
return nil
98104
}
99105

100-
header := table.Row{"ID", "Workflow", "Version", "State", "Created At", "Runner"}
106+
header := table.Row{"ID", "Workflow", "Version", "State", "Policy Status", "Created At", "Runner"}
101107
if full {
102108
header = append(header, "Finished At", "Failure reason")
103109
}
@@ -107,7 +113,7 @@ func workflowRunListTableOutput(runs []*action.WorkflowRunItem) error {
107113

108114
for _, p := range runs {
109115
wf := p.Workflow
110-
r := table.Row{p.ID, wf.NamespacedName(), versionString(p.ProjectVersion), p.State, p.CreatedAt.Format(time.RFC822), p.RunnerType}
116+
r := table.Row{p.ID, wf.NamespacedName(), versionString(p.ProjectVersion), p.State, p.PolicyStatus, p.CreatedAt.Format(time.RFC822), p.RunnerType}
111117

112118
if full {
113119
var finishedAt string

app/cli/documentation/cli-reference.mdx

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -3890,13 +3890,14 @@ chainloop workflow workflow-run list [flags]
38903890
Options
38913891

38923892
```
3893-
--full full report
3894-
-h, --help help for list
3895-
--limit int number of items to show (default 50)
3896-
--next string cursor to load the next page
3897-
--project string project name
3898-
--status string filter by workflow run status: [CANCELLED EXPIRED FAILED INITIALIZED SUCCEEDED]
3899-
--workflow string workflow name
3893+
--full full report
3894+
-h, --help help for list
3895+
--limit int number of items to show (default 50)
3896+
--next string cursor to load the next page
3897+
--policy-status string filter by policy violations status: all, failed, passed
3898+
--project string project name
3899+
--status string filter by workflow run status: [CANCELLED EXPIRED FAILED INITIALIZED SUCCEEDED]
3900+
--workflow string workflow name
39003901
```
39013902

39023903
Options inherited from parent commands

app/cli/pkg/action/workflow_run_list.go

Lines changed: 26 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
//
2-
// Copyright 2024 The Chainloop Authors.
2+
// Copyright 2024-2025 The Chainloop Authors.
33
//
44
// Licensed under the Apache License, Version 2.0 (the "License");
55
// you may not use this file except in compliance with the License.
@@ -52,6 +52,7 @@ type WorkflowRunItem struct {
5252
ContractRevisionUsed int `json:"contractRevisionUsed"`
5353
ContractRevisionLatest int `json:"contractRevisionLatest"`
5454
ProjectVersion *ProjectVersion `json:"projectVersion,omitempty"`
55+
PolicyStatus string `json:"policyStatus,omitempty"`
5556
}
5657

5758
type ProjectVersion struct {
@@ -74,6 +75,7 @@ type WorkflowRunListOpts struct {
7475
WorkflowName, ProjectName string
7576
Pagination *PaginationOpts
7677
Status string
78+
PolicyStatus string
7779
}
7880
type PaginationOpts struct {
7981
Limit int
@@ -95,6 +97,18 @@ func (action *WorkflowRunList) Run(opts *WorkflowRunListOpts) (*PaginatedWorkflo
9597
req.Status = v
9698
}
9799

100+
// Map policy status string to proto enum
101+
if opts.PolicyStatus != "" {
102+
switch opts.PolicyStatus {
103+
case "failed":
104+
req.PolicyViolations = pb.PolicyViolationsFilter_POLICY_VIOLATIONS_FILTER_WITH_VIOLATIONS
105+
case "passed":
106+
req.PolicyViolations = pb.PolicyViolationsFilter_POLICY_VIOLATIONS_FILTER_WITHOUT_VIOLATIONS
107+
case "all":
108+
req.PolicyViolations = pb.PolicyViolationsFilter_POLICY_VIOLATIONS_FILTER_UNSPECIFIED
109+
}
110+
}
111+
98112
resp, err := client.List(context.Background(), req)
99113
if err != nil {
100114
return nil, err
@@ -145,6 +159,7 @@ func pbWorkflowRunItemToAction(in *pb.WorkflowRunItem) *WorkflowRunItem {
145159
Version: in.GetVersion().GetVersion(),
146160
Prerelease: in.GetVersion().GetPrerelease(),
147161
},
162+
PolicyStatus: humanizedPolicyStatus(in.HasPolicyViolations),
148163
}
149164

150165
if in.GetContractVersion() != nil {
@@ -158,6 +173,16 @@ func pbWorkflowRunItemToAction(in *pb.WorkflowRunItem) *WorkflowRunItem {
158173
return item
159174
}
160175

176+
func humanizedPolicyStatus(hasPolicyViolations *bool) string {
177+
if hasPolicyViolations == nil {
178+
return "N/A"
179+
}
180+
if *hasPolicyViolations {
181+
return "failed"
182+
}
183+
return "passed"
184+
}
185+
161186
func humanizedRunnerType(in v1.CraftingSchema_Runner_RunnerType) string {
162187
mapping := map[v1.CraftingSchema_Runner_RunnerType]string{
163188
*v1.CraftingSchema_Runner_RUNNER_TYPE_UNSPECIFIED.Enum(): "Unspecified",

0 commit comments

Comments
 (0)