Skip to content
Get Started for Free

Database for PostgreSQL Flexible Server

Azure Database for PostgreSQL flexible server is a fully managed relational database service that provides granular control over database configuration and tuning. It supports PostgreSQL community versions and offers built-in high availability, intelligent performance monitoring, and flexible scaling across Burstable, General Purpose, and Memory Optimized compute tiers. Common use cases include web applications, microservices backends, and analytics workloads that benefit from PostgreSQL’s extensibility and standards compliance. For more information, see What is Azure Database for PostgreSQL - Flexible Server?.

LocalStack for Azure provides a local environment for building and testing applications that make use of Azure DB for PostgreSQL. The supported APIs are available on our API Coverage section, which provides information on the extent of DB for PostgreSQL integration with LocalStack.

This guide is designed for users new to Azure DB for PostgreSQL and assumes basic knowledge of the Azure CLI and our azlocal wrapper script.

Launch LocalStack using your preferred method. For more information, see Introduction to LocalStack for Azure. Once the container is running, enable Azure CLI interception by running:

Terminal window
azlocal start-interception

This command points the az CLI away from the public Azure management REST API and toward the LocalStack for Azure emulator API. To revert this configuration, run:

Terminal window
azlocal stop-interception

This reconfigures the az CLI to send commands to the official Azure management REST API.

Create a resource group to hold all resources created in this guide:

Terminal window
az group create \
--name rg-postgres-demo \
--location westeurope
Output
{
"id": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/rg-postgres-demo",
"location": "westeurope",
"name": "rg-postgres-demo",
"properties": {
"provisioningState": "Succeeded"
},
...
}

Create and inspect a PostgreSQL flexible server

Section titled “Create and inspect a PostgreSQL flexible server”

Create a Burstable-tier PostgreSQL 16 flexible server with 32 GB of storage:

Terminal window
az postgres flexible-server create \
--name postgres-demo \
--resource-group rg-postgres-demo \
--location westeurope \
--admin-user pgadmin \
--admin-password 'P@ssw0rd2024!' \
--sku-name Standard_B1ms \
--tier Burstable \
--version 16 \
--storage-size 32 \
--yes
Output
{
"connectionString": "postgresql://pgadmin:P%40ssw0rd2024%21@postgres-demo.postgres.database.azure.com/postgres?sslmode=require",
"host": "postgres-demo.postgres.database.azure.com",
"id": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/rg-postgres-demo/providers/Microsoft.DBforPostgreSQL/flexibleServers/postgres-demo",
"location": "westeurope",
"password": "P@ssw0rd2024!",
"resourceGroup": "rg-postgres-demo",
"skuname": "Standard_B1ms",
"username": "pgadmin",
"version": "16"
}

The command waits for the server to reach the Ready state before returning.

Retrieve the details of the flexible server:

Terminal window
az postgres flexible-server show \
--name postgres-demo \
--resource-group rg-postgres-demo
Output
{
"administratorLogin": "pgadmin",
"authConfig": {
"activeDirectoryAuth": "Disabled",
"passwordAuth": "Enabled",
"tenantId": null
},
"backup": {
"backupRetentionDays": 7,
"geoRedundantBackup": "Disabled"
},
"fullyQualifiedDomainName": "postgres-demo.postgres.database.azure.com",
"highAvailability": {
"mode": "Disabled",
"state": "NotEnabled"
},
"id": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/rg-postgres-demo/providers/Microsoft.DBforPostgreSQL/flexibleServers/postgres-demo",
"location": "westeurope",
"name": "postgres-demo",
"network": {
"publicNetworkAccess": "Enabled"
},
"resourceGroup": "rg-postgres-demo",
"sku": {
"name": "Standard_B1ms",
"tier": "Burstable"
},
"state": "Ready",
"storage": {
"autoGrow": "Disabled",
"storageSizeGb": 32,
"tier": "P4",
"type": "Premium_LRS"
},
"type": "Microsoft.DBforPostgreSQL/flexibleServers",
"version": "16",
...
}

Then list all flexible servers in the resource group:

Terminal window
az postgres flexible-server list \
--resource-group rg-postgres-demo
Output
[
{
"id": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/rg-postgres-demo/providers/Microsoft.DBforPostgreSQL/flexibleServers/postgres-demo",
"location": "westeurope",
"name": "postgres-demo",
"sku": {
"name": "Standard_B1ms",
"tier": "Burstable"
},
"state": "Ready",
"version": "16",
...
}
]

Update the server SKU and storage size:

Terminal window
az postgres flexible-server update \
--name postgres-demo \
--resource-group rg-postgres-demo \
--sku-name Standard_B2s \
--tier Burstable \
--storage-size 64
Output
{
"administratorLogin": "pgadmin",
"authConfig": {
"activeDirectoryAuth": "Disabled",
"passwordAuth": "Enabled",
"tenantId": null
},
"backup": {
"backupRetentionDays": 7,
"geoRedundantBackup": "Disabled"
},
"fullyQualifiedDomainName": "postgres-demo.postgres.database.azure.com",
"highAvailability": {
"mode": "Disabled",
"state": "NotEnabled"
},
"id": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/rg-postgres-demo/providers/Microsoft.DBforPostgreSQL/flexibleServers/postgres-demo",
"location": "westeurope",
"name": "postgres-demo",
"network": {
"publicNetworkAccess": "Enabled"
},
"resourceGroup": "rg-postgres-demo",
"sku": {
"name": "Standard_B2s",
"tier": "Burstable"
},
"state": "Ready",
"storage": {
"autoGrow": "Disabled",
"storageSizeGb": 64,
"tier": "P6",
"type": "Premium_LRS"
},
"type": "Microsoft.DBforPostgreSQL/flexibleServers",
"version": "16",
...
}

Create a database on the flexible server:

Terminal window
az postgres flexible-server db create \
--server-name postgres-demo \
--resource-group rg-postgres-demo \
--database-name sampledb \
--charset UTF8 \
--collation en_US.utf8
Output
{
"charset": "UTF8",
"collation": "en_US.utf8",
"id": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/rg-postgres-demo/providers/Microsoft.DBforPostgreSQL/flexibleServers/postgres-demo/databases/sampledb",
"name": "sampledb",
"resourceGroup": "rg-postgres-demo",
"type": "Microsoft.DBforPostgreSQL/flexibleServers/databases"
}

Get and list databases:

Terminal window
az postgres flexible-server db show \
--resource-group rg-postgres-demo \
--server-name postgres-demo \
--database-name sampledb
az postgres flexible-server db list \
--resource-group rg-postgres-demo \
--server-name postgres-demo
Output
{
"name": "sampledb",
"charset": "utf8",
"collation": "en_US.utf8",
...
}
[
{
"name": "postgres",
...
},
{
"name": "azure_sys",
...
},
{
"name": "azure_maintenance",
...
},
{
"name": "sampledb",
...
}
]

Create a firewall rule to allow connections from a specific IP address:

Terminal window
az postgres flexible-server firewall-rule create \
--resource-group rg-postgres-demo \
--name postgres-demo \
--rule-name allow-myip \
--start-ip-address 203.0.113.10 \
--end-ip-address 203.0.113.10
Output
{
"id": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/rg-postgres-demo/providers/Microsoft.DBforPostgreSQL/flexibleServers/postgres-demo/firewallRules/allow-myip",
"name": "allow-myip",
"resourceGroup": "rg-postgres-demo",
"startIpAddress": "203.0.113.10",
"endIpAddress": "203.0.113.10",
"type": "Microsoft.DBforPostgreSQL/flexibleServers/firewallRules"
}

Get and list firewall rules:

Terminal window
az postgres flexible-server firewall-rule show \
--resource-group rg-postgres-demo \
--name postgres-demo \
--rule-name allow-myip
az postgres flexible-server firewall-rule list \
--resource-group rg-postgres-demo \
--name postgres-demo
Output
{
"name": "allow-myip",
"startIpAddress": "203.0.113.10",
"endIpAddress": "203.0.113.10",
...
}
[
{
"name": "allow-myip",
"startIpAddress": "203.0.113.10",
"endIpAddress": "203.0.113.10",
...
}
]

View the current value of the max_connections configuration parameter:

Terminal window
az postgres flexible-server parameter show \
--resource-group rg-postgres-demo \
--server-name postgres-demo \
--name max_connections
Output
{
"allowedValues": "25-5000",
"dataType": "Integer",
"defaultValue": "100",
"description": "Sets the maximum number of concurrent connections.",
"documentationLink": "https://www.postgresql.org/docs/16/runtime-config-connection.html#GUC-MAX-CONNECTIONS",
"id": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/rg-postgres-demo/providers/Microsoft.DBforPostgreSQL/flexibleServers/postgres-demo/configurations/max_connections",
"isConfigPendingRestart": false,
"isDynamicConfig": false,
"isReadOnly": false,
"name": "max_connections",
"resourceGroup": "rg-postgres-demo",
"source": "system-default",
"type": "Microsoft.DBforPostgreSQL/flexibleServers/configurations",
"unit": "",
"value": "100"
}

Update max_connections to 200:

Terminal window
az postgres flexible-server parameter set \
--resource-group rg-postgres-demo \
--server-name postgres-demo \
--name max_connections \
--value 200 \
--source user-override
Output
{
"allowedValues": "25-5000",
"dataType": "Integer",
"defaultValue": "100",
"description": "Sets the maximum number of concurrent connections.",
"documentationLink": "https://www.postgresql.org/docs/16/runtime-config-connection.html#GUC-MAX-CONNECTIONS",
"id": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/rg-postgres-demo/providers/Microsoft.DBforPostgreSQL/flexibleServers/postgres-demo/configurations/max_connections",
"isConfigPendingRestart": true,
"isDynamicConfig": false,
"isReadOnly": false,
"name": "max_connections",
"resourceGroup": "rg-postgres-demo",
"source": "user-override",
"type": "Microsoft.DBforPostgreSQL/flexibleServers/configurations",
"unit": "",
"value": "200"
}

Non-dynamic parameters such as max_connections set isConfigPendingRestart to true after an update. A server restart applies the change.

Stop the flexible server:

Terminal window
az postgres flexible-server stop \
--resource-group rg-postgres-demo \
--name postgres-demo
Output
Server will be automatically started after 7 days if you do not perform a manual start operation

Verify the server state is Stopped:

Terminal window
az postgres flexible-server show \
--name postgres-demo \
--resource-group rg-postgres-demo \
--query state \
--output tsv
Output
Stopped

Start the server again:

Terminal window
az postgres flexible-server start \
--resource-group rg-postgres-demo \
--name postgres-demo

Restart the server to apply pending configuration changes:

Terminal window
az postgres flexible-server restart \
--resource-group rg-postgres-demo \
--name postgres-demo

Delete the flexible server:

Terminal window
az postgres flexible-server delete \
--resource-group rg-postgres-demo \
--name postgres-demo \
--yes

Then list all flexible servers to confirm the resource group is now empty:

Terminal window
az postgres flexible-server list \
--resource-group rg-postgres-demo
Output
[]

The PostgreSQL Flexible Server emulator supports the following features:

  • Server lifecycle management: Create, get, update, list, and delete flexible servers with full ARM resource model support.
  • Stop, start, and restart: Transition servers between Ready and Stopped states with proper state machine enforcement.
  • Database management: Create, get, list, and delete user databases. Each database is backed by a real PostgreSQL instance.
  • Firewall rules: Create, get, update, list, and delete IP-based firewall rules with address range validation.
  • Server configuration: Get, list, and update over 14 PostgreSQL configuration parameters with data-type validation and restart-pending tracking.
  • SKU tiers: Burstable, General Purpose, and Memory Optimized tiers with multiple SKU sizes per tier.
  • PostgreSQL versions: Versions 13, 14, 15, 16, and 17 with in-place major version upgrade support.
  • Storage management: Configurable storage from 32 GB to 16 TB with automatic tier mapping and storage auto-grow support.
  • Name availability check: Validate server name uniqueness across subscriptions before creation.
  • Location capabilities: Query available SKUs, storage sizes, and supported PostgreSQL versions per region.
  • Long-running operations: Server create, delete, start, stop, and restart return 202 Accepted with async operation tracking headers.
  • Bicep and Terraform support: Deploy flexible servers, databases, and firewall rules using infrastructure-as-code templates.
  • Backup and restore: Backup retention days and geo-redundant backup settings are stored but no actual backups are performed. Point-in-time restore is not supported.
  • Read replicas: Replica properties are returned in the server response but replica creation and management are not implemented.
  • Microsoft Entra authentication: The authConfig.activeDirectoryAuth property is stored but Active Directory authentication is not enforced.
  • Virtual network integration: Delegated subnet and private DNS zone properties are accepted but VNet injection is not performed.
  • Private endpoint connections: The property is returned in the response but private endpoint connectivity is not implemented.
  • High availability failover: High availability mode and standby availability zone are stored but no failover mechanism is active.
  • Firewall rule enforcement: Firewall rules are stored and queryable but are not enforced on actual database connections.
  • Storage auto-grow enforcement: The auto-grow setting is stored but automatic storage expansion does not occur.

Explore end-to-end examples in the LocalStack for Azure Samples repository.

OperationImplemented
Page 1 of 0
Was this page helpful?