0:35
Thank you for joining me on this session about Config Maps and Secrets
0:41
Today, I'm not going to show you my webcam because it died
0:45
My GoPro camera died yesterday, so I won't be able to show my camera
0:51
which is cool, I guess, so you don't have to see my face
0:55
anyways today we're going to talk about config maps and secrets however let's do a quick recap
1:05
about the last session you might remember that we talked about health checks which is a way to
1:12
verify if our pods are behaving correctly right health checks are used to determine if the state
1:21
of a container or pod is behaving correctly, right? So there are three types of health checks
1:31
liveness, readiness, and startup. I talked about those differences. Liveness is for specifying or detecting
1:40
if the pod or the container is ready to receive requests. readiness is, I'm sorry
1:52
lightness is to determine if it's alive, readiness is to determine if it's ready to receive traffic
1:59
and startup is for executing something that you need to run at the startup of your containers
2:09
So there are three probing mechanisms that we can use. The first one is a command execution
2:16
Maybe you want to execute a command or application to determine if your container is behaving correctly
2:24
Or maybe you can expose a HTTP endpoint so you can receive requests
2:32
So Kubernetes can know if this pod is behaving correctly. And there's also a TCP socket mechanism
2:41
And we showed you this couple of examples with the HTTP GET and the command execution as well
2:51
So that's nice. And today I'm going to talk about config maps and secrets
2:57
which is a way to configure our applications. So you don't have your configurations
3:06
and secrets hard coded in your code, right? So that's a way of decoupling your configuration
3:15
and managing that configuration in a decoupled way. Before we do this
3:22
let me explain environment variables in Kubernetes. So you might remember when we create a pod
3:31
we have the manifest file that has the API version, kind, metadata, and spec
3:37
And inside the spec field, we have the containers element. And that's the place where we define the container configuration, right
3:49
Such as the image name and resource limits and some other things
3:54
And actually, this is the place where we configure the environment variables that your application or service might want to use
4:02
So for instance, in this example that I have here on the screen, you can see that I'm specifying
4:10
a couple of environment variables named environment underscore variable underscore name and the other one with two, right
4:21
So as you can see, env, env, this is the element that we use for specifying the environment variables
4:30
for our containers in a pod. Very easy stuff. However, what happens if you don't want to set your values
4:40
directly in the manifest file? Because remember, most of the time those manifest files
4:46
will be stored in the source control repository, right? So it doesn't make sense to store a hard coded value
4:58
For instance, let's say that this is a connection string or this is an API key or something for security purposes
5:06
it doesn't make sense to store that value in the manifest file
5:10
So you need something like environment variables to dynamically inject those values into your containers
5:19
Okay. Okay, that said, let's talk about config maps, which is the first topic for today
5:31
ConfigMaps are shared configuration stores that we can read from the Jamil files
5:40
So ConfigMaps, you can think about those like a special place where you can put configuration values
5:48
Those are key value pairs that you can specify and your container can read those values dynamically
5:58
and in a decoupled fashion, right? This is for non-confidential decoupled configuration items
6:07
And one of the traits of config maps is that their data is not encrypted, okay
6:14
So you should be careful about that. Config maps are not meant to store super confidential
6:22
and super secure and sensitive information, okay? because the data is not encrypted, that's why
6:30
And config maps, they have this limit, data can be larger than one maybe byte
6:38
which is almost one megabyte. Actually those data types are different, however
6:48
data can be larger than one maybe byte, okay? So config maps are useful
6:55
when we want to set environment variables in our containers precisely, okay
7:02
So you can, for example, use the name of the config map that you want to use
7:08
and Kubernetes is going to make sure that all the key values in a specific file
7:16
or maybe in a directory, those values that you want to inject
7:22
will be available in your container okay And one of the things that you should be careful about is that the config maps objects that you want to use for your container and pods
7:35
must be in the same namespace. So you need to create your config map objects
7:42
in the same name face as your pods where you're going to use those configurations
7:52
So if you want to do this, in other words if you if you want to use a config map for specifying and setting your environment
8:01
variables instead of a hard-coded code hard-coded value you can use the value from field
8:10
as you can see here on the screen okay so I'm going to talk about that in a minute
8:17
there are different sources that we can use for config maps the first one is literal literal
8:22
values. In other words, you can specify by using the kubectl command the environment variable and
8:31
literal values that you want to use for that config map. The other ones are a file with
8:38
environment variables. This is an env file that has key value pairs and also you can use a file
8:48
with arbitrary text of course those are quite similar just a text file with key value pairs
8:56
right or you can use a directory that has one or many files that you want to dynamically read
9:04
to inject those values into your containers so why do we want to do this well it depends on your
9:16
however most of the time you're going to use I say a file an environment variables file
9:25
that you might have to implement yourself and or maybe you want to use from the from literal
9:36
option okay so the first one the first command that I have here on the screen is creating a
9:44
config map object named logger that is using the from literal flag and it's using the equal sign
9:55
and then specifying the key and value for this literal okay so you know what let me open up the
10:05
terminal because I'm not sure if I run minikube beforehand let's do this minikube delete
10:13
and I'm going to stop the previous cluster that I had before
10:23
And after I do this, I'm going to deploy a new cluster, say Minikube
10:31
start in the driver that I want to use this Hyper-V. Okay, I'm going to deploy this cluster with one node only
10:41
Okay, so the second option is, as you can see here, is reading these myconfig.nv file
10:50
that has environment variables. The other one from file is reading that my file.txt file
10:58
And finally, the other one, the last one is just reading a directory named my directory
11:06
and it's going to read all the files. It might have one file or maybe it has 10 files
11:13
It doesn't matter. It's gonna read all the files in that particular directory
11:19
And of course that's for imperative creation of the config map objects
11:24
And you can also use a manifest file. Here's an example of a manifest file written in Jammel
11:33
And as you can see, it's using the API version kind, The kind is config map metadata
11:40
This is the place where we use the name field for specifying the name
11:46
the technical name that we're going to use for referring to this config map object
11:52
which in this case is my app dash config map. And finally, instead of spec, we have data
12:00
this field when I can specify all the different key value pairs
12:05
such as environment equals development, file name equals file.txt, name equals Kubernetes
12:14
show equals Kubernetes fundamentals and whatnot. And also you can use get for obtaining and listing
12:25
all the config maps objects that you have on your cluster. So the first command that I have here on the screen
12:32
is returning all the config maps objects And the last one is getting a specific config map object
12:42
which is logger and it's returning its values and the entire object as jammel, okay
12:51
So let's see if the cluster is already deployed. Yes, kubectl say get nodes
13:01
This is behaving correctly. I just need one node. I don't need anything else
13:05
for today's session. So let me go here to session eight, because I want to create a couple of files
13:16
for creating the config map. Say that I want to create a config map
13:23
by using the imperative way. So I can use kubectl create config map and the name, right
13:31
Demo. and I can use from literal, or I can use from file in those things
13:39
So let's say I want to use from literal and I want to specify, I don't know
13:45
name equals C sharp corner. Okay. So as you can see, I created this config map object
13:55
and I can list all the different config maps by using kubectl get config map or config maps or cm
14:05
Remember that we have those aliases when using kubectl. So as you can see, I have demo
14:13
which is the config map object that I just created. And Minikube, when it deployed the cluster
14:21
it created this kuberoot-ca-crt config map for its own purposes. So let's say that I want to get the specific config map
14:35
So get cm forward slash demo. And I can output this as YAML
14:44
So you can see that this is actually the manifest for this particular object
14:50
That why I showing you the API version metadata kind and data of course the position of those fields is different However it doesn matter in this case okay
15:05
We can see that in data, I have name, which is this key that I created, right
15:13
And the value is C sharp corner, okay? So let's go back here
15:21
Let's see what we can do. So let's create a new environment variable file named
15:33
myconfig. Actually, in order to expedite this process, I already created one
15:40
So you need to see me typing all the time. So I created this mysecrets.emb, right
15:49
Let's clear up the screen. So name series session eight, right? Only in C sharp corner live
16:05
Okay. So I have those four key value pairs and I want to read this entire file
16:12
when creating the config map. Okay. So let's create another config map
16:19
create config map. let's say demo with file or just file demo dash file
16:28
And I'm going to use this other command that I showed you
16:33
which is from EMB file. So EMB file and the name of the file is my secret
16:44
Is that it? I can remember. Maybe it's mysecret.emb. No, mysecrets
16:54
Yes, mysecrets. It's right there, mysecrets.emb. So this config map object was created
17:02
And of course, if I execute again, get all the different config map objects
17:08
I can get the demo and also the demo file config map
17:13
that I created, right? and it has four key value pairs. And I can do this, get config maps
17:23
demo file and output jammel. So I can see that name only in series and session
17:32
were successfully uploaded to the config map object. Okay. So very easy stuff for creating those value
17:42
and key value pairs that I need in my applications, right? So let's say that you have a pod
17:52
where you want to use those config map key value pairs. So what would you do
18:01
So in this case, as you can see in this fragment of this pod manifest file
18:08
I'm using embfrom, right? It's using embfrom instead of emb, and it's using this element named configmapRef
18:23
for referencing the entire configmap object by name. So as you can see, we can do this embfrom
18:32
using the configmapRef and then specifying the name of the configmap object that you want to use
18:38
Okay. So actually let's do this. Okay. Let's do this. Let's go back to the terminal
18:50
and let's create a pod. Okay. Actually to expedite this process
18:59
I think I created a pod. Yes. So I created this my pod.jml file
19:08
and the name it doesn't matter. Actually the container image name, it doesn't matter as well
19:15
You can see that I'm using EMB from, and I'm using config map ref
19:21
And finally I'm using demo, let's use demo-file. So that's the config map that has four
19:32
different key value pairs, right? So if I execute kubectl apply and I pass this my pod.jml file as a parameter
19:45
this is gonna inject all those different key value pairs as environment variables in this particular container
19:54
Okay, so let's see if this works. So kubectl apply my pod.jml
20:02
So the pod was created. Let's verify if I have the pod created
20:09
It's creating the container in this particular moment. Okay, so let's wait up for a little bit
20:17
So the container is created. Okay, it's running now. And now we can verify
20:26
if we have those environment variables in place. There are many ways that we can use for verifying this
20:34
I can, I don't know, I can create a new web API application
20:38
by using .NET in ASP.NET Core and using the environment class for reading
20:45
all the environment variables and blah, blah, blah, blah, blah. Or I just can execute the env command in the shell
20:54
So let's do that. kubectl, kubectl, okay. Exec, remember that we have this command
21:06
for executing commands in a particular pod. So the pod is my app and the command
21:14
that I want to execute is emb. So as you can see, I have only in C-sharp corner
21:24
type, series, session, and name, right? Those were injected dynamically when I created the pod
21:36
because I'm referencing that particular config map. So that's one way, of course
21:44
I can use other techniques such as making an interactive session here
21:50
And this is the shell of that particular container. As you can see, this is Linux
22:00
And I can, again, I can execute EMB and return all the different environment variables
22:09
that I have here in this container. Cool. So this is working
22:17
This is one way that we can use for running this, right
22:23
Let go back to the presentation and let continue talking about this So the thing about the technique that I used
22:35
is that it's not changing the key names. And what happens if you have this particular
22:46
I don't know, maybe a particular rule for naming things. In other words, what happens if I had
22:54
say, I don't know, only in, right? Only in lowercase instead of uppercase
23:04
And maybe you want all your different environment variables to be in uppercase, right
23:10
Or maybe you want to separate words with an underscore. Or maybe you want to have, say, a prefix or something, right
23:22
So with this technique that I used, I mean, injecting the entire file
23:30
that's not possible with that, okay? So you need to do something else
23:35
such as reading by key. In this way, as you can see, I'm specifying each environment variable, right
23:44
For example, asp.net core underscore environment, file name, only underscore in or whatnot
23:56
The most important thing here is that I'm not using EMB from anymore
24:02
I'm just using EMB, okay? So you use value from instead of value
24:10
when specifying your environment variables and you use the config map key ref, okay
24:16
you reference the key inside the config map instead of the entire config map object
24:26
Make sense? So you're referencing a key instead of the entire object
24:31
In this case, I'm reading the environment fictitious key that I have in this fictitious config map
24:41
Of course, if we use this for our own purposes, I can use this for renaming things, right
24:50
So actually let's do this. Let's copy this and let's go back to Visual Studio Code
24:59
And let's get rid of EMB from, okay? Let's use EMB. Let's try again, right
25:11
So only in... right? And the name of the config map that I want to use
25:20
is demo file. And the key is only in, I'm changing the names
25:27
I'm changing the keys, right? So you have full control. At the end of the day
25:33
this is the technique that you want to use for having full control over the names
25:40
of your environment variables. So just to expedite this process, let's do this
25:48
So I guess that's the only change that I need to specify
25:53
Let's try kubectl apply fmypod.jml. So I have something wrong with this structure
26:06
Try again. Oh, Jammel, name, name, name, EMB name, it's under EMB value from it's under
26:16
Ah, this is the thing about Jammel, right? So, okay, name and value from should be on the same alignment
26:27
EMB should be, okay, let's try again. So I guess this is wrong
26:34
this should be the place. Identical fields, something is going on only in config map
26:49
Name body from, am I making something wrong? Okay, yes
26:59
The thing is that I cannot change other things Other than the containers and the image
27:07
and some other things, it looks like it's not allowing me to change the environment variables
27:15
So let's see if I can delete the pod, my app, right
27:21
And let's try again. Yes, that was the error. And okay, let's go back to the terminal
27:30
because I don't have enough space here. So I have the pod again, get pods, okay
27:39
kubectl exec my app EMB. And as you can see, I renamed that particular key
27:50
because I had full control over the naming of keys, right? And of course I just read one particular environment variable
28:00
However, you can use this technique for specifying the rest of the environment variables
28:07
In this case, I was only using only in, right? Anyways, and remember that you cannot change
28:15
environment variables while your pod is running. I had that error. And I fixed that by just deleting the pod, right
28:30
Okay, cool. So you can verify if all your environment variables are in place by executing EMB
28:41
Of course, this is a technique if you're using Linux, right? And, or you can just use an interactive session
28:52
in your container and execute and explore the environment with other commands, right
29:00
So cool, let's talk about secrets. So secrets are similar to config maps
29:11
Actually the commands and the explanation is almost the same. However, secrets are meant to be used
29:23
for storing sensitive data, such as passwords, connection strings, tokens, API keys and whatnot
29:35
And again, this is for decoupling your configuration and for decoupling your values
29:44
And of course those sensitive data values that you want to use in your applications
29:52
So one thing that you should know about secrets is that values are just encoded in base 64
29:59
or format, those secrets are not encrypted, okay? So secrets are not super secure out of the box, okay
30:15
If you want to make them super secure, maybe you want to use something like Azure Key Vault
30:21
or HashiCorp Vault or something else for encrypting your data at rest, okay
30:30
because those values out of the box are just encoded in base64 format
30:39
So we use secrets very similar to config maps. We can use them for setting environment variables
30:49
just like I did beforehand when I use the config map. However, in this case, you can use the secret key ref
30:57
If you want to say you want to reference as a particular key in your secret object
31:03
you can use secret key ref. So this is a very similar
31:08
to the previous technique that I used. So there are three secrets options
31:16
that you want to use when creating those objects. The first one, and I think that that's the most common one
31:24
is generic. This is for creating secrets that are meant to be used
31:32
with local files, directories, and literal values, very similar to the config map, okay
31:41
So let's say that you want to specify your own literal values
31:45
then you should use generic, or maybe you want to use the same technique that I used
31:52
I say with that environment variable file, right? Like my secrets.env that I used
32:02
then you should use generic. The other two Docker registry and TLS
32:10
are for creating a secret that is going to be used with a Docker registry
32:16
And the latter is for creating a TLS secret. So in this case, I'm going to use generic. Okay
32:25
So if you use generic, then you can use the same sources
32:30
that I explained before with config maps. Again, literal values, a file with environment variables
32:38
or a file with arbitrary text or a directory that has one or many files
32:47
So you can create secrets. Of course, with the imperative way, by using kubectl or you can use a manifest file, right
33:00
In this case, I'm showing you here on the screen, the way of creating a secret by using the kubectl command
33:09
And the first one, the first line that I have here is using the from literal flag
33:15
and it's specifying API key, one, two, three, four, five as the value of that particular key
33:23
Very easy stuff. Just take into account this generic option. This is the place where you use generic or TLS
33:32
or Docker registry, okay? TubeCuddle create secret, the type of secret, and then the name of the secret
33:41
And finally, all the different flags that you want to use. So the second option here is reading the mysecrets.emb file
33:51
by using the from emb file flag. And the last one is reading a file
33:59
that has say a connection string or something, right? That's just an arbitrary text file
34:08
that has this content, right? So if you want to use the JAMA way
34:17
in other words, the declarative way, then you should create a manifest file
34:24
And here on the screen, we have this manifest file for a secret
34:28
take into account that the kind is secret. So we have API version, kind metadata
34:36
and we have other things such as type and data. Type is for specifying the contents here
34:43
in the manifest file by using a base64 string. Take into account that you have to encode it yourself
34:51
This is not going to be encoded by Kubernetes, okay? So you should use something like an online encoder
35:01
or maybe you have a command or tool in your own operating system that does that
35:08
However, you need to do that, okay? You need to encode it yourself
35:12
So let's say base64 encoder. So this is the one that I use
35:19
which is base64 decode.org. And then you can decode your text here
35:28
And actually, I think there's another one for encoding your data, okay? This is just for decoding
35:34
Oh, yeah, the option is right there. encode, right? So this is funny that they have two different domain names
35:46
for encoding and decoding. Anyways, that's that. And you can encode your string values here
35:54
Anyways, you have to encode it yourself. That's the message that I want to give you, okay
36:00
So you can use getSecrets for obtaining all the secrets or if you want to obtain a single secret
36:08
You can use get secret and the name of the secret. And then you can output that particular secret
36:15
in other formats such as YAML, right? And you can use describe as well
36:23
for describing a particular secret. So let's do this. Let's create a secret, okay
36:30
And I'm going to use this option because I want to reuse the mysecrets.emb file
36:39
that I already have. So kubectl create secret, right? And the type is generic mysecret okay That the name and from emb file and the name of the file is mysecrets
36:59
Of course, I'm executing this command in this folder because this is the place where I have this file, right
37:09
So let's execute this. I don't know what happened. Again, oh, what's going on here
37:17
Looks like, I don't know if that was executed. kubectl get secrets
37:27
No, okay, again. Okay, that was created successfully. Again, get secrets. I have my secret with base64 data
37:39
So let's see what's going on here, okay? Let's see if, say kubectl get secrets
37:48
my secret, okay, that's the secret, I'll put jamml. So in this case, I have those values
37:59
I guess this is because I use the file option, okay? And I use the kubectl command
38:06
if you want to use my, I mean, the manifest file way
38:12
in other words, the declarative way, you should encode it yourself. However, if you use the kubectl command
38:22
then those values will be encoded by Kubernetes, okay? Just to be perfectly clear about that
38:33
So, because I mentioned before that you have to encode it yourself
38:37
Yes, that's true for the declarative way. However, I'm using the imperative way, right
38:46
By using kubectl create. Anyways, I have name only in series and session
38:52
And as you can see, those values are encoded in base 64
38:57
So we can actually verify this. Say, I want to copy this
39:04
Okay. let's go back here to the decode option and let's click on decode and I have this value
39:15
There is no value which is C sharp corner line, which is great
39:20
So I don't need to show you the name and series and session as well
39:24
because those are base64. I'm sure about that. Again, remember, if you want to use the manifest file
39:33
then you should encode those values yourself. Anyways, this is great
39:43
I created my first secret and I'm listing all the secrets. And actually this is my last slide
39:50
And you know what, let me, let's change the pod. change the pod let's change this because I want to use the technique that I showed you in this slide
40:08
so instead of using config map key ref I'm going to use secret key ref okay
40:15
Okay, so value from, okay, secret key ref, and the name of the secret is my secret, right
40:26
And the key is only in, okay? So I'm going to create this pod
40:35
and it's going to read the values from the secrets instead of the config maps, okay
40:42
just to be sure that we understand what we're doing here. So before I do this, let's delete the pod
40:53
Because remember that you can change the environment variables while the pod is running
40:59
So let's create the pod by executing apply, kubectl apply my pod.yaml
41:08
So the pod is created. let's verify this kubectl get pods, it's running
41:15
kubectl exec my app EMB and let's see if we have the only in environment variable
41:30
and we have it only underscore in and the value is C sharp corner right
41:37
Make sense? The thing here is that I'm using the secret instead of the config map
41:43
Of course, I'm just using the C-sharp corner line string. It's not super sensitive data
41:50
but of course you can easily see that you can use this with connection strings or E-value pairs or whatnot
41:57
I'm sorry, with API keys or connection strings and sensitive data. Okay
42:07
So cool. So I think I have enough time to do that demo
42:12
that I want to create by using .NET. Let's create a new web API named demo session eight
42:27
Okay. So I'm using .NET for creating this web API. I'm using .NET 7, okay
42:37
So here in this place, I have a lot of things and those are from the template that I'm using
42:49
So let's create a new endpoint here, say get environment variable or something, right
42:57
or something right so I want to use environment environment dot get environment variable and the
43:08
name is only in so I'm going to return this okay and let's use the http get attribute
43:19
uh so this is going to be emb or something actually doesn't matter uh so I'm returning
43:26
each time I execute a get to this endpoint this is going to return the value of only in okay make sense
43:36
so of course there are a lot of there's a lot of noise here actually you know what let me
43:42
just get rid of everything I not going to use anything from the weather forecast thing
43:53
So cool. .NET build. So this is compiling. .NET run. Okay. So this is running
44:04
So I can go ahead and open up a new terminal and let's go back here
44:12
What was the name of the, okay, this is the endpoint. I mean the URL of this web API
44:21
So let's say curl blah, blah, blah, emb. Of course, I'm not going to return anything
44:26
because there's no only in in this particular in my machine, right
44:37
So something's going on. So it's weather forecast EMB. Let me try again
44:45
Weather forecast EMB. Okay, yeah, it's not returning an error. The first one was because my endpoint was incorrect
44:56
Anyways, I'm touching this particular line. and the thing is that I don't have any environment variable
45:06
named only in, okay? So this is the scenario here. Okay, cool
45:13
Let me close Visual Studio because I don't have enough space in this resolution
45:21
And let's do the following. Do you know what? I need to create a Docker file
45:28
What I want to do is, okay, I have this small web API
45:32
that is going to read the environment variable. So I need to create a Docker image file
45:39
I mean, not a file, but the container image, right? And then I have to upload it somewhere
45:45
In that somewhere, most of the time is Docker Hub. So Kubernetes can pull that container image
45:55
when creating a pod. So this is what I'm going to do here
45:59
So .NET new solution, let me create a new solution here. And if you're not a .NET developer
46:09
just be sure that I'm just reading the environment variable. Okay. That's it
46:17
And I created this ESLM file. This is the solution that is for grouping projects in .NET
46:27
so .NET solution add. Okay, cool. Again, let me open up the solution in Visual Studio
46:39
And why Visual Studio? Because I have this beautiful command, this option here, add Docker support for Linux
46:50
and this is gonna create the Docker file. Okay, that's why I created, I'm sorry
46:55
I opened the project inside Visual Studio for creating this Docker file
47:03
That's it. So, okay, I created the Docker file. So as you should know, Docker file files
47:12
are used for creating container images. So I'm ready to create this image container Docker
47:20
what was that command docker build, is that it? Let's see if this is enough
47:37
So what it's doing right now is downloading a bunch of base images because I'm using .NET 7, okay
47:46
So after that is going to start creating the entire container image
47:56
So it looks like it's working. Okay, cool. So at the end of the day
48:04
I will have the demo session eight container image name. Okay. So Docker image list, or what was the Docker image
48:13
image this that's the command right so this is the one I didn't specify any kind of tag
48:26
so let's tag this docker tag and the name of my Docker Hub account
48:41
and then demo session eight. Okay. So I guess I'm ready to push Docker push
48:51
the name of my username demo session eight. So it's pushing this container image to Docker Hub
49:04
So let's wait and see if this is gonna work. Again, let me show you the code for this in the controller
49:18
I'm just using environment.getEnvironmentVariable and a name of an environment variable, okay
49:26
So the thing about this web API is that I want to return the value of that particular environment variable
49:32
Make sense? If you're not a .NET developer, actually it doesn't matter
49:38
It's super easy, right? The only thing that this is doing, that this is executing is this line of code, okay
49:51
The rest of the things here, they doesn't matter. They don't matter, okay
49:56
Okay, let's go back to the terminal and wait for this container image to be pushed
50:04
I'm sorry about that. Anyways, let's wait and see. And let's open up Docker Hub
50:14
I don't know if this is going to work. I am pretty sure it will work
50:21
Okay, hubdocker.com, my username. I don't need to register, I don't need to log in, right
50:32
So, okay, let's wait and see. Let go back here to the terminal And just let wait for this to be pushed Okay
50:47
In the meantime, I'm going to modify my pod.yml because I need to change this
50:56
to that particular container image, right? That I'm just pushing. So the name will be my app
51:05
The image name is another different one. And so I'm creating this environment variable
51:14
This is important, right? This is important. So I just created the secrets
51:23
The secrets are in place. I don't need to do anything else, right
51:27
Because the secrets are part of the cluster. those are decoupled from the pods
51:36
So I think I don't need to do anything else. I'm just creating this only in
51:41
and I'm reading the secret, which the key is only in. Okay, makes sense
51:49
So it's just a matter of waiting for this. So let's wait for a little bit
52:01
It's kind of slow today. Anyways, this is gonna be fun. I promise you I'm going to execute curl
52:11
and it's going to return only in C sharp corner live. only in C-sharp corner line
52:21
So great, that container image name was pushed. Let's go back here
52:29
Yes, so I have it here in my Docker Hub and because of the fact Docker Hub
52:37
is the default container registry for Kubernetes. If I apply this pod manifest file
52:48
I'm telling Kubernetes, hey, do you know what? I want to use this container image name
52:55
So this should work. kubectl get pods. Let's delete this pod. Delete pod my app
53:05
Okay, cool. Get pods. And again, kubectl apply my pod and create it
53:16
So this is being created right now because it needs to pull the container image
53:27
from Docker Hub, right? And of course, I already had the container image
53:33
in my machine, right? So that's why it happened super fast. So it's running
53:42
So let's go back to the terminal. Let's see what happened. Describe pod my app
53:51
So as you can see, pulling image, blah, blah, blah. Successfully pulled image, blah, blah, blah
54:00
Okay, cool. So, okay. Now kubectl exec my app and I want to execute EMB
54:14
And as you can see, this is returning C-sharp corner live. So that's great
54:23
And I need to expose somehow this pod. I need to expose this somehow
54:36
I need to create a service. I don't think I will have the time to do that
54:45
So anyways, I'm going to show you this in the beginning of the next session
54:50
because I need to create a service to expose this pod and then execute curl with the endpoint
55:00
with the endpoint, which is weather forecast forward slash EMB to return this
55:07
However, believe me, this is going to work. I just need to expose this
55:11
However, I don't have enough time in this session. That's going to, I'm going to show you that
55:17
in the following session, okay? Anyways, I showed you this entire flow
55:24
this workflow, right? For creating the container image. actually I created this super fast web API project and then I containerized this project
55:37
I pushed the container image to a docker registry and then I created the pod that pulls
55:44
that container image and anyways the environment variable is there right so
55:52
So the .NET command environment.get environment variable, I assure you that it's going to work
56:01
and it's going to return that. However, I don't have enough time to do that
56:05
in this particular session. So that's what I had for today. And in the following session
56:15
we're going to do a learning checkpoint. So learning checkpoint, okay. Checkpoint is not a feature about Kubernetes
56:25
It's not an object. I just want to review the entire eight sessions
56:31
that we had already, okay? So this is gonna be like a summary
56:37
of all the things related to the first eight sessions that we had in this Kubernetes fundamental series
56:45
only in C-sharp corner, okay? Of course, before we start the learning checkpoint
56:53
I'm going to be sure to show you the service executing curl to return the environment variable value
57:04
Okay. Anyways, this was great. This was fun, config maps and secrets
57:14
Those are for specifying configuration values in a decoupled fashion for our Kubernetes applications and services
57:24
Thank you very much for your time friends and see you next week