Micro service skeleton can be created and deployed in 5 min.
Most of the logic is 'mix task'. To make the task available in all directories for current user clone the repo and type:
MIX_ENV=prod mix do compile, archive.build --include-dot-files, archive.install
This adds family of usvc mix tasks.
Starting with project creation all the way to deployment.
mix usvc.new <svc_name>
Command creates new Elixir project and populates it with 'Hello' http server + some config and script files. Http server listens on port 4000.
cd <svc_name>
All development is conducted in Docker container based on renderedtext/elixir image.
The container is connected to the host network.
To automatically recompile and run tests on each file change:
make watch
Starts interactive docker image with mounted project directories:
make console
If you need PostgreSql database for local development:
make postgres.run
It will run Postgres in Docker container in background, connected to the host network.
The database will not persist data outside the container.
To stop it:
docker kill db
make image.build
Note:
Build target creates docker image called renderedtext/<svc_name>
with these tags:
latest<git_hash>-<SEMAPHORE_EXECUTABLE_UUID>
make image.runwill:- build
renderedtext/<svc_name>image and - run container created from it.
- build
make image.testwill:- build
renderedtext/<svc_name>image - generate
docker-compose.ymlfromdocker-compose.yml.eex - run all containers defined in
docker-compose.yml
- build
To test container send requests to port 4000 (e.g. curl localhost:4000/)
To upload image to DockerHub repo use make image.push.
To download image from DockerHub repo use make image.pull.
To deploy
make deploy
This command deploys to default k8s cluster.
Before deploy, it pushes docker image to DockerHub.
Note: By default k8s uses dockerhub-secrets secret to pull image from DockerHub.
dockerhub-secrets contains rtrobot DockerHub user's credentials.
To grant rtrobot permission to pull image
you need to give read permissions on your new service image
to DockerHub team deployers.
After the micro-service initial deployment, it is not visible outside the k8s cluster.
In order to communicate with the service you must either:
- Create request from within the cluster or
- Create load balancer and make the micro-service accessible from outside the cluster.
When new micro-service is first deployed k8s entity called 'service'
of type NodePort is created.
It creates stable IP address within cluster for the micro-service.
After each successful deploy, this entity's configuration is shown.
It looks like this:
NAME CLUSTER-IP EXTERNAL-IP PORT(S) AGE
<usvc> 100.67.25.213 <nodes> 4000:30195/TCP 4d
The configuration tells us that the micro-service is, within the cluster, accessible on IP 100.67.25.213 and port 4000 (disregard the second port number).
To send request from within the cluster you need to "enter" existing container in the cluster (or create new one) to issue requests from. First list all pods in the namespace and jump into container in one of them:
kubectl get po
....
kubectl exec -it <pod-name> /bin/bash
After that issue requests from within the container:
ssh curl <cluster-ip>:<port>
There are two types of load balancers in AWS
- Traditional ELB and
- Application LB (ALB)
Latter is preferred one in RT. In k8s terminology, ALB is called ingress.
There is one cluster wide ingress. To register your new micro-service in it, edit the configuration file.