Merge pull request #39428 from shiywang/refactor_wideColumns_printer

Automatic merge from submit-queue (batch tested with PRs 39132, 39428)

Move wideHeader [] strings into handlerEntry

To adress this problem: https://github.com/openshift/origin/pull/12354, make `-o wide` more flexible to be used by OpenShift
pull/6/head
Kubernetes Submit Queue 2017-01-06 09:53:20 -08:00 committed by GitHub
commit 0d93a4c360
2 changed files with 127 additions and 149 deletions

View File

@ -351,9 +351,10 @@ func (p *YAMLPrinter) HandledResources() []string {
}
type handlerEntry struct {
columns []string
printFunc reflect.Value
args []reflect.Value
columns []string
columnsWithWide []string
printFunc reflect.Value
args []reflect.Value
}
type PrintOptions struct {
@ -414,7 +415,7 @@ func (h *HumanReadablePrinter) EnsurePrintWithKind(kind string) {
// Handler adds a print handler with a given set of columns to HumanReadablePrinter instance.
// See validatePrintHandlerFunc for required method signature.
func (h *HumanReadablePrinter) Handler(columns []string, printFunc interface{}) error {
func (h *HumanReadablePrinter) Handler(columns, columnsWithWide []string, printFunc interface{}) error {
printFuncValue := reflect.ValueOf(printFunc)
if err := h.validatePrintHandlerFunc(printFuncValue); err != nil {
glog.Errorf("Unable to add print handler: %v", err)
@ -423,8 +424,9 @@ func (h *HumanReadablePrinter) Handler(columns []string, printFunc interface{})
objType := printFuncValue.Type().In(0)
h.handlerMap[objType] = &handlerEntry{
columns: columns,
printFunc: printFuncValue,
columns: columns,
columnsWithWide: columnsWithWide,
printFunc: printFuncValue,
}
return nil
}
@ -475,41 +477,51 @@ func (h *HumanReadablePrinter) AfterPrint(output io.Writer, res string) error {
// NOTE: When adding a new resource type here, please update the list
// pkg/kubectl/cmd/get.go to reflect the new resource type.
var (
podColumns = []string{"NAME", "READY", "STATUS", "RESTARTS", "AGE"}
podTemplateColumns = []string{"TEMPLATE", "CONTAINER(S)", "IMAGE(S)", "PODLABELS"}
podDisruptionBudgetColumns = []string{"NAME", "MIN-AVAILABLE", "ALLOWED-DISRUPTIONS", "AGE"}
replicationControllerColumns = []string{"NAME", "DESIRED", "CURRENT", "READY", "AGE"}
replicaSetColumns = []string{"NAME", "DESIRED", "CURRENT", "READY", "AGE"}
jobColumns = []string{"NAME", "DESIRED", "SUCCESSFUL", "AGE"}
cronJobColumns = []string{"NAME", "SCHEDULE", "SUSPEND", "ACTIVE", "LAST-SCHEDULE"}
serviceColumns = []string{"NAME", "CLUSTER-IP", "EXTERNAL-IP", "PORT(S)", "AGE"}
ingressColumns = []string{"NAME", "HOSTS", "ADDRESS", "PORTS", "AGE"}
statefulSetColumns = []string{"NAME", "DESIRED", "CURRENT", "AGE"}
endpointColumns = []string{"NAME", "ENDPOINTS", "AGE"}
nodeColumns = []string{"NAME", "STATUS", "AGE", "VERSION"}
daemonSetColumns = []string{"NAME", "DESIRED", "CURRENT", "READY", "NODE-SELECTOR", "AGE"}
eventColumns = []string{"LASTSEEN", "FIRSTSEEN", "COUNT", "NAME", "KIND", "SUBOBJECT", "TYPE", "REASON", "SOURCE", "MESSAGE"}
limitRangeColumns = []string{"NAME", "AGE"}
resourceQuotaColumns = []string{"NAME", "AGE"}
namespaceColumns = []string{"NAME", "STATUS", "AGE"}
secretColumns = []string{"NAME", "TYPE", "DATA", "AGE"}
serviceAccountColumns = []string{"NAME", "SECRETS", "AGE"}
persistentVolumeColumns = []string{"NAME", "CAPACITY", "ACCESSMODES", "RECLAIMPOLICY", "STATUS", "CLAIM", "REASON", "AGE"}
persistentVolumeClaimColumns = []string{"NAME", "STATUS", "VOLUME", "CAPACITY", "ACCESSMODES", "AGE"}
componentStatusColumns = []string{"NAME", "STATUS", "MESSAGE", "ERROR"}
thirdPartyResourceColumns = []string{"NAME", "DESCRIPTION", "VERSION(S)"}
roleColumns = []string{"NAME", "AGE"}
roleBindingColumns = []string{"NAME", "AGE"}
clusterRoleColumns = []string{"NAME", "AGE"}
clusterRoleBindingColumns = []string{"NAME", "AGE"}
storageClassColumns = []string{"NAME", "TYPE"}
statusColumns = []string{"STATUS", "REASON", "MESSAGE"}
podColumns = []string{"NAME", "READY", "STATUS", "RESTARTS", "AGE"}
podWideColumns = []string{"IP", "NODE"}
podTemplateColumns = []string{"TEMPLATE", "CONTAINER(S)", "IMAGE(S)", "PODLABELS"}
podDisruptionBudgetColumns = []string{"NAME", "MIN-AVAILABLE", "ALLOWED-DISRUPTIONS", "AGE"}
replicationControllerColumns = []string{"NAME", "DESIRED", "CURRENT", "READY", "AGE"}
replicationControllerWideColumns = []string{"CONTAINER(S)", "IMAGE(S)", "SELECTOR"}
replicaSetColumns = []string{"NAME", "DESIRED", "CURRENT", "READY", "AGE"}
replicaSetWideColumns = []string{"CONTAINER(S)", "IMAGE(S)", "SELECTOR"}
jobColumns = []string{"NAME", "DESIRED", "SUCCESSFUL", "AGE"}
cronJobColumns = []string{"NAME", "SCHEDULE", "SUSPEND", "ACTIVE", "LAST-SCHEDULE"}
batchJobWideColumns = []string{"CONTAINER(S)", "IMAGE(S)", "SELECTOR"}
serviceColumns = []string{"NAME", "CLUSTER-IP", "EXTERNAL-IP", "PORT(S)", "AGE"}
serviceWideColumns = []string{"SELECTOR"}
ingressColumns = []string{"NAME", "HOSTS", "ADDRESS", "PORTS", "AGE"}
statefulSetColumns = []string{"NAME", "DESIRED", "CURRENT", "AGE"}
endpointColumns = []string{"NAME", "ENDPOINTS", "AGE"}
nodeColumns = []string{"NAME", "STATUS", "AGE", "VERSION"}
nodeWideColumns = []string{"EXTERNAL-IP"}
daemonSetColumns = []string{"NAME", "DESIRED", "CURRENT", "READY", "NODE-SELECTOR", "AGE"}
daemonSetWideColumns = []string{"CONTAINER(S)", "IMAGE(S)", "SELECTOR"}
eventColumns = []string{"LASTSEEN", "FIRSTSEEN", "COUNT", "NAME", "KIND", "SUBOBJECT", "TYPE", "REASON", "SOURCE", "MESSAGE"}
limitRangeColumns = []string{"NAME", "AGE"}
resourceQuotaColumns = []string{"NAME", "AGE"}
namespaceColumns = []string{"NAME", "STATUS", "AGE"}
secretColumns = []string{"NAME", "TYPE", "DATA", "AGE"}
serviceAccountColumns = []string{"NAME", "SECRETS", "AGE"}
persistentVolumeColumns = []string{"NAME", "CAPACITY", "ACCESSMODES", "RECLAIMPOLICY", "STATUS", "CLAIM", "REASON", "AGE"}
persistentVolumeClaimColumns = []string{"NAME", "STATUS", "VOLUME", "CAPACITY", "ACCESSMODES", "AGE"}
componentStatusColumns = []string{"NAME", "STATUS", "MESSAGE", "ERROR"}
thirdPartyResourceColumns = []string{"NAME", "DESCRIPTION", "VERSION(S)"}
roleColumns = []string{"NAME", "AGE"}
roleBindingColumns = []string{"NAME", "AGE"}
roleBindingWideColumns = []string{"ROLE", "USERS", "GROUPS", "SERVICEACCOUNTS"}
clusterRoleColumns = []string{"NAME", "AGE"}
clusterRoleBindingColumns = []string{"NAME", "AGE"}
clusterRoleBindingWideColumns = []string{"ROLE", "USERS", "GROUPS", "SERVICEACCOUNTS"}
storageClassColumns = []string{"NAME", "TYPE"}
statusColumns = []string{"STATUS", "REASON", "MESSAGE"}
// TODO: consider having 'KIND' for third party resource data
thirdPartyResourceDataColumns = []string{"NAME", "LABELS", "DATA"}
horizontalPodAutoscalerColumns = []string{"NAME", "REFERENCE", "TARGET", "CURRENT", "MINPODS", "MAXPODS", "AGE"}
withNamespacePrefixColumns = []string{"NAMESPACE"} // TODO(erictune): print cluster name too.
deploymentColumns = []string{"NAME", "DESIRED", "CURRENT", "UP-TO-DATE", "AVAILABLE", "AGE"}
deploymentWideColumns = []string{"CONTAINER(S)", "IMAGE(S)", "SELECTOR"}
configMapColumns = []string{"NAME", "DATA", "AGE"}
podSecurityPolicyColumns = []string{"NAME", "PRIV", "CAPS", "SELINUX", "RUNASUSER", "FSGROUP", "SUPGROUP", "READONLYROOTFS", "VOLUMES"}
clusterColumns = []string{"NAME", "STATUS", "AGE"}
@ -536,79 +548,79 @@ func (h *HumanReadablePrinter) printPodList(podList *api.PodList, w io.Writer, o
// addDefaultHandlers adds print handlers for default Kubernetes types.
func (h *HumanReadablePrinter) addDefaultHandlers() {
h.Handler(podColumns, h.printPodList)
h.Handler(podColumns, h.printPod)
h.Handler(podTemplateColumns, printPodTemplate)
h.Handler(podTemplateColumns, printPodTemplateList)
h.Handler(podDisruptionBudgetColumns, printPodDisruptionBudget)
h.Handler(podDisruptionBudgetColumns, printPodDisruptionBudgetList)
h.Handler(replicationControllerColumns, printReplicationController)
h.Handler(replicationControllerColumns, printReplicationControllerList)
h.Handler(replicaSetColumns, printReplicaSet)
h.Handler(replicaSetColumns, printReplicaSetList)
h.Handler(daemonSetColumns, printDaemonSet)
h.Handler(daemonSetColumns, printDaemonSetList)
h.Handler(jobColumns, printJob)
h.Handler(jobColumns, printJobList)
h.Handler(cronJobColumns, printCronJob)
h.Handler(cronJobColumns, printCronJobList)
h.Handler(serviceColumns, printService)
h.Handler(serviceColumns, printServiceList)
h.Handler(ingressColumns, printIngress)
h.Handler(ingressColumns, printIngressList)
h.Handler(statefulSetColumns, printStatefulSet)
h.Handler(statefulSetColumns, printStatefulSetList)
h.Handler(endpointColumns, printEndpoints)
h.Handler(endpointColumns, printEndpointsList)
h.Handler(nodeColumns, printNode)
h.Handler(nodeColumns, printNodeList)
h.Handler(eventColumns, printEvent)
h.Handler(eventColumns, printEventList)
h.Handler(limitRangeColumns, printLimitRange)
h.Handler(limitRangeColumns, printLimitRangeList)
h.Handler(resourceQuotaColumns, printResourceQuota)
h.Handler(resourceQuotaColumns, printResourceQuotaList)
h.Handler(namespaceColumns, printNamespace)
h.Handler(namespaceColumns, printNamespaceList)
h.Handler(secretColumns, printSecret)
h.Handler(secretColumns, printSecretList)
h.Handler(serviceAccountColumns, printServiceAccount)
h.Handler(serviceAccountColumns, printServiceAccountList)
h.Handler(persistentVolumeClaimColumns, printPersistentVolumeClaim)
h.Handler(persistentVolumeClaimColumns, printPersistentVolumeClaimList)
h.Handler(persistentVolumeColumns, printPersistentVolume)
h.Handler(persistentVolumeColumns, printPersistentVolumeList)
h.Handler(componentStatusColumns, printComponentStatus)
h.Handler(componentStatusColumns, printComponentStatusList)
h.Handler(thirdPartyResourceColumns, printThirdPartyResource)
h.Handler(thirdPartyResourceColumns, printThirdPartyResourceList)
h.Handler(deploymentColumns, printDeployment)
h.Handler(deploymentColumns, printDeploymentList)
h.Handler(horizontalPodAutoscalerColumns, printHorizontalPodAutoscaler)
h.Handler(horizontalPodAutoscalerColumns, printHorizontalPodAutoscalerList)
h.Handler(configMapColumns, printConfigMap)
h.Handler(configMapColumns, printConfigMapList)
h.Handler(podSecurityPolicyColumns, printPodSecurityPolicy)
h.Handler(podSecurityPolicyColumns, printPodSecurityPolicyList)
h.Handler(thirdPartyResourceDataColumns, printThirdPartyResourceData)
h.Handler(thirdPartyResourceDataColumns, printThirdPartyResourceDataList)
h.Handler(clusterColumns, printCluster)
h.Handler(clusterColumns, printClusterList)
h.Handler(networkPolicyColumns, printNetworkPolicy)
h.Handler(networkPolicyColumns, printNetworkPolicyList)
h.Handler(roleColumns, printRole)
h.Handler(roleColumns, printRoleList)
h.Handler(roleBindingColumns, printRoleBinding)
h.Handler(roleBindingColumns, printRoleBindingList)
h.Handler(clusterRoleColumns, printClusterRole)
h.Handler(clusterRoleColumns, printClusterRoleList)
h.Handler(clusterRoleBindingColumns, printClusterRoleBinding)
h.Handler(clusterRoleBindingColumns, printClusterRoleBindingList)
h.Handler(certificateSigningRequestColumns, printCertificateSigningRequest)
h.Handler(certificateSigningRequestColumns, printCertificateSigningRequestList)
h.Handler(storageClassColumns, printStorageClass)
h.Handler(storageClassColumns, printStorageClassList)
h.Handler(statusColumns, printStatus)
h.Handler(podColumns, podWideColumns, h.printPodList)
h.Handler(podColumns, podWideColumns, h.printPod)
h.Handler(podTemplateColumns, nil, printPodTemplate)
h.Handler(podTemplateColumns, nil, printPodTemplateList)
h.Handler(podDisruptionBudgetColumns, nil, printPodDisruptionBudget)
h.Handler(podDisruptionBudgetColumns, nil, printPodDisruptionBudgetList)
h.Handler(replicationControllerColumns, replicationControllerWideColumns, printReplicationController)
h.Handler(replicationControllerColumns, replicationControllerWideColumns, printReplicationControllerList)
h.Handler(replicaSetColumns, replicaSetWideColumns, printReplicaSet)
h.Handler(replicaSetColumns, replicaSetWideColumns, printReplicaSetList)
h.Handler(daemonSetColumns, daemonSetWideColumns, printDaemonSet)
h.Handler(daemonSetColumns, daemonSetWideColumns, printDaemonSetList)
h.Handler(jobColumns, batchJobWideColumns, printJob)
h.Handler(jobColumns, batchJobWideColumns, printJobList)
h.Handler(cronJobColumns, batchJobWideColumns, printCronJob)
h.Handler(cronJobColumns, batchJobWideColumns, printCronJobList)
h.Handler(serviceColumns, serviceWideColumns, printService)
h.Handler(serviceColumns, serviceWideColumns, printServiceList)
h.Handler(ingressColumns, nil, printIngress)
h.Handler(ingressColumns, nil, printIngressList)
h.Handler(statefulSetColumns, nil, printStatefulSet)
h.Handler(statefulSetColumns, nil, printStatefulSetList)
h.Handler(endpointColumns, nil, printEndpoints)
h.Handler(endpointColumns, nil, printEndpointsList)
h.Handler(nodeColumns, nodeWideColumns, printNode)
h.Handler(nodeColumns, nodeWideColumns, printNodeList)
h.Handler(eventColumns, nil, printEvent)
h.Handler(eventColumns, nil, printEventList)
h.Handler(limitRangeColumns, nil, printLimitRange)
h.Handler(limitRangeColumns, nil, printLimitRangeList)
h.Handler(resourceQuotaColumns, nil, printResourceQuota)
h.Handler(resourceQuotaColumns, nil, printResourceQuotaList)
h.Handler(namespaceColumns, nil, printNamespace)
h.Handler(namespaceColumns, nil, printNamespaceList)
h.Handler(secretColumns, nil, printSecret)
h.Handler(secretColumns, nil, printSecretList)
h.Handler(serviceAccountColumns, nil, printServiceAccount)
h.Handler(serviceAccountColumns, nil, printServiceAccountList)
h.Handler(persistentVolumeClaimColumns, nil, printPersistentVolumeClaim)
h.Handler(persistentVolumeClaimColumns, nil, printPersistentVolumeClaimList)
h.Handler(persistentVolumeColumns, nil, printPersistentVolume)
h.Handler(persistentVolumeColumns, nil, printPersistentVolumeList)
h.Handler(componentStatusColumns, nil, printComponentStatus)
h.Handler(componentStatusColumns, nil, printComponentStatusList)
h.Handler(thirdPartyResourceColumns, nil, printThirdPartyResource)
h.Handler(thirdPartyResourceColumns, nil, printThirdPartyResourceList)
h.Handler(deploymentColumns, deploymentWideColumns, printDeployment)
h.Handler(deploymentColumns, deploymentWideColumns, printDeploymentList)
h.Handler(horizontalPodAutoscalerColumns, nil, printHorizontalPodAutoscaler)
h.Handler(horizontalPodAutoscalerColumns, nil, printHorizontalPodAutoscalerList)
h.Handler(configMapColumns, nil, printConfigMap)
h.Handler(configMapColumns, nil, printConfigMapList)
h.Handler(podSecurityPolicyColumns, nil, printPodSecurityPolicy)
h.Handler(podSecurityPolicyColumns, nil, printPodSecurityPolicyList)
h.Handler(thirdPartyResourceDataColumns, nil, printThirdPartyResourceData)
h.Handler(thirdPartyResourceDataColumns, nil, printThirdPartyResourceDataList)
h.Handler(clusterColumns, nil, printCluster)
h.Handler(clusterColumns, nil, printClusterList)
h.Handler(networkPolicyColumns, nil, printNetworkPolicy)
h.Handler(networkPolicyColumns, nil, printNetworkPolicyList)
h.Handler(roleColumns, nil, printRole)
h.Handler(roleColumns, nil, printRoleList)
h.Handler(roleBindingColumns, roleBindingWideColumns, printRoleBinding)
h.Handler(roleBindingColumns, roleBindingWideColumns, printRoleBindingList)
h.Handler(clusterRoleColumns, nil, printClusterRole)
h.Handler(clusterRoleColumns, nil, printClusterRoleList)
h.Handler(clusterRoleBindingColumns, clusterRoleBindingWideColumns, printClusterRoleBinding)
h.Handler(clusterRoleBindingColumns, clusterRoleBindingWideColumns, printClusterRoleBindingList)
h.Handler(certificateSigningRequestColumns, nil, printCertificateSigningRequest)
h.Handler(certificateSigningRequestColumns, nil, printCertificateSigningRequestList)
h.Handler(storageClassColumns, nil, printStorageClass)
h.Handler(storageClassColumns, nil, printStorageClassList)
h.Handler(statusColumns, nil, printStatus)
}
func (h *HumanReadablePrinter) unknown(data []byte, w io.Writer) error {
@ -2350,43 +2362,6 @@ func formatLabelHeaders(columnLabels []string) []string {
return formHead
}
// headers for -o wide
func formatWideHeaders(wide bool, t reflect.Type) []string {
if wide {
if t.String() == "*api.Pod" || t.String() == "*api.PodList" {
return []string{"IP", "NODE"}
}
if t.String() == "*api.ReplicationController" || t.String() == "*api.ReplicationControllerList" {
return []string{"CONTAINER(S)", "IMAGE(S)", "SELECTOR"}
}
if t.String() == "*batch.Job" || t.String() == "*batch.JobList" {
return []string{"CONTAINER(S)", "IMAGE(S)", "SELECTOR"}
}
if t.String() == "*api.Service" || t.String() == "*api.ServiceList" {
return []string{"SELECTOR"}
}
if t.String() == "*extensions.DaemonSet" || t.String() == "*extensions.DaemonSetList" {
return []string{"CONTAINER(S)", "IMAGE(S)", "SELECTOR"}
}
if t.String() == "*extensions.Deployment" || t.String() == "*extensions.DeploymentList" {
return []string{"CONTAINER(S)", "IMAGE(S)", "SELECTOR"}
}
if t.String() == "*extensions.ReplicaSet" || t.String() == "*extensions.ReplicaSetList" {
return []string{"CONTAINER(S)", "IMAGE(S)", "SELECTOR"}
}
if t.String() == "*api.Node" || t.String() == "*api.NodeList" {
return []string{"EXTERNAL-IP"}
}
if t.String() == "*rbac.RoleBinding" || t.String() == "*rbac.RoleBindingList" {
return []string{"ROLE", "USERS", "GROUPS", "SERVICEACCOUNTS"}
}
if t.String() == "*rbac.ClusterRoleBinding" || t.String() == "*rbac.ClusterRoleBindingList" {
return []string{"ROLE", "USERS", "GROUPS", "SERVICEACCOUNTS"}
}
}
return nil
}
// headers for --show-labels=true
func formatShowLabelsHeader(showLabels bool, t reflect.Type) []string {
if showLabels {
@ -2418,7 +2393,10 @@ func (h *HumanReadablePrinter) PrintObj(obj runtime.Object, output io.Writer) er
t := reflect.TypeOf(obj)
if handler := h.handlerMap[t]; handler != nil {
if !h.options.NoHeaders && t != h.lastType {
headers := append(handler.columns, formatWideHeaders(h.options.Wide, t)...)
headers := handler.columns
if h.options.Wide {
headers = append(headers, handler.columnsWithWide...)
}
headers = append(headers, formatLabelHeaders(h.options.ColumnLabels)...)
// LABELS is always the last column.
headers = append(headers, formatShowLabelsHeader(h.options.ShowLabels, t)...)

View File

@ -256,7 +256,7 @@ func ErrorPrintHandler(obj *TestPrintType, w io.Writer, options PrintOptions) er
func TestCustomTypePrinting(t *testing.T) {
columns := []string{"Data"}
printer := NewHumanReadablePrinter(PrintOptions{})
printer.Handler(columns, PrintCustomType)
printer.Handler(columns, nil, PrintCustomType)
obj := TestPrintType{"test object"}
buffer := &bytes.Buffer{}
@ -273,7 +273,7 @@ func TestCustomTypePrinting(t *testing.T) {
func TestCustomTypePrintingWithKind(t *testing.T) {
columns := []string{"Data"}
printer := NewHumanReadablePrinter(PrintOptions{})
printer.Handler(columns, PrintCustomType)
printer.Handler(columns, nil, PrintCustomType)
printer.EnsurePrintWithKind("test")
obj := TestPrintType{"test object"}
@ -291,7 +291,7 @@ func TestCustomTypePrintingWithKind(t *testing.T) {
func TestPrintHandlerError(t *testing.T) {
columns := []string{"Data"}
printer := NewHumanReadablePrinter(PrintOptions{})
printer.Handler(columns, ErrorPrintHandler)
printer.Handler(columns, nil, ErrorPrintHandler)
obj := TestPrintType{"test object"}
buffer := &bytes.Buffer{}
err := printer.PrintObj(&obj, buffer)