Skip to content

Commit fa607f0

Browse files
committed
Add PostgreSQL Flexible Server sample
Add a new sample demonstrating Azure PostgreSQL Flexible Server deployment with Python SDK, .NET SDK, and a notes app, including Terraform, Bicep, and ARM (scripts) deployment options. Use az rest for server creation to bypass CLI SKU validation that fails on LocalStack's capabilities endpoint.
1 parent c15235f commit fa607f0

File tree

26 files changed

+2553
-1
lines changed

26 files changed

+2553
-1
lines changed

README.md

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,8 @@ This repository contains comprehensive sample projects demonstrating how to deve
2929
| [Function App and Storage](./samples/function-app-storage-http/dotnet/README.md) | Azure Functions App using Blob, Queue, and Table Storage |
3030
| [Function App and Front Door](./samples/function-app-front-door/python/README.md) | Azure Functions App exposed via Front Door |
3131
| [Function App and Managed Identities](./samples/function-app-managed-identity/python/README.md) | Azure Function App using Managed Identities |
32-
| [Web App and CosmosDB for MongoDB API ](./samples/web-app-cosmosdb-mongodb-api/python/README.md) | Azure Web App using CosmosDB for MongoDB API |
32+
| [PostgreSQL Flexible Server](./samples/postgresql-flexible-server/python/README.md) | Azure PostgreSQL Flexible Server with Python SDK, .NET SDK, and Flask apps |
33+
| [Web App and CosmosDB for MongoDB API ](./samples/web-app-cosmosdb-mongodb-api/python/README.md) | Azure Web App using CosmosDB for MongoDB API |
3334
| [Web App and CosmosDB for NoSQL API ](./samples/web-app-cosmosdb-nosql-api/python/README.md) | Azure Web App using CosmosDB for NoSQL API |
3435
| [Web App and Managed Identities](./samples/web-app-managed-identity/python/README.md) | Azure Web App using Managed Identities |
3536
| [Web App and SQL Database ](./samples/web-app-sql-database/python/README.md) | Azure Web App using SQL Database |

run-samples.sh

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -81,6 +81,7 @@ SAMPLES=(
8181
"samples/web-app-cosmosdb-mongodb-api/python|bash scripts/deploy.sh|bash scripts/validate.sh && bash scripts/call-web-app.sh"
8282
"samples/web-app-managed-identity/python|bash scripts/user-assigned.sh|bash scripts/validate.sh && bash scripts/call-web-app.sh"
8383
"samples/web-app-sql-database/python|bash scripts/deploy.sh|bash scripts/validate.sh && bash scripts/get-web-app-url.sh"
84+
"samples/postgresql-flexible-server/python|bash scripts/deploy.sh|bash scripts/validate.sh"
8485
)
8586

8687
# 3a. Define Terraform Samples
@@ -90,6 +91,7 @@ TERRAFORM_SAMPLES=(
9091
"samples/web-app-cosmosdb-mongodb-api/python/terraform|bash deploy.sh"
9192
"samples/web-app-managed-identity/python/terraform|bash deploy.sh"
9293
"samples/web-app-sql-database/python/terraform|bash deploy.sh"
94+
"samples/postgresql-flexible-server/python/terraform|bash deploy.sh"
9395
)
9496

9597
# 3b. Define Bicep Samples
@@ -99,6 +101,7 @@ BICEP_SAMPLES=(
99101
"samples/function-app-storage-http/dotnet/bicep|bash deploy.sh"
100102
"samples/web-app-cosmosdb-mongodb-api/python/bicep|bash deploy.sh"
101103
"samples/web-app-managed-identity/python/bicep|bash deploy.sh"
104+
"samples/postgresql-flexible-server/python/bicep|bash deploy.sh"
102105
)
103106

104107
# 4. Calculate Shard
Lines changed: 206 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,206 @@
1+
# Azure Database for PostgreSQL Flexible Server
2+
3+
This sample demonstrates a Notes web application with full-text search, powered by [Azure Database for PostgreSQL Flexible Server](https://learn.microsoft.com/en-us/azure/postgresql/flexible-server/overview). The app is a Python Flask single-page application that creates, searches, and deletes notes stored in the `notes` table within the `sampledb` database on a PostgreSQL Flexible Server instance. The sample also includes Python and C# Azure SDK management demos that exercise server, database, configuration, and firewall rule operations.
4+
5+
## Architecture
6+
7+
The following diagram illustrates the architecture of the solution:
8+
9+
```mermaid
10+
graph TB
11+
subgraph IaC["Infrastructure as Code"]
12+
CLI["Azure CLI<br/>(azlocal)"]
13+
Bicep["Bicep<br/>(main.bicep)"]
14+
TF["Terraform<br/>(main.tf)"]
15+
end
16+
17+
subgraph LS["LocalStack for Azure"]
18+
MGMT["Management API<br/>(ARM / REST)"]
19+
PG_SERVER["PostgreSQL Flexible Server"]
20+
subgraph DBs["Databases"]
21+
SAMPLEDB["sampledb"]
22+
ANALYTICSDB["analyticsdb"]
23+
end
24+
FW["Firewall Rules<br/>allow-all · corporate · vpn"]
25+
end
26+
27+
subgraph DC["Docker Compose Containers"]
28+
NOTES["Notes App<br/>(Flask · port 5001)"]
29+
SDK_PY["Python SDK Demo<br/>(azure-mgmt-postgresql)"]
30+
SDK_CS["C# SDK Demo<br/>(Azure.ResourceManager)"]
31+
end
32+
33+
USER((User<br/>Browser))
34+
35+
CLI -->|provision| MGMT
36+
Bicep -->|provision| MGMT
37+
TF -->|provision| MGMT
38+
MGMT --> PG_SERVER
39+
PG_SERVER --> DBs
40+
PG_SERVER --> FW
41+
42+
USER -->|"http://localhost:5001"| NOTES
43+
NOTES <-->|"psycopg2 · CRUD + full-text search"| SAMPLEDB
44+
45+
SDK_PY -->|"management plane<br/>list servers · configs · DBs · rules"| MGMT
46+
SDK_PY -->|"psycopg2 · direct query"| SAMPLEDB
47+
SDK_PY -->|"POST results to UI"| NOTES
48+
49+
SDK_CS -->|"management plane<br/>ArmClient · list · get"| MGMT
50+
SDK_CS -->|"Npgsql · direct query"| SAMPLEDB
51+
SDK_CS -->|"POST results to UI"| NOTES
52+
53+
USER -.->|"trigger SDK demo"| NOTES
54+
NOTES -.->|"trigger signal"| SDK_PY
55+
NOTES -.->|"trigger signal"| SDK_CS
56+
```
57+
58+
- **Azure Database for PostgreSQL Flexible Server**: Managed PostgreSQL database server hosting the `sampledb` and `analyticsdb` databases
59+
- **Notes App (Flask)**: Python Flask web application with full-text search using PostgreSQL `tsvector`
60+
- **Python SDK Demo**: Demonstrates `azure-mgmt-postgresqlflexibleservers` management operations (list servers, get/update configurations, list databases, manage firewall rules, check name availability)
61+
- **C# SDK Demo**: Demonstrates `Azure.ResourceManager.PostgreSql` management operations from .NET
62+
63+
## Prerequisites
64+
65+
- [Azure Subscription](https://azure.microsoft.com/free/)
66+
- [Azure CLI](https://learn.microsoft.com/en-us/cli/azure/install-azure-cli)
67+
- [Python 3.12+](https://www.python.org/downloads/)
68+
- [Docker](https://docs.docker.com/get-docker/)
69+
- [Bicep extension](https://marketplace.visualstudio.com/items?itemName=ms-azuretools.vscode-bicep), if you plan to install the sample via Bicep.
70+
- [Terraform](https://developer.hashicorp.com/terraform/downloads), if you plan to install the sample via Terraform.
71+
72+
## Deployment
73+
74+
Set up the Azure emulator using the LocalStack for Azure Docker image. Before starting, ensure you have a valid `LOCALSTACK_AUTH_TOKEN` to access the Azure emulator. Refer to the [Auth Token guide](https://docs.localstack.cloud/getting-started/auth-token/) to obtain your Auth Token and set it in the `LOCALSTACK_AUTH_TOKEN` environment variable. The Azure Docker image is available on the [LocalStack Docker Hub](https://hub.docker.com/r/localstack/localstack-azure-alpha). To pull the image, execute:
75+
76+
```bash
77+
docker pull localstack/localstack-azure-alpha
78+
```
79+
80+
Start the LocalStack Azure emulator by running:
81+
82+
```bash
83+
export LOCALSTACK_AUTH_TOKEN=<your_auth_token>
84+
IMAGE_NAME=localstack/localstack-azure-alpha localstack start
85+
```
86+
87+
Deploy the application to LocalStack for Azure using one of these methods:
88+
89+
- [Azure CLI Deployment](./scripts/README.md)
90+
- [Bicep Deployment](./bicep/README.md)
91+
- [Terraform Deployment](./terraform/README.md)
92+
93+
All deployment methods have been fully tested against Azure and the LocalStack for Azure local emulator.
94+
95+
> **Note**
96+
> When you deploy the application to LocalStack for Azure for the first time, the initialization process involves downloading and building Docker images. This is a one-time operation—subsequent deployments will be significantly faster. Depending on your internet connection and system resources, this initial setup may take several minutes.
97+
98+
## Test
99+
100+
After provisioning the PostgreSQL Flexible Server infrastructure using any of the deployment methods above, launch the application containers using Docker Compose:
101+
102+
```bash
103+
cd samples/postgresql-flexible-server/python
104+
105+
# Set environment variables (adjust values based on your deployment outputs)
106+
export RESOURCE_GROUP="rg-pgflex"
107+
export SERVER_NAME="pgflex-sample"
108+
export PG_HOST="host.docker.internal"
109+
export PG_PORT="5432"
110+
export PG_USER="pgadmin"
111+
export PG_PASSWORD="P@ssw0rd12345!"
112+
export PG_DATABASE="sampledb"
113+
export FLASK_PORT="5001"
114+
115+
docker compose up --build
116+
```
117+
118+
Open a web browser and navigate to `http://localhost:5001`. If the deployment was successful, you will see the Notes application with full-text search and Azure SDK demo panels.
119+
120+
You can use the `validate.sh` Bash script below to verify that all Azure resources were created and configured correctly:
121+
122+
```bash
123+
#!/bin/bash
124+
125+
# Variables
126+
RESOURCE_GROUP='rg-pgflex'
127+
SERVER_NAME='pgflex-sample'
128+
PRIMARY_DB='sampledb'
129+
SECONDARY_DB='analyticsdb'
130+
ENVIRONMENT=$(az account show --query environmentName --output tsv)
131+
132+
# Choose the appropriate CLI based on the environment
133+
if [[ $ENVIRONMENT == "LocalStack" ]]; then
134+
echo "Using azlocal for LocalStack emulator environment."
135+
AZ="azlocal"
136+
else
137+
echo "Using standard az for AzureCloud environment."
138+
AZ="az"
139+
fi
140+
141+
# Check resource group
142+
echo "=== Resource Group ==="
143+
$AZ group show \
144+
--name "$RESOURCE_GROUP" \
145+
--output table
146+
147+
# List resources in the resource group
148+
echo ""
149+
echo "=== Resources ==="
150+
$AZ resource list \
151+
--resource-group "$RESOURCE_GROUP" \
152+
--output table
153+
154+
# Check PostgreSQL Flexible Server
155+
echo ""
156+
echo "=== PostgreSQL Flexible Server ==="
157+
$AZ postgres flexible-server show \
158+
--name "$SERVER_NAME" \
159+
--resource-group "$RESOURCE_GROUP" \
160+
--output table
161+
162+
# List databases
163+
echo ""
164+
echo "=== Databases ==="
165+
$AZ postgres flexible-server db list \
166+
--server-name "$SERVER_NAME" \
167+
--resource-group "$RESOURCE_GROUP" \
168+
--output table
169+
170+
# List firewall rules
171+
echo ""
172+
echo "=== Firewall Rules ==="
173+
$AZ postgres flexible-server firewall-rule list \
174+
--server-name "$SERVER_NAME" \
175+
--resource-group "$RESOURCE_GROUP" \
176+
--output table
177+
```
178+
179+
## PostgreSQL Tooling
180+
181+
You can use [pgAdmin](https://www.pgadmin.org/) to explore and manage your PostgreSQL databases. When connecting, specify `localhost` as the host and use the port published by the PostgreSQL container on the host, mapped to the internal PostgreSQL port `5432`.
182+
183+
Alternatively, you can use the [psql](https://www.postgresql.org/docs/current/app-psql.html) command-line tool to interact with and administer your PostgreSQL instance, as shown below:
184+
185+
```bash
186+
~$ psql -h localhost -p 49114 -U pgadmin -d sampledb
187+
Password for user pgadmin:
188+
psql (16.0)
189+
Type "help" for help.
190+
191+
sampledb=# SELECT id, title, SUBSTRING(content, 1, 30) FROM notes;
192+
id | title | substring
193+
----+----------------+--------------------------------
194+
1 | Meeting Notes | Discussed Q4 planning and bud
195+
2 | Shopping List | Eggs, milk, bread, butter, ch
196+
3 | Project Ideas | Build a notes app with full-te
197+
(3 rows)
198+
```
199+
200+
## References
201+
202+
- [Azure Database for PostgreSQL Flexible Server](https://learn.microsoft.com/en-us/azure/postgresql/flexible-server/overview)
203+
- [Azure CLI — PostgreSQL Flexible Server](https://learn.microsoft.com/en-us/cli/azure/postgres/flexible-server)
204+
- [Terraform — azurerm_postgresql_flexible_server](https://registry.terraform.io/providers/hashicorp/azurerm/latest/docs/resources/postgresql_flexible_server)
205+
- [Azure Identity Client Library for Python](https://learn.microsoft.com/en-us/python/api/overview/azure/identity-readme?view=azure-python)
206+
- [LocalStack for Azure](https://azure.localstack.cloud/)
Lines changed: 124 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,124 @@
1+
# Bicep Deployment
2+
3+
This directory contains the Bicep template and a deployment script for provisioning Azure Database for PostgreSQL Flexible Server resources in LocalStack for Azure. Refer to the [Azure Database for PostgreSQL Flexible Server](../README.md) guide for details about the sample application.
4+
5+
## Prerequisites
6+
7+
Before deploying this solution, ensure you have the following tools installed:
8+
9+
- [LocalStack for Azure](https://azure.localstack.cloud/): Local Azure cloud emulator for development and testing
10+
- [Visual Studio Code](https://code.visualstudio.com/): Code editor installed on one of the [supported platforms](https://code.visualstudio.com/docs/supporting/requirements#_platforms)
11+
- [Bicep extension](https://marketplace.visualstudio.com/items?itemName=ms-azuretools.vscode-bicep): VS Code extension for Bicep language support and IntelliSense
12+
- [Docker](https://docs.docker.com/get-docker/): Container runtime required for LocalStack
13+
- [Azure CLI](https://learn.microsoft.com/en-us/cli/azure/install-azure-cli): Azure command-line interface
14+
- [azlocal CLI](https://azure.localstack.cloud/user-guides/sdks/az/): LocalStack Azure CLI wrapper
15+
- [Python](https://www.python.org/downloads/): Python runtime (version 3.12 or above)
16+
- [jq](https://jqlang.org/): JSON processor for scripting and parsing command outputs
17+
18+
### Installing azlocal CLI
19+
20+
The [deploy.sh](deploy.sh) Bash script uses the `azlocal` CLI instead of the standard Azure CLI to work with LocalStack. Install it using:
21+
22+
```bash
23+
pip install azlocal
24+
```
25+
26+
For more information, see [Get started with the az tool on LocalStack](https://azure.localstack.cloud/user-guides/sdks/az/).
27+
28+
## Architecture Overview
29+
30+
The [deploy.sh](deploy.sh) script creates the [Azure Resource Group](https://learn.microsoft.com/en-us/azure/azure-resource-manager/management/manage-resource-groups-cli) for all the Azure resources, while the [main.bicep](main.bicep) Bicep module creates the following Azure resources:
31+
32+
1. [Azure Database for PostgreSQL Flexible Server](https://learn.microsoft.com/en-us/azure/postgresql/flexible-server/overview): Managed PostgreSQL database server with version 16.
33+
2. [PostgreSQL Database](https://learn.microsoft.com/en-us/azure/postgresql/flexible-server/concepts-servers): The `sampledb` database for the Notes application.
34+
3. [Firewall Rule](https://learn.microsoft.com/en-us/azure/postgresql/flexible-server/concepts-firewall-rules): Allows access from all IP addresses for development.
35+
36+
For more information, see [Azure Database for PostgreSQL Flexible Server](../README.md).
37+
38+
## Deployment
39+
40+
You can set up the Azure emulator by utilizing LocalStack for Azure Docker image. Before starting, ensure you have a valid `LOCALSTACK_AUTH_TOKEN` to access the Azure emulator. Refer to the [Auth Token guide](https://docs.localstack.cloud/getting-started/auth-token/) to obtain your Auth Token and specify it in the `LOCALSTACK_AUTH_TOKEN` environment variable. The Azure Docker image is available on the [LocalStack Docker Hub](https://hub.docker.com/r/localstack/localstack-azure-alpha). To pull the Azure Docker image, execute the following command:
41+
42+
```bash
43+
docker pull localstack/localstack-azure-alpha
44+
```
45+
46+
Start the LocalStack Azure emulator using the localstack CLI, execute the following command:
47+
48+
```bash
49+
export LOCALSTACK_AUTH_TOKEN=<your_auth_token>
50+
IMAGE_NAME=localstack/localstack-azure-alpha localstack start
51+
```
52+
53+
Navigate to the `bicep` folder:
54+
55+
```bash
56+
cd samples/postgresql-flexible-server/python/bicep
57+
```
58+
59+
Make the script executable:
60+
61+
```bash
62+
chmod +x deploy.sh
63+
```
64+
65+
Run the deployment script:
66+
67+
```bash
68+
./deploy.sh
69+
```
70+
71+
## Validation
72+
73+
After deployment, you can use the `validate.sh` script to verify that all resources were created and configured correctly:
74+
75+
```bash
76+
#!/bin/bash
77+
78+
# Variables
79+
ENVIRONMENT=$(az account show --query environmentName --output tsv)
80+
81+
# Choose the appropriate CLI based on the environment
82+
if [[ $ENVIRONMENT == "LocalStack" ]]; then
83+
echo "Using azlocal for LocalStack emulator environment."
84+
AZ="azlocal"
85+
else
86+
echo "Using standard az for AzureCloud environment."
87+
AZ="az"
88+
fi
89+
90+
# Check resource group
91+
$AZ group show \
92+
--name rg-pgflex-bicep \
93+
--output table
94+
95+
# List resources
96+
$AZ resource list \
97+
--resource-group rg-pgflex-bicep \
98+
--output table
99+
100+
# Check PostgreSQL Flexible Server
101+
$AZ postgres flexible-server list \
102+
--resource-group rg-pgflex-bicep \
103+
--output table
104+
```
105+
106+
## Cleanup
107+
108+
To destroy all created resources:
109+
110+
```bash
111+
# Delete resource group and all contained resources
112+
azlocal group delete --name rg-pgflex-bicep --yes --no-wait
113+
114+
# Verify deletion
115+
azlocal group list --output table
116+
```
117+
118+
This will remove all Azure resources created by the Bicep deployment script.
119+
120+
## Related Documentation
121+
122+
- [Azure Bicep Documentation](https://docs.microsoft.com/en-us/azure/azure-resource-manager/bicep/)
123+
- [Bicep Language Reference](https://docs.microsoft.com/en-us/azure/azure-resource-manager/bicep/bicep-functions)
124+
- [LocalStack for Azure Documentation](https://azure.localstack.cloud/)

0 commit comments

Comments
 (0)