diff --git a/README.md b/README.md
index 6559d0307f5319e2af02cef58d5c0ab7c6b45222..f20c14f259d170a0a321360b318e3b59774d07be 100644
--- a/README.md
+++ b/README.md
@@ -129,7 +129,7 @@ Supported Components
 -   Application
     -   [cephfs-provisioner](https://github.com/kubernetes-incubator/external-storage) v2.1.0-k8s1.11
     -   [cert-manager](https://github.com/jetstack/cert-manager) v0.5.2
-    -   [coredns](https://github.com/coredns/coredns) v1.2.6
+    -   [coredns](https://github.com/coredns/coredns) v1.4.0
     -   [ingress-nginx](https://github.com/kubernetes/ingress-nginx) v0.21.0
 
 Note: The list of validated [docker versions](https://github.com/kubernetes/kubernetes/blob/master/CHANGELOG-1.13.md) was updated to 1.11.1, 1.12.1, 1.13.1, 17.03, 17.06, 17.09, 18.06. kubeadm now properly recognizes Docker 18.09.0 and newer, but still treats 18.06 as the default supported version. The kubelet might break on docker's non-standard version numbering (it no longer uses semantic versioning). To ensure auto-updates don't break your cluster look into e.g. yum versionlock plugin or apt pin).
@@ -155,9 +155,9 @@ Requirements
     or command parameters `--become or -b` should be specified.
 
 Hardware:        
-These limits are safe guarded by Kubespray. Actual requirements for your workload can differ. For a sizing guide go to the [Building Large Clusters](https://kubernetes.io/docs/setup/cluster-large/#size-of-master-and-master-components) guide. 
+These limits are safe guarded by Kubespray. Actual requirements for your workload can differ. For a sizing guide go to the [Building Large Clusters](https://kubernetes.io/docs/setup/cluster-large/#size-of-master-and-master-components) guide.
 
--   Master 
+-   Master
     - Memory: 1500 MB
 -   Node
     - Memory: 1024 MB
diff --git a/roles/download/defaults/main.yml b/roles/download/defaults/main.yml
index 00cc715ad7e6412553408434ca1875cc6b51e0f2..2689e889c949e23d2f793c7149dcc1470d70d0ac 100644
--- a/roles/download/defaults/main.yml
+++ b/roles/download/defaults/main.yml
@@ -202,7 +202,7 @@ multus_image_tag: "{{ multus_version }}"
 nginx_image_repo: nginx
 nginx_image_tag: 1.13
 
-coredns_version: "1.2.6"
+coredns_version: "1.4.0"
 coredns_image_repo: "coredns/coredns"
 coredns_image_tag: "{{ coredns_version }}"
 
diff --git a/roles/kubernetes-apps/ansible/templates/coredns-config.yml.j2 b/roles/kubernetes-apps/ansible/templates/coredns-config.yml.j2
index faa26a34143b47bf6486f17268ef77988755b9bd..51131df68de308774326bc7a4d2b49d0e42cdafe 100644
--- a/roles/kubernetes-apps/ansible/templates/coredns-config.yml.j2
+++ b/roles/kubernetes-apps/ansible/templates/coredns-config.yml.j2
@@ -22,9 +22,9 @@ data:
         }
         prometheus :9153
 {% if resolvconf_mode == 'host_resolvconf' and upstream_dns_servers is defined and upstream_dns_servers|length > 0 %}
-        proxy . {{ upstream_dns_servers.join(' ') }}
+        forward . {{ upstream_dns_servers.join(' ') }}
 {% else %}
-        proxy . /etc/resolv.conf
+        forward . /etc/resolv.conf
 {% endif %}
         cache 30
         loop
diff --git a/roles/kubernetes-apps/ansible/templates/coredns-deployment.yml.j2 b/roles/kubernetes-apps/ansible/templates/coredns-deployment.yml.j2
index 5a56a49b6073d267b28ba5b274c2f46a84bcc0a7..5a1edb8ae2ddb33fa30c12e5758e169514513863 100644
--- a/roles/kubernetes-apps/ansible/templates/coredns-deployment.yml.j2
+++ b/roles/kubernetes-apps/ansible/templates/coredns-deployment.yml.j2
@@ -95,6 +95,15 @@ spec:
           timeoutSeconds: 5
           successThreshold: 1
           failureThreshold: 5
+        readinessProbe:
+          httpGet:
+            path: /health
+            port: 8080
+            scheme: HTTP
+          initialDelaySeconds: 60
+          timeoutSeconds: 5
+          successThreshold: 1
+          failureThreshold: 5
       dnsPolicy: Default
       volumes:
         - name: config-volume