Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
K
k3s
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Jacklull
k3s
Commits
4b36b421
Commit
4b36b421
authored
Jun 30, 2015
by
Jeff Lowdermilk
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
e2e test for kubectl exec, port-forward
parent
f0a36b0a
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
103 additions
and
0 deletions
+103
-0
kubectl.go
test/e2e/kubectl.go
+88
-0
util.go
test/e2e/util.go
+15
-0
No files found.
test/e2e/kubectl.go
View file @
4b36b421
...
@@ -20,7 +20,10 @@ import (
...
@@ -20,7 +20,10 @@ import (
"encoding/json"
"encoding/json"
"errors"
"errors"
"fmt"
"fmt"
"io/ioutil"
"net/http"
"path/filepath"
"path/filepath"
"regexp"
"strings"
"strings"
"time"
"time"
...
@@ -42,6 +45,14 @@ const (
...
@@ -42,6 +45,14 @@ const (
kubectlProxyPort
=
8011
kubectlProxyPort
=
8011
guestbookStartupTimeout
=
10
*
time
.
Minute
guestbookStartupTimeout
=
10
*
time
.
Minute
guestbookResponseTimeout
=
3
*
time
.
Minute
guestbookResponseTimeout
=
3
*
time
.
Minute
simplePodSelector
=
"name=nginx"
simplePodName
=
"nginx"
nginxDefaultOutput
=
"Welcome to nginx!"
simplePodPort
=
80
)
var
(
portForwardRegexp
=
regexp
.
MustCompile
(
"Forwarding from 127.0.0.1:([0-9]+) -> 80"
)
)
)
var
_
=
Describe
(
"Kubectl client"
,
func
()
{
var
_
=
Describe
(
"Kubectl client"
,
func
()
{
...
@@ -127,8 +138,85 @@ var _ = Describe("Kubectl client", func() {
...
@@ -127,8 +138,85 @@ var _ = Describe("Kubectl client", func() {
})
})
})
})
Describe
(
"Simple pod"
,
func
()
{
var
podPath
string
BeforeEach
(
func
()
{
podPath
=
filepath
.
Join
(
testContext
.
RepoRoot
,
"examples/pod.yaml"
)
By
(
"creating the pod"
)
runKubectl
(
"create"
,
"-f"
,
podPath
,
fmt
.
Sprintf
(
"--namespace=%v"
,
ns
))
checkPodsRunningReady
(
c
,
ns
,
[]
string
{
simplePodName
},
podStartTimeout
)
})
AfterEach
(
func
()
{
cleanup
(
podPath
,
ns
,
simplePodSelector
)
})
It
(
"should support exec"
,
func
()
{
By
(
"executing a command in the container"
)
execOutput
:=
runKubectl
(
"exec"
,
fmt
.
Sprintf
(
"--namespace=%v"
,
ns
),
simplePodName
,
"echo"
,
"running"
,
"in"
,
"container"
)
expectedExecOutput
:=
"running in container"
if
execOutput
!=
expectedExecOutput
{
Failf
(
"Unexpected kubectl exec output. Wanted '%s', got '%s'"
,
execOutput
,
expectedExecOutput
)
}
})
It
(
"should support port-forward"
,
func
()
{
By
(
"forwarding the container port to a local port"
)
cmd
:=
kubectlCmd
(
"port-forward"
,
fmt
.
Sprintf
(
"--namespace=%v"
,
ns
),
"-p"
,
simplePodName
,
fmt
.
Sprintf
(
":%d"
,
simplePodPort
))
defer
func
()
{
if
err
:=
cmd
.
Process
.
Kill
();
err
!=
nil
{
Logf
(
"ERROR failed to kill kubectl port-forward command! The process may leak"
)
}
}()
// This is somewhat ugly but is the only way to retrieve the port that was picked
// by the port-forward command. We don't want to hard code the port as we have no
// way of guaranteeing we can pick one that isn't in use, particularly on Jenkins.
Logf
(
"starting port-forward command and streaming output"
)
stdout
,
stderr
,
err
:=
startCmdAndStreamOutput
(
cmd
)
if
err
!=
nil
{
Failf
(
"Failed to start port-forward command: %v"
,
err
)
}
defer
stdout
.
Close
()
defer
stderr
.
Close
()
buf
:=
make
([]
byte
,
128
)
var
n
int
Logf
(
"reading from `kubectl port-forward` command's stderr"
)
if
n
,
err
=
stderr
.
Read
(
buf
);
err
!=
nil
{
Failf
(
"Failed to read from kubectl port-forward stderr: %v"
,
err
)
}
portForwardOutput
:=
string
(
buf
[
:
n
])
match
:=
portForwardRegexp
.
FindStringSubmatch
(
portForwardOutput
)
if
len
(
match
)
!=
2
{
Failf
(
"Failed to parse kubectl port-forward output: %s"
,
portForwardOutput
)
}
By
(
"curling local port output"
)
localAddr
:=
fmt
.
Sprintf
(
"http://localhost:%s"
,
match
[
1
])
body
,
err
:=
curl
(
localAddr
)
if
err
!=
nil
{
Failf
(
"Failed http.Get of forwarded port (%s): %v"
,
localAddr
,
err
)
}
if
!
strings
.
Contains
(
body
,
nginxDefaultOutput
)
{
Failf
(
"Container port output missing expected value. Wanted:'%s', got: %s"
,
nginxDefaultOutput
,
body
)
}
})
})
})
})
func
curl
(
addr
string
)
(
string
,
error
)
{
resp
,
err
:=
http
.
Get
(
addr
)
if
err
!=
nil
{
return
""
,
err
}
defer
resp
.
Body
.
Close
()
body
,
err
:=
ioutil
.
ReadAll
(
resp
.
Body
)
if
err
!=
nil
{
return
""
,
err
}
return
string
(
body
[
:
]),
nil
}
func
validateGuestbookApp
(
c
*
client
.
Client
,
ns
string
)
{
func
validateGuestbookApp
(
c
*
client
.
Client
,
ns
string
)
{
Logf
(
"Waiting for frontend to serve content."
)
Logf
(
"Waiting for frontend to serve content."
)
if
!
waitForGuestbookResponse
(
c
,
"get"
,
""
,
`{"data": ""}`
,
guestbookStartupTimeout
,
ns
)
{
if
!
waitForGuestbookResponse
(
c
,
"get"
,
""
,
`{"data": ""}`
,
guestbookStartupTimeout
,
ns
)
{
...
...
test/e2e/util.go
View file @
4b36b421
...
@@ -19,6 +19,7 @@ package e2e
...
@@ -19,6 +19,7 @@ package e2e
import
(
import
(
"bytes"
"bytes"
"fmt"
"fmt"
"io"
"io/ioutil"
"io/ioutil"
"math"
"math"
"math/rand"
"math/rand"
...
@@ -832,6 +833,20 @@ func runKubectl(args ...string) string {
...
@@ -832,6 +833,20 @@ func runKubectl(args ...string) string {
return
strings
.
TrimSpace
(
stdout
.
String
())
return
strings
.
TrimSpace
(
stdout
.
String
())
}
}
func
startCmdAndStreamOutput
(
cmd
*
exec
.
Cmd
)
(
stdout
,
stderr
io
.
ReadCloser
,
err
error
)
{
stdout
,
err
=
cmd
.
StdoutPipe
()
if
err
!=
nil
{
return
}
stderr
,
err
=
cmd
.
StderrPipe
()
if
err
!=
nil
{
return
}
Logf
(
"Asyncronously running '%s %s'"
,
cmd
.
Path
,
strings
.
Join
(
cmd
.
Args
,
" "
))
err
=
cmd
.
Start
()
return
}
// testContainerOutput runs testContainerOutputInNamespace with the default namespace.
// testContainerOutput runs testContainerOutputInNamespace with the default namespace.
func
testContainerOutput
(
scenarioName
string
,
c
*
client
.
Client
,
pod
*
api
.
Pod
,
containerIndex
int
,
expectedOutput
[]
string
)
{
func
testContainerOutput
(
scenarioName
string
,
c
*
client
.
Client
,
pod
*
api
.
Pod
,
containerIndex
int
,
expectedOutput
[]
string
)
{
testContainerOutputInNamespace
(
scenarioName
,
c
,
pod
,
containerIndex
,
expectedOutput
,
api
.
NamespaceDefault
)
testContainerOutputInNamespace
(
scenarioName
,
c
,
pod
,
containerIndex
,
expectedOutput
,
api
.
NamespaceDefault
)
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment