I want to automate kubectl
and helm
commands using Ansible. The target machine is configured properly, so that both works on the cli in a manual shell (e.g. kubectl get nodes
or helm list
). But when trying to make any API calls like get the server version
- name: List charts
shell: kubectl version -v=8
It breaks with a Forbidden error. The verbose logging doesn't give me much more details:
fatal: [127.0.0.1]: FAILED! => changed=true
cmd: kubectl version -v=10
delta: '0:00:00.072452'
end: '2020-02-27 15:22:36.227928'
msg: non-zero return code
rc: 255
start: '2020-02-27 15:22:36.155476'
stderr: |-
I0227 15:22:36.224517 27321 loader.go:359] Config loaded from file /home/user/.kube/config
I0227 15:22:36.225211 27321 round_trippers.go:386] curl -k -v -XGET -H "Accept: application/json, */*" -H "User-Agent: kubectl/v1.11.3 (linux/amd64) kubernetes/a452946" 'https://k8smaster01:6443/version?timeout=32s'
I0227 15:22:36.225975 27321 round_trippers.go:405] GET https://k8smaster01:6443/version?timeout=32s in 0 milliseconds
I0227 15:22:36.225986 27321 round_trippers.go:411] Response Headers:
I0227 15:22:36.226062 27321 helpers.go:219] Connection error: Get https://k8smaster01:6443/version?timeout=32s: Forbidden
F0227 15:22:36.226080 27321 helpers.go:119] Unable to connect to the server: Forbidden
stderr_lines: <omitted>
stdout: 'Client Version: version.Info{Major:"1", Minor:"11", GitVersion:"v1.11.3", GitCommit:"a4529464e4629c21224b3d52edfe0ea91b072862", GitTreeState:"clean", BuildDate:"2018-09-09T18:02:47Z", GoVersion:"go1.10.3", Compiler:"gc", Platform:"linux/amd64"}'
stdout_lines: <omitted>
However, when sending a manual request to those API url like this
- name: Test master connection
shell: curl -k https://k8smaster01:6443/version?timeout=32s
It works:
stderr_lines: <omitted>
stdout: |-
{
"major": "1",
"minor": "11",
"gitVersion": "v1.11.3",
"gitCommit": "a4529464e4629c21224b3d52edfe0ea91b072862",
"gitTreeState": "clean",
"buildDate": "2018-09-09T17:53:03Z",
"goVersion": "go1.10.3",
"compiler": "gc",
"platform": "linux/amd64"
}
kubectl
doesn't work when executed with Ansible?I'm behind a proxy server, but k8smaster01
is set in no_proxy
. Ansible got it, I printed $no_proxy
in the task for testing purpose.
For curl
I used -k
since its a self signed cert from k8s. This sould harm kubectl
(which itself works when not running from Ansible). It also doesn't work when calling kubectl --insecure-skip-tls-verify=true get node
with Ansible.
I tried to unset the env variables from the proxy (since the proxy is required just for internet access) by setting empty environment variables:
- name: Kubectl test
become: false
shell: kubectl get no -v=10
environment:
http_proxy:
https_proxy:
no_proxy:
HTTP_PROXY:
HTTPS_PROXY:
NO_PROXY:
This was a bad idea, since curl
(which seems to be used inside kubectl
) parse this to None
and fail. Strangely, kubectl
failed with an dns error:
skipped caching discovery info due to Get https://k8smaster01:6443/api?timeout=32s: proxyconnect tcp: dial tcp: lookup None on 127.0.0.53:53: server misbehaving
Found out that the main problem was that I set NO_PROXY=$no_proxy
in /etc/environment
, where no_proxy
contains the hostname k8smaster01
. Since /etc/environment
doesn't resolve bash variables, the uppercase NO_PROXY
just contains $no_proxy
as string. So it was enough to replace NO_PROXY=$no_proxy
by the corresponding value (e.h. NO_PROXY=k8smaster01
).
It wasn't an issue before, because most applications seems to follow the Linux specification of using lowercase environment variables for proxy usage.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With