Docker Swarm Series: #7th Advanced Managing config and secret objects
Tags: docker, swarm
Published: 2023-07-22 05:05:58

--- series: Swarm ---

# Inception

Hello everyone, This article is part of The Swarm series, The knowledge in this series is built in sequence, Check out The Swarm series section above.

In the [last article](https://mohamed-eleraky.hashnode.dev/docker-swarm-series-6th-managing-config-and-secret-objects), we covered how to use and manage **config objects** and how to **store secrets** securely, using Docker-compose YAML file, Docker CLI, And [Play-with-docker](https://labs.play-with-docker.com/) lab, And we going to discuss more advanced topics today.

---

# Overview

In This article, We will complete The Swarm tutorials by explaining Config and Secret advanced stuff, will discuss how to use and manage **config objects** and how to **store secrets** securely and use them in your deployment. However in an advanced and efficient way. in this lab Also will use the [Play-with-docker](https://labs.play-with-docker.com/) lab.

---

# Advanced Managing config objects

In The [Last Deployment](https://mohamed-eleraky.hashnode.dev/docker-swarm-series-6th-managing-config-and-secret-objects#heading-deployment-example), we created a config file that contains The **MongoDB username** and refer to The **Mongo password** file. That is actually a Nice way to manage config and store secrets without defining them as clear text in your docker-compose YAML file. However **what if we want to update our config file with new content?**

In Fact, Swarm doesn't have a way to manage config versioning. you should do it on your own, That means You can't update the same config file with new content, and then the service will update the config automatically.  
**However**, you can create another config file and update the service by defining the new config file. Therefore you will Manage the config file object versioning.

---

# Update The Config object example

This example will Continue from the [last article's](https://mohamed-eleraky.hashnode.dev/docker-swarm-series-6th-managing-config-and-secret-objects#heading-deployment-example) stand-up point, Kindly submit the example there and come back here to figure out how to update and version the config object file.

Now we have our environment ready, And we have a service running using config and secret stored in Swarm Database. Let's update the config and secret as below steps:

* The config object file cannot be deleted while the service is using it. you should create another config and update the service to use the new config object, Then you can delete it. However prefer to not delete any, instead you should version your object files So you have your config files versioned so you can roll back to the old one, and then update the service YAML file to use the new version of the object file. and this is exactly what we going to do below steps:
    
    * Create a new config file called `mongo_config-v2.txt` with the updated content below:
        
<br>
```bash
MONGO_INITDB_ROOT_USERNAME=root
MONGO_INITDB_ROOT_PASSWORD_FILE=/run/secrets/mongo_password.v2
```
        

Create the new config by running the following:

<br>
```bash
docker config create mongo_config.v2 mongo_config-v2.txt
```

* now you should have two config objects
   
<br> 
```bash
docker config ls
```
    

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1689965324427/cc900706-60e8-49d1-a6f8-e4bf90fae1e1.png)
    

---

# Update The Secret object example

The secret is almost pretty much the same as the config, you cannot recreate it with the same name, And cannot be deleted while the service is using it.

Instead, Also you would need to create another secret with the new content and version and update the service to use the new secret created. let's do this:

* Create a new secret file object called `mongo_password-v2.txt` have the content below
    
<br>
```bash
supersecretp@$$w0rd
```
    

Create the secret by the following:

<br>
```bash
docker secret create mongo_password.v2 mongo_password-v2.txt
```

* now you should have two Secret objects
    

<br>
```bash
docker secret ls
```

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1689966551884/47c6e494-1209-4c8b-bf1c-62bd55eff5f3.png)

Some of The listed secrets are created by **long-syntax** and others by **short-syntax** ways, Will figure out that in a second.

---

# Update The Service

Now let's update the service YAML file to use the new config and secret have just created, will not delete or update anything in the same file instead will copy the YAML file with a new name `docker-compose-v2.yml` so after a bunch of updates, we will have the YAML files listed and versioned. This a good way for rolling back, history, and tracking updates.

* Copy the YAML file with the new name `docker-compose-v2.yml`
    
<br>
```bash
cp docker-compose.yml docker-compose-v2.yml
```
    

Open the version two compose file using `vim` and submit the updates as the following:

* Mongo service Config
  
<br>  
```bash
configs:
  - source: mongo_config.v2
    target: /docker-entrypoint-initdb.d/mongo_config-v2.txt
```
    
* Mongo service Secrets
    
<br>
```bash
secrets:
  - mongo_password.v2
```
    
* Mongo-Express service Admin password environment variable
  
<br>  
```bash
ME_CONFIG_MONGODB_ADMINPASSWORD_FILE: /run/secrets/mongo_password.v2
```
    
* Mongo-Express service Secrets
  
<br>  
```bash
secrets:
  - mongo_password.v2
  - mongo_admin_username
  - me_username
  - me_password
```
    
* Main Secrets and Config definition
    
<br>
```bash
secrets:
  mongo_password.v2:
    external: true
mongo_admin_username:
  external: true
me_username:
  external: true
me_password:
  external: true
    
configs:
  mongo_config.v2:
    external: true
```
    
* Update the service by the following:
   
<br> 
```bash
docker stack deploy -c docker-compose-v2.yml myapp
```
    

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1689968329179/7f857226-9306-4bf4-90fb-b53f1c994d01.png)
    
* ensure the service running as expected by running the following
    
<br>
```bash
docker stack services myapp
docker stack ps myapp
```
    

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1689968543438/1d74a05a-f1ca-4014-a5bc-1eff1bfad2a9.png)
    
Yeah, The service's desired state are matched the actual state, Also notice here the swarm has shut down the old services and created new services with our updates.
    
* You can delete the config by running the following, Consider that you cannot delete the config and secret while the service is using it, will delete the config object meanwhile And will let the config object files itself for versioning list reasons.
   
<br> 
```bash
docker config rm mongo_config
"""
notice that you still have the config file after deleted
the config object from swarm storage.
"""
```
    
Also, you can do the same with secrets.
    

---

# Swarm secret long and short syntax

*"The main difference between the* ***long*** *and* ***short syntax*** *for creating Swarm secrets is the way in which the secret's value is specified."* [*\-POE-*](http://WWW.POE.COM)

With the **long syntax**, The secret value is stored in a file and you run `docker secret create` with mentioning the file path.

This approach can be useful when creating secrets that have Certificate values, or any complex values.

"The long syntax allows mounting a secret in any path and even set the access permissions." [*\-Metin-*](https://forums.docker.com/t/re-docker-swarm-series-6th-managing-config-and-secret-objects/136865)

On the other hand, the **short syntax** provides a more convenient way for defining the secrets by simply passing the secret value with a `docker secret create` command with the - option at the end, like the one below:

<br>
```bash
echo "mongo_pass" | docker secret create me_password -
```

The short syntax doesn't require to have a secret file

---


# How the Cluster manages stacks

A stack is just a group of resources that the cluster orchestration tool manages them. at the moment you have an idea of how to build and manage your stack. However, Elton Stoneman the author of [Learn Docker in a Month of Lunches](https://www.amazon.com/Learn-Docker-Month-Lunches-Stoneman/dp/1617297054/ref=sr_1_1?keywords=learn+docker+in+a+month+of+lunches&link_code=qs&qid=1690103529&sourceid=Mozilla-search&sr=8-1) has sort-down some points that I think it'll make it more clear, Let me summarize these points:

* Volumes can be created and removed by the Swarm. Stacks will create a default volume if the service image specifies one, and that volume will be removed when the stack is removed. If you specify **a named volume** for the stack, it will be created when you deploy, but it **won’t be removed** when you delete the stack.
    
* Secrets and configs are created when an external file gets uploaded to the cluster. They’re stored in the cluster database and delivered to containers where the service definition requires them. They are effectively write-once read-many objects and can’t be updated.
    
* Networks can be managed independently of applications, with admins explicitly creating networks for applications to use, or they can be managed by the Swarm, which will create and remove them when necessary. Every stack will be deployed with a **network to attach services to**, even if **one is not specified in the Compose file.**
    
* Services are created or removed when stacks are deployed, and while they’re running, the Swarm monitors them constantly to ensure the desired service level is being met. Replicas that fail health checks get replaced, as do replicas that get lost when nodes go offline.
    

---

# References

* [POE AI](http://www.poe.com)
    
* [Metin guidance](https://forums.docker.com/t/re-docker-swarm-series-6th-managing-config-and-secret-objects/136865)
    

---

That's it, Very straightforward, very fast 🚀. Hope this article inspired you and will appreciate your feedback. Thank you.