HashiCorp Certified: Consul Associate Certification
Register Services and Use Service Discovery
Demo Prepared Queries
In this guide, we’ll cover how to leverage Consul Prepared Queries for metadata-driven traffic routing. You’ll learn to create, inspect, and update prepared queries to shift traffic seamlessly between service versions.
Consul Cluster Overview
Start by verifying your cluster members on a server node:
consul members
Sample output:
Node Address Status Type Build Protocol DC Segment
consul-node-a 10.0.101.110:8301 alive server 1.9.3+ent 2 us-east-1 <all>
consul-node-b 10.0.101.248:8301 alive server 1.9.3+ent 2 us-east-1 <all>
web-server-01 10.0.101.177:8301 alive client 1.9.3+ent 2 us-east-1 <default>
web-server-02 10.0.101.114:8301 alive client 1.9.3+ent 2 us-east-1 <default>
For clarity, here’s the same data in a table:
Node | Address | Status | Type | Protocol | Datacenter |
---|---|---|---|---|---|
consul-node-a | 10.0.101.110:8301 | alive | server | 2 | us-east-1 |
consul-node-b | 10.0.101.248:8301 | alive | server | 2 | us-east-1 |
web-server-01 | 10.0.101.177:8301 | alive | client | 2 | us-east-1 |
web-server-02 | 10.0.101.114:8301 | alive | client | 2 | us-east-1 |
Each client hosts an Apache-based e-commerce front end, registering the front-end-eCommerce
service with version tags.
Service Registration in the Consul UI
In the Consul web interface, you’ll see two instances of front-end-eCommerce
. One is tagged v7.05
and the other v8
, both in the production
environment.
Server | IP Address | Version Tag |
---|---|---|
web-server-02 | 10.0.101.114 | v7.05 |
web-server-01 | 10.0.101.177 | v8 |
Creating a Prepared Query
Save this JSON as
prepared-query.json
:{ "Name": "eCommerce", "Service": { "Service": "front-end-eCommerce", "Tags": ["v7.05", "production"] } }
Register the query via Consul’s HTTP API:
curl --request POST --data @prepared-query.json http://10.0.101.110:8500/v1/query | jq
Response:
{ "ID": "b34f3b89-68be-9285-8f3e-c05d5d09f7le" }
Inspect the full query definition:
curl http://10.0.101.110:8500/v1/query/b34f3b89-68be-9285-8f3e-c05d5d09f7le | jq
{ "ID": "b34f3b89-68be-9285-8f3e-c05d5d09f7le", "Name": "eCommerce", "Service": { "Service": "front-end-eCommerce", "Failover": { "NearestN": 0, "Datacenters": null } }, "OnlyPassing": false, "Tags": ["v7.05", "production"] // ... other fields ... }
Best Practice
Set "OnlyPassing": true
in your query definition to ensure only healthy service instances are returned.
Querying via DNS
Consul exposes prepared queries under the *.query.consul
DNS domain. Run:
dig @10.0.101.110 -p 8600 eCommerce.query.consul
You should see the IP of the v7.05
instance:
;; ANSWER SECTION:
eCommerce.query.consul. 0 IN A 10.0.101.114
Updating the Prepared Query to v8
When it’s time to shift traffic to version v8
, update prepared-query.json
:
{
"Name": "eCommerce",
"Service": {
"Service": "front-end-eCommerce",
"Tags": ["v8", "production"]
}
}
Apply the update with a PUT
request (replace the ID):
curl --request PUT --data @prepared-query.json \
http://10.0.101.110:8500/v1/query/b34f3b89-68be-9285-8f3e-c05d5d09f7le
Then verify with DNS again:
dig @10.0.101.110 -p 8600 eCommerce.query.consul
;; ANSWER SECTION:
eCommerce.query.consul. 0 IN A 10.0.101.177
Ensure Correct ID
Always replace the query ID in your API URL when inspecting or updating prepared queries.
Conclusion
Consul Prepared Queries enable you to route client requests based on service metadata without touching client configurations. By updating the query payload, you can perform zero-downtime version rollouts and A/B testing with ease.
Links and References
Watch Video
Watch video content
Practice Lab
Practice lab