/
options.go
165 lines (138 loc) · 4.53 KB
/
options.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
package mesh
// Options.go holds the option settings for a single graph request.
import (
"context"
"fmt"
"net/http"
"net/url"
"strconv"
"strings"
"time"
"k8s.io/client-go/tools/clientcmd/api"
"github.com/kiali/kiali/business"
"github.com/kiali/kiali/business/authentication"
)
// The supported vendors
const (
VendorCytoscape string = "cytoscape"
defaultConfigVendor string = VendorCytoscape
)
const (
BoxByCluster string = "cluster"
BoxByDataPlanes string = "dataplanes"
BoxByNamespace string = "namespace"
)
// CommonOptions are those supplied to Vendors
type CommonOptions struct {
Params url.Values // make available the raw query params for vendor-specific handling
QueryTime int64 // unix time in seconds
}
// ConfigOptions are those supplied to Config Vendors
type ConfigOptions struct {
BoxBy string
CommonOptions
}
type RequestedAppenders struct {
All bool
AppenderNames []string
}
// ClusterSensitiveKey is the recommended [string] type for maps keying on a cluster-sensitive name
type ClusterSensitiveKey = string
// GetClusterSensitiveKey returns a valid key for maps using a ClusterSensitiveKey
func GetClusterSensitiveKey(cluster, name string) ClusterSensitiveKey {
return fmt.Sprintf("%s:%s", cluster, name)
}
type AccessibleNamespace struct {
Cluster string
CreationTimestamp time.Time
Name string
}
// AccessibleNamepaces is a map with Key: ClusterSensitive namespace Key, Value: *AccessibleNamespace
type AccessibleNamespaces map[ClusterSensitiveKey]*AccessibleNamespace
// Options comprises all available options
type Options struct {
AccessibleNamespaces AccessibleNamespaces
Appenders RequestedAppenders // requested appenders, nil if param not supplied
ConfigVendor string
Namespaces NamespaceInfoMap
ConfigOptions
}
func NewOptions(r *http.Request) Options {
// path variables (0 or more will be set)
// vars := mux.Vars(r)
// query params
params := r.URL.Query()
var queryTime int64
appenders := RequestedAppenders{All: true}
configVendor := params.Get("configVendor")
queryTimeString := params.Get("queryTime")
if _, ok := params["appenders"]; ok {
appenderNames := strings.Split(params.Get("appenders"), ",")
for i, appenderName := range appenderNames {
appenderNames[i] = strings.TrimSpace(appenderName)
}
appenders = RequestedAppenders{All: false, AppenderNames: appenderNames}
}
if configVendor == "" {
configVendor = defaultConfigVendor
} else if configVendor != VendorCytoscape {
BadRequest(fmt.Sprintf("Invalid configVendor [%s]", configVendor))
}
if queryTimeString == "" {
queryTime = time.Now().Unix()
} else {
var queryTimeErr error
queryTime, queryTimeErr = strconv.ParseInt(queryTimeString, 10, 64)
if queryTimeErr != nil {
BadRequest(fmt.Sprintf("Invalid queryTime [%s]", queryTimeString))
}
}
// Process namespaces options:
namespaceMap := NewNamespaceInfoMap()
authInfoContext := authentication.GetAuthInfoContext(r.Context())
var authInfo *api.AuthInfo
if authInfoContext != nil {
if authInfoCheck, ok := authInfoContext.(*api.AuthInfo); !ok {
Error("authInfo is not of type *api.AuthInfo")
} else {
authInfo = authInfoCheck
}
} else {
Error("token missing in request context")
}
accessibleNamespaces := getAccessibleNamespaces(authInfo)
options := Options{
AccessibleNamespaces: accessibleNamespaces,
Appenders: appenders,
Namespaces: namespaceMap,
ConfigVendor: configVendor,
ConfigOptions: ConfigOptions{
CommonOptions: CommonOptions{
Params: params,
QueryTime: queryTime,
},
},
}
return options
}
// getAccessibleNamespaces returns a Set of all namespaces accessible to the user.
// The Set is implemented using the map convention. Each map entry is set to the
// creation timestamp of the namespace, to be used to ensure valid time ranges for
// queries against the namespace.
func getAccessibleNamespaces(authInfo *api.AuthInfo) AccessibleNamespaces {
// Get the namespaces
business, err := business.Get(authInfo)
CheckError(err)
namespaces, err := business.Namespace.GetNamespaces(context.TODO())
CheckError(err)
// Create a map to store the namespaces
accessibleNamespaces := make(AccessibleNamespaces)
for _, namespace := range namespaces {
accessibleNamespaces[GetClusterSensitiveKey(namespace.Cluster, namespace.Name)] = &AccessibleNamespace{
Cluster: namespace.Cluster,
CreationTimestamp: namespace.CreationTimestamp,
Name: namespace.Name,
}
}
return accessibleNamespaces
}