• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

astronomer / astro-cli / d8c087d9-3e34-4a26-9912-4e9425408752

04 Feb 2026 08:31PM UTC coverage: 32.799% (+0.005%) from 32.794%
d8c087d9-3e34-4a26-9912-4e9425408752

push

circleci

jeremybeard
Fix linting

18 of 95 new or added lines in 9 files covered. (18.95%)

5 existing lines in 1 file now uncovered.

21211 of 64670 relevant lines covered (32.8%)

8.33 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

87.39
/pkg/openapi/endpoints.go
1
package openapi
2

3
import (
4
        "sort"
5
        "strings"
6
)
7

8
const defaultMethodOrder = 99
9

10
// ExtractEndpoints extracts all endpoints from an OpenAPI spec.
11
func ExtractEndpoints(spec *OpenAPISpec) []Endpoint {
2✔
12
        if spec == nil {
3✔
13
                return nil
1✔
14
        }
1✔
15

16
        var endpoints []Endpoint
1✔
17

1✔
18
        for path, pathItem := range spec.Paths {
3✔
19
                if pathItem.Get != nil {
4✔
20
                        endpoints = append(endpoints, newEndpoint("GET", path, pathItem.Get))
2✔
21
                }
2✔
22
                if pathItem.Post != nil {
3✔
23
                        endpoints = append(endpoints, newEndpoint("POST", path, pathItem.Post))
1✔
24
                }
1✔
25
                if pathItem.Put != nil {
2✔
26
                        endpoints = append(endpoints, newEndpoint("PUT", path, pathItem.Put))
×
27
                }
×
28
                if pathItem.Patch != nil {
2✔
29
                        endpoints = append(endpoints, newEndpoint("PATCH", path, pathItem.Patch))
×
30
                }
×
31
                if pathItem.Delete != nil {
3✔
32
                        endpoints = append(endpoints, newEndpoint("DELETE", path, pathItem.Delete))
1✔
33
                }
1✔
34
                if pathItem.Options != nil {
2✔
35
                        endpoints = append(endpoints, newEndpoint("OPTIONS", path, pathItem.Options))
×
36
                }
×
37
                if pathItem.Head != nil {
2✔
38
                        endpoints = append(endpoints, newEndpoint("HEAD", path, pathItem.Head))
×
39
                }
×
40
        }
41

42
        // Sort endpoints by path, then method
43
        sort.Slice(endpoints, func(i, j int) bool {
4✔
44
                if endpoints[i].Path != endpoints[j].Path {
4✔
45
                        return endpoints[i].Path < endpoints[j].Path
1✔
46
                }
1✔
47
                return methodOrder(endpoints[i].Method) < methodOrder(endpoints[j].Method)
2✔
48
        })
49

50
        return endpoints
1✔
51
}
52

53
// newEndpoint creates an Endpoint from an Operation.
54
func newEndpoint(method, path string, op *Operation) Endpoint {
4✔
55
        return Endpoint{
4✔
56
                Method:      method,
4✔
57
                Path:        path,
4✔
58
                OperationID: op.OperationID,
4✔
59
                Summary:     op.Summary,
4✔
60
                Description: op.Description,
4✔
61
                Tags:        op.Tags,
4✔
62
                Parameters:  op.Parameters,
4✔
63
                RequestBody: op.RequestBody,
4✔
64
                Responses:   op.Responses,
4✔
65
                Deprecated:  op.Deprecated,
4✔
66
        }
4✔
67
}
4✔
68

69
// methodOrder returns an ordering value for HTTP methods.
70
func methodOrder(method string) int {
4✔
71
        order := map[string]int{
4✔
72
                "GET":     1,
4✔
73
                "POST":    2,
4✔
74
                "PUT":     3,
4✔
75
                "PATCH":   4,
4✔
76
                "DELETE":  5,
4✔
77
                "OPTIONS": 6,
4✔
78
                "HEAD":    7,
4✔
79
        }
4✔
80
        if o, ok := order[method]; ok {
8✔
81
                return o
4✔
82
        }
4✔
NEW
83
        return defaultMethodOrder
×
84
}
85

86
// FilterEndpoints returns endpoints matching the given filter string.
87
// The filter is matched against the path, method, operation ID, summary, and tags.
88
func FilterEndpoints(endpoints []Endpoint, filter string) []Endpoint {
6✔
89
        if filter == "" {
7✔
90
                return endpoints
1✔
91
        }
1✔
92

93
        filter = strings.ToLower(filter)
5✔
94
        var filtered []Endpoint
5✔
95

5✔
96
        for i := range endpoints {
25✔
97
                if matchesFilter(&endpoints[i], filter) {
25✔
98
                        filtered = append(filtered, endpoints[i])
5✔
99
                }
5✔
100
        }
101

102
        return filtered
5✔
103
}
104

105
// matchesFilter checks if an endpoint matches the filter string.
106
func matchesFilter(ep *Endpoint, filter string) bool {
20✔
107
        // Check path
20✔
108
        if strings.Contains(strings.ToLower(ep.Path), filter) {
24✔
109
                return true
4✔
110
        }
4✔
111

112
        // Check method
113
        if strings.Contains(strings.ToLower(ep.Method), filter) {
17✔
114
                return true
1✔
115
        }
1✔
116

117
        // Check operation ID
118
        if strings.Contains(strings.ToLower(ep.OperationID), filter) {
15✔
119
                return true
×
120
        }
×
121

122
        // Check summary
123
        if strings.Contains(strings.ToLower(ep.Summary), filter) {
15✔
124
                return true
×
125
        }
×
126

127
        // Check tags
128
        for _, tag := range ep.Tags {
30✔
129
                if strings.Contains(strings.ToLower(tag), filter) {
15✔
130
                        return true
×
131
                }
×
132
        }
133

134
        return false
15✔
135
}
136

137
// FindEndpoint finds an endpoint by method and path.
138
func FindEndpoint(endpoints []Endpoint, method, path string) *Endpoint {
4✔
139
        method = strings.ToUpper(method)
4✔
140
        for i := range endpoints {
12✔
141
                if endpoints[i].Method == method && endpoints[i].Path == path {
10✔
142
                        return &endpoints[i]
2✔
143
                }
2✔
144
        }
145
        return nil
2✔
146
}
147

148
// FindEndpointByPath finds endpoints matching the given path (any method).
149
func FindEndpointByPath(endpoints []Endpoint, path string) []Endpoint {
2✔
150
        var matches []Endpoint
2✔
151
        for i := range endpoints {
8✔
152
                if endpoints[i].Path == path {
8✔
153
                        matches = append(matches, endpoints[i])
2✔
154
                }
2✔
155
        }
156
        return matches
2✔
157
}
158

159
// GetPathParameters extracts path parameters from an endpoint path.
160
// For example, "/organizations/{organizationId}/deployments" returns ["organizationId"].
161
func GetPathParameters(path string) []string {
5✔
162
        var params []string
5✔
163
        start := -1
5✔
164

5✔
165
        for i, c := range path {
177✔
166
                if c == '{' {
181✔
167
                        start = i + 1
9✔
168
                } else if c == '}' && start >= 0 {
181✔
169
                        params = append(params, path[start:i])
9✔
170
                        start = -1
9✔
171
                }
9✔
172
        }
173

174
        return params
5✔
175
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc