7
7
"flag"
8
8
"fmt"
9
9
"os"
10
+ "sort"
10
11
"sync"
11
12
12
13
v1 "k8s.io/api/core/v1"
@@ -36,6 +37,18 @@ const (
36
37
podNameColor = BrightCyan
37
38
)
38
39
40
+ type PodResult struct {
41
+ PodName string
42
+ Output string
43
+ Error error
44
+ }
45
+
46
+ type ByPodName []PodResult
47
+
48
+ func (p ByPodName ) Len () int { return len (p ) }
49
+ func (p ByPodName ) Less (i , j int ) bool { return p [i ].PodName < p [j ].PodName }
50
+ func (p ByPodName ) Swap (i , j int ) { p [i ], p [j ] = p [j ], p [i ] }
51
+
39
52
func main () {
40
53
kubeconfig := flag .String ("kubeconfig" , "" , "Path to the kubeconfig file" )
41
54
containerFlag := flag .String ("c" , "" , "Container to execute the command against" )
@@ -79,38 +92,40 @@ func main() {
79
92
}
80
93
81
94
var wg sync.WaitGroup
82
- results := make (chan string , len (pods .Items ))
95
+ resultsChan := make (chan PodResult , len (pods .Items ))
83
96
84
97
for _ , pod := range pods .Items {
85
98
wg .Add (1 )
86
99
go func (p v1.Pod ) {
87
100
defer wg .Done ()
88
- output , err := execCommand (config , clientset , p , * containerFlag , args )
89
- if err != nil {
90
- results <- fmt .Sprintf ("Error executing command on pod %s: %v" , p .Name , err )
91
- } else {
92
- results <- fmt .Sprintf ("%sPod %s\n %s%s" ,
93
- colorize (divColor , divText ),
94
- colorize (podNameColor , p .Name ),
95
- colorize (divColor , divText ),
96
- output )
97
- }
101
+ resultsChan <- execCommand (config , clientset , p , * containerFlag , args )
98
102
}(pod )
99
103
}
100
104
101
105
wg .Wait ()
102
- close (results )
106
+ close (resultsChan )
107
+
108
+ var results []PodResult
109
+ for result := range resultsChan {
110
+ results = append (results , result )
111
+ }
112
+
113
+ sort .Sort (ByPodName (results ))
103
114
104
- for result := range results {
105
- fmt .Println (result )
115
+ for _ , result := range results {
116
+ fmt .Printf ("%sPod %s\n %s%s" ,
117
+ colorize (divColor , divText ),
118
+ colorize (podNameColor , result .PodName ),
119
+ colorize (divColor , divText ),
120
+ result .Output )
106
121
}
107
122
}
108
123
109
124
func colorize (colorCode ColorCode , text string ) string {
110
125
return fmt .Sprintf ("\033 [%dm%s\033 [0m" , colorCode , text )
111
126
}
112
127
113
- func execCommand (config * rest.Config , clientset * kubernetes.Clientset , pod v1.Pod , container string , command []string ) ( string , error ) {
128
+ func execCommand (config * rest.Config , clientset * kubernetes.Clientset , pod v1.Pod , container string , command []string ) PodResult {
114
129
req := clientset .CoreV1 ().RESTClient ().Post ().
115
130
Resource ("pods" ).
116
131
Name (pod .Name ).
@@ -125,7 +140,7 @@ func execCommand(config *rest.Config, clientset *kubernetes.Clientset, pod v1.Po
125
140
126
141
exec , err := remotecommand .NewSPDYExecutor (config , "POST" , req .URL ())
127
142
if err != nil {
128
- return "" , err
143
+ return PodResult { pod . Name , "" , err }
129
144
}
130
145
131
146
var stdout , stderr bytes.Buffer
@@ -135,12 +150,12 @@ func execCommand(config *rest.Config, clientset *kubernetes.Clientset, pod v1.Po
135
150
})
136
151
137
152
if err != nil {
138
- return "" , err
153
+ return PodResult { pod . Name , "" , err }
139
154
}
140
155
141
156
if stderr .Len () > 0 {
142
- return stdout .String (), fmt .Errorf ("stderr: %s" , stderr .String ())
157
+ return PodResult { pod . Name , stdout .String (), fmt .Errorf ("stderr: %s" , stderr .String ())}
143
158
}
144
159
145
- return stdout .String (), nil
160
+ return PodResult { pod . Name , stdout .String (), nil }
146
161
}
0 commit comments