diff --git a/ansible/post-deploy.yml b/ansible/post-deploy.yml
index ec83bd11f4..61d91d765a 100644
--- a/ansible/post-deploy.yml
+++ b/ansible/post-deploy.yml
@@ -32,6 +32,15 @@
         group: "{{ ansible_facts.user_gid }}"
         mode: 0600
 
+    - name: Template out public-openrc.sh
+      become: true
+      template:
+        src: "roles/common/templates/public-openrc.sh.j2"
+        dest: "{{ node_config }}/public-openrc.sh"
+        owner: "{{ ansible_facts.user_uid }}"
+        group: "{{ ansible_facts.user_gid }}"
+        mode: 0600
+
     - import_role:
         name: octavia
         tasks_from: openrc.yml
diff --git a/ansible/roles/common/templates/public-openrc.sh.j2 b/ansible/roles/common/templates/public-openrc.sh.j2
new file mode 100644
index 0000000000..b268a8b976
--- /dev/null
+++ b/ansible/roles/common/templates/public-openrc.sh.j2
@@ -0,0 +1,17 @@
+# {{ ansible_managed }}
+
+# Clear any old environment that may conflict.
+for key in $( set | awk '{FS="="}  /^OS_/ {print $1}' ); do unset $key ; done
+export OS_PROJECT_DOMAIN_NAME=Default
+export OS_USER_DOMAIN_NAME=Default
+export OS_PROJECT_NAME={{ keystone_admin_project }}
+export OS_TENANT_NAME={{ keystone_admin_project }}
+export OS_USERNAME={{ keystone_admin_user }}
+export OS_PASSWORD={{ keystone_admin_password }}
+export OS_AUTH_URL={{ keystone_public_url }}
+export OS_IDENTITY_API_VERSION=3
+export OS_REGION_NAME={{ openstack_region_name }}
+export OS_AUTH_PLUGIN=password
+{% if kolla_admin_openrc_cacert is not none and kolla_admin_openrc_cacert | length > 0 %}
+export OS_CACERT={{ kolla_admin_openrc_cacert }}
+{% endif %}