Kubernetes pod keeps crashing with no error in logs - docker

I am trying to deploy apache docker image using Terraform on Kubernetes Cluster
I tried the following command and able to hit the URL localhost:8082 from browser successfully
docker run -it --rm -d -p 8082:80 webservice
I then created a kubernetes_deployment using Terraform but pod keeps crashing and there's nothing in logs
resource "kubernetes_deployment" "api" {
metadata {
name = "ex-api"
labels = {
app = "EX"
component = "api"
}
}
spec {
replicas = 1
selector {
match_labels = {
app = "EX"
}
}
template {
metadata {
name = "ex-api"
labels = {
app = "EX"
component = "api"
}
}
spec {
container {
image = "${var.web_service_image}:${var.web_service_image_tag}"
image_pull_policy = "IfNotPresent"
name = "api-image"
# All the other configuration options should be here too.
port {
container_port = 80
name = "web"
}
} # end of container block
} # end of spec block
} # end of template block
} # end of spec out-block
}
Pod's output
kubectl get pod
NAME READY STATUS RESTARTS AGE
ex-api-5458586bd8-ex6sp 0/1 CrashLoopBackOff 19 72m
I assume I should either add some command or daemonize (eg -itd when using docker) it so that it keeps running. I may be wrong here
Kindly let me know what should I do to overcome this

No logs or no events shown when you run the describe command generally suggests that that there is an issue with invoking your entrypoint in your Dockerfile. So, you may have to overwrite the command in your deployment.yaml
In your case - your deployment may need to use the command that you have or tried to use in your Dockerfile. Apparently, kubernetes pod is unable to use what you have defined in the Dockerfile.

Related

Build and deploy a golang Docker image using Terraform?

I am trying to setup auto deployment in Terraform to Docker of my golang server.
I have it working if I am deploying manually, but can't get the terraform config working.
Here is what I have.
resource "docker_image" "terraform_golang" {
name = "terraform_golang"
build {
path = "./../"
build_arg = {
tag : "golang-server"
}
label = {
author : "Bill"
}
}
}
resource "docker_container" "terraform_backend" {
image = docker_image.terraform_golang.latest
name = "Terraform_Backend"
env = [ "database=172.19.0.3:3306" ]
ports {
internal = 8080
external = 8080
}
network_mode = "bridge"
networks_advanced {
name = "golang-server"
}
}
This is the error I get:
│ Error: failed to solve with frontend dockerfile.v0: failed to read dockerfile: Error processing tar file(exit status 1): unexpected EOF
│
│
│
│ with module.terraform.docker_image.terraform_golang,
│ on terraform\backend.tf line 2, in resource "docker_image" "terraform_golang":
│ 2: resource "docker_image" "terraform_golang" {
Here is my manual deployment cmd, which is working:
docker build . -t golang-server
docker run --network=golang-server --name=golang-server --env database=172.19.0.3:3306 --expose=8080 -p=8080:8080/tcp golang-server
Here is my dockerfile:
FROM golang:1.18
WORKDIR $GOPATH/src
COPY . .
RUN go get -d -v ./...
RUN go install -v ./...
EXPOSE 8080
CMD ["golang-server"]
My folder structure is setup such that my terraform files are in a subfolder, in a module, I hope this doesn't mess with anything:
"path" only changes the context path, not the path where to find the docker file. Honestly feels like a bug since the docker command defaults to PATH/Dockerfile as a docker file path, but that's how the terraform plugin currently works.
What you need is to add a dockerfile parameter to point to the actual Dockerfile;
resource "docker_image" "terraform_golang" {
name = "terraform_golang"
build {
dockerfile = "../Dockerfile"
path = ".."
build_arg = {
tag : "golang-server"
}
label = {
author : "Bill"
}
}
}

Nomad Connect Two docker Containers

I am having trouble establishing communication between two docker containers via nomad. Containers are in the same task group but still unable to reach each other. Even when using NOMAD_ADDR_ environment variable. Can anyone help in this regard? I tried both host and bridge network mode.
My nomad config is given below. Images are pulled and the Redis container and application container starts, but then app container crashes with Redis Connection Refused error
The second issue is, as you might have guessed is of prettifying the code with proper indentation etc. Just like Javascript or HTML or YAML is automatically formatted in VS code. I am unable to find a code prettifier for the HCL language.
job "app-deployment" {
datacenters = ["dc1"]
group "app" {
network {
mode = "bridge"
port "web-ui" { to = 5000 }
port "redis" { to = 6379 }
}
service {
name = "web-ui"
port = "web-ui"
// check {
// type = "http"
// path = "/health"
// interval = "2s"
// timeout = "2s"
// }
}
task "myapp" {
driver = "docker"
config {
image_pull_timeout = "10m"
image = "https://docker.com"
ports = ["web-ui"]
}
env {
REDIS_URL="redis://${NOMAD_ADDR_redis}"
// REDIS_URL="redis://$NOMAD_IP_redis:$NOMAD_PORT_redis"
NODE_ENV="production"
}
}
task "redis" {
driver = "docker"
config {
image = "redis"
ports = ["redis"]
}
}
}
}
So I was able to resolve it, basically, when you start nomad agent in dev mode, by default it binds to the loopback interface and that is why you get 127.0.0.1 as IP and node port in NOMAD env variables. 127.0.0.1 resolves to localhost inside container and hence it is unable to reach the Redis server.
To fix the issue, simply run
ip a
Identify the primary network interface for me it was my wifi interface. Then start the nomad like below.
nomad agent -dev -network-interface="en0"
# where en0 is the primary network interface
That way u will still be able to access the nomad UI on localhost:4646 but your containers will get the HOST IP from your network rather then 127.0.0.1

How to keep nomad task from exiting?

In docker we have -t flag to keep containers from exiting. How can achieve the same thing in nomad?
I want to debug if I can ping one service from another, so I just want a container with curl. However, if I try to deploy the ubuntu image specifying it like below it exits and keeps restarting. What can I do so it just keeps running?
task "testubuntu" {
driver = "docker"
config {
image = "ubuntu:latest"
}
resources {
cpu = 500
memory = 256
network {
mbits = 10
}
}
}
Another solution would be to set a "dummy" entry point tail -f /dev/null
task "testubuntu" {
driver = "docker"
config {
image = "ubuntu:latest"
entrypoint = [
"tail", "-f", "/dev/null",
]
}
resources {
cpu = 500
memory = 256
}
}
It is particularly useful, when you have a task that errors at the container startup but there is not much useful information in the logs. This "dummy" entry point will keep container alive allowing you to get inside container and execute a real startup command with attached debugger for example.
Apart from tail -f /dev/null, you can also simply use yes as an entry point. However, it will pollute stdout and affect your logging solution if it is setup.
Add container = true in the config stanza
task "testubuntu" {
driver = "docker"
config {
image = "ubuntu:latest"
container = true
}
resources {
cpu = 500
memory = 256
network {
mbits = 10
}
}
}

Unable to get Consul Connect to work with Nomad

I'm trying to get Consul Connect side car envoy to work but the health checks for sidecar keeps failing.
I'm using following versions of Consul and Nomad
Consul : 1.7.3
Nomad : 0.11.1
CNI Plugins : 0.8.6
My setup looks like follows.
1 Consul Server running consul in docker container.
docker run -d --net=host --name=server -v /var/consul/:/consul/config consul:1.7 agent -server -ui -node=server-1 -bind=$internal_ip -ui -bootstrap-expect=1 -client=0.0.0.0
internal_ip is the internal IP address of my GCP VM.
1 Nomad Server with Consul Agent in client mode
nohup nomad agent -config=/etc/nomad.d/server.hcl &
docker run -d --name=consul-client --net=host -v ${volume_path}:/consul/config/ consul:1.7 agent -node=$node_name -bind=$internal_ip -join=${server_ip} -client=0.0.0.0
interal_ip is the internal IP address of GCP VM and server_ip is the internal IP address of Server VM.
2 Nomad Client with Consul Agent in client mode
nohup nomad agent -config=/etc/nomad.d/client.hcl &
docker run -d --name=consul-client --net=host -v ${volume_path}:/consul/config/ consul:1.7 agent -node=$node_name -bind=$internal_ip -join=${server_ip} -client=0.0.0.0
On Nomad clients, I also have consul binary available in path.
Now I'm trying to deploy the sample Nomad and Consul Connect job from here
job "countdash" {
datacenters = ["dc1"]
group "api" {
network {
mode = "bridge"
}
service {
name = "count-api"
port = "9001"
connect {
sidecar_service {}
}
}
task "web" {
driver = "docker"
config {
image = "hashicorpnomad/counter-api:v1"
}
}
}
group "dashboard" {
network {
mode = "bridge"
port "http" {
static = 9002
to = 9002
}
}
service {
name = "count-dashboard"
port = "9002"
connect {
sidecar_service {
proxy {
upstreams {
destination_name = "count-api"
local_bind_port = 8080
}
}
}
}
}
task "dashboard" {
driver = "docker"
env {
COUNTING_SERVICE_URL = "http://${NOMAD_UPSTREAM_ADDR_count_api}"
}
config {
image = "hashicorpnomad/counter-dashboard:v1"
}
}
}
}
The docker container for service and sidecar gets started and gets registered in Consul, but I'm unable to access any of the service.
I SSH onto the Nomad Client node and can see the container running.
Odd thing I noticed is that I cannot see port forwarded to the host
I cannot access it via curl from host.
I tried doing curl $internal_ip:9002 but it didn't work.
I checked if Nomad created any new bridge network since that's what I used as mode in the network stanza but there are no new networks.
Is there anything that I'm missing in my setup ?
Have you tried setting COUNTING_SERVICE_URL = "http://${NOMAD_UPSTREAM_ADDR_count_api}" to COUNTING_SERVICE_URL = "http://localhost:8080", since that is the local bind port that the envoy proxy will be listening on to forward traffic to the count-api.
An example of a working connect setup can be found at https://github.com/hashicorp/video-content/tree/master/nomad-connect-integration/nomad_jobs

Docker Container from Terraform will not start

I launched a Docker container with Terraform, simple code.
> cat main.tf
provider "docker"{
}
resource "docker_image" "ubuntu"{
name = "ubuntu:latest"
}
resource "docker_container" "webserver" {
image = "${docker_image.ubuntu.latest}"
name = "dev-web-p01"
#start = true
must_run = true
publish_all_ports = true
}
I can see the container spun up but not running.
> docker container -ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
63c770e28ad2 47b19964fb50 "/bin/bash" 10 minutes ago Exited (0) 3 minutes ago dev-web-p01
My attempt to start and connect to the container fails and I am not sure why?
> docker container start 63c
63c
> docker container exec -it 63c /bin/bash
Error response from daemon: Container 63c770e28ad256e77442cb2fb8b9b8bbc14b8f37b99296bc63f2d249209e0399 is not running
I have tried this for a couple of times but it doesn't work. Sorry bit of a noob here.
Exited (0) means program successfully completed. With docker you need to execute some long running commands to ensure it doesn't finish immediately.
Best way to test some changes with docker, is waiting for nothing. Try this:
resource "docker_image" "ubuntu" {
name = "ubuntu:latest"
}
resource "docker_container" "webserver" {
image = "${docker_image.ubuntu.latest}"
name = "terraform-docker-test"
must_run = true
publish_all_ports = true
command = [
"tail",
"-f",
"/dev/null"
]
}

Resources