CloudBrum
CloudBrum · Cloud decision-support platform
Google Cloud Databases

Cloud SQLLast reviewedReading time~12 minLevelBeginner to advanced

Google Cloud · Databases · Managed relational database

Google runs the database server, you run the data. Cloud SQL gives you MySQL, PostgreSQL or SQL Server as a managed instance, with automatic backups, a standby in another zone and read replicas. The choice that matters most is the edition. Enterprise covers most applications, and Enterprise Plus adds a higher availability promise and near-zero planned downtime for a higher price. Decide between a private and a public address at creation, because it shapes how everything connects.

On this page (17 sections)

    Mind map: Cloud SQL at a glance

    Cloud SQL mind map Cloud SQL at a glance: Engines: PostgreSQL, MySQL, SQL Server; Editions: Enterprise, Enterprise Plus, Data cache; Availability: Regional HA standby, Automatic failover, Maintenance windows; Scale: Read replicas, Storage auto-increase, Cascading replicas; Backup: Automated and on-demand, Point-in-time recovery, Retained backup count; Network: Private IP, Authorised networks, Auth Proxy, connectors; Identity: IAM authentication, Built-in users, CMEK keys; Pricing: vCPU and memory hours, Storage and backups, Committed use. Cloud SQL at a glance A managed relational database on Google Cloud: the main building blocks and decisions CloudBrum Cloud decision-support platform CloudBrum PostgreSQL MySQL SQL Server Engines Enterprise Enterprise Plus Data cache Editions Regional HA standby Automatic failover Maintenance windows Availability Read replicas Storage auto-increase Cascading replicas Scale Automated and on-demand Point-in-time recovery Retained backup count Backup Private IP Authorised networks Auth Proxy, connectors Network IAM authentication Built-in users CMEK keys Identity vCPU and memory hours Storage and backups Committed use Pricing Cloud SQL17-point analysis CloudBrum· 17-point cloud service analysis cloudbrum.com
    CloudBrum Cloud SQL at a glance · 17-point analysis Engines PostgreSQL MySQL SQL Server Editions Enterprise Enterprise Plus Data cache Availability Regional HA standby Automatic failover Maintenance windows Scale Read replicas Storage auto-increase Cascading replicas Backup Automated and on-demand Point-in-time recovery Retained backup count Network Private IP Authorised networks Auth Proxy, connectors Identity IAM authentication Built-in users CMEK keys Pricing vCPU and memory hours Storage and backups Committed use CloudBrum · cloudbrum.com

    Free to share. The downloaded image includes the CloudBrum link.

    Key features (summary)

    • Three enginesMySQL, PostgreSQL and SQL Server run as managed instances, with the usual drivers and tools. Each engine has its own version list and limits, so read the page for yours.
    • Two editionsEnterprise is for general use. Enterprise Plus targets heavier workloads with a higher availability commitment, near-zero downtime for planned maintenance, a longer log window for recovery and an optional local SSD data cache.
    • A standby in another zoneTurn on high availability and Cloud SQL keeps a standby instance in a second zone of the same Region. If the primary or its zone fails, the standby takes over automatically and keeps the same IP address.
    • Backups and point-in-time recoveryDaily automated backups, on-demand backups and a continuous log let you restore to a moment you choose, as a new instance or over the existing one.
    • Read replicasAdd replicas in the same Region or another, for read traffic or recovery. A replica can be promoted to a stand-alone instance.
    • Safer ways to connectThe Cloud SQL Auth Proxy and the language connectors use IAM to authorise and TLS to encrypt, so you don’t have to maintain IP allow-lists or client certificates.
    • IAM sign-inWith IAM database authentication, people and service accounts log in with short-lived tokens, and database access follows the same roles as the rest of Google Cloud.
    • Query insightsA built-in tool shows the queries that use the most time and which applications issue them, so slow spots are visible without installing anything.

    Basic concepts

    Instance
    One managed database server, with an engine and version, a machine size, storage and a Region.
    Edition
    Enterprise or Enterprise Plus. It decides the available machine types, the availability commitment, maintenance downtime and some features.
    Machine tier
    The vCPU and memory of the instance, such as db-custom-2-7680 for 2 vCPUs and 7.5 GB. Enterprise Plus uses its own performance-optimised tiers.
    High availability (regional)
    A primary and a standby in two zones of one Region, with the data copied synchronously. Failover is automatic, and the standby doesn’t answer queries.
    Read replica
    An asynchronous copy for read traffic or recovery, in-Region or cross-Region. It lags a little behind and can be promoted.
    Automated backup
    A daily backup that Cloud SQL keeps for a number of copies that you choose (1 to 365).
    Point-in-time recovery
    Uses the backups plus the transaction logs, which are kept for a set number of days, to rebuild the database at a chosen moment.
    Private IP
    An address inside your VPC network, reached through private services access or Private Service Connect, with no route from the internet.
    Authorised networks
    The list of public IP ranges allowed to connect when the instance has a public address.
    Cloud SQL Auth Proxy
    A small program that opens an encrypted, IAM-checked tunnel to the instance, so the application connects to localhost.
    Language connector
    A library (Python, Java, Go, Node.js) that does what the proxy does from inside your code.
    IAM database authentication
    Logging in with an IAM user or service account and a short-lived token instead of a database password.
    Database flag
    An engine setting you change through Cloud SQL, such as max_connections or cloudsql.iam_authentication. Some flags restart the instance.
    Maintenance window
    A weekly slot when updates can be applied, with an optional deny period of up to 90 days during which they’re held back.

    How to create & configure it

    Create a PostgreSQL instance in the Google Cloud console

    1. Pick the project, enable the API and decide on networkingChoose a project with billing, enable the Cloud SQL Admin API, and decide whether the instance gets a private IP. A private IP needs private services access set up on the VPC network first, which means reserving an address range.
    2. Start the create flowOpen SQL, choose Create instance, then PostgreSQL. Give it a name (it can’t be reused for about a week after deletion) and a strong password for the default postgres user, or plan to use IAM sign-in.
    3. Choose the editionPick Enterprise for most applications. Choose Enterprise Plus if you need the higher availability commitment, near-zero maintenance downtime or the data cache, and check that your Region and version offer it.
    4. Choose the Region and the availabilityPick the Region nearest your application (Mumbai asia-south1 or Delhi asia-south2 for India). Choose Multiple zones (highly available) for production, or a single zone for development.
    5. Pick the machine and the storageChoose vCPUs and memory, SSD storage, and turn on automatic storage increases with a limit. Start modest, since you can change the machine later with a short restart.
    6. Configure connectivityUntick Public IP and tick Private IP, selecting the network. If you have to use a public IP, leave authorised networks empty and connect through the Auth Proxy instead of opening a range.
    7. Set up data protectionTurn on automated backups and point-in-time recovery, choose how many backups to keep and how many days of logs, and turn on deletion protection.
    8. Add flags and sign-inSet the flag cloudsql.iam_authentication to on if you want IAM database sign-in, and keep SSL enforcement at Encrypted only.
    9. Connect and testConnect with the Auth Proxy or a language connector from a VM or Cloud Run service in the network, create an application user with limited rights, and test a restore to a new instance before you depend on the backups.

    Tip: the console is good for a first look. For anything shared, define the instance as code (gcloud, Terraform, see the code references) so the network, availability and backup choices are reviewed and repeatable.

    Common issues after configuration

    SymptomLikely causeWhat to check / fix
    Connection times outNo route to the instance, or your address isn’t allowedFor a private IP, check the client is in the VPC (or peered, with routes exported) and that private services access is set up. For a public IP, check the authorised networks, or switch to the Auth Proxy.
    Auth Proxy fails with a 403 or NOT_AUTHORIZED errorThe identity lacks the client role, or the Admin API is offGrant roles/cloudsql.client to the identity running the proxy, enable the Cloud SQL Admin API, and check the instance connection name (project:region:instance) is exact.
    IAM login failsThe flag isn’t on, the role is missing or the database user wasn’t createdSet cloudsql.iam_authentication to on (it restarts the instance), grant roles/cloudsql.instanceUser, and create the IAM user on the instance. For a service account, drop .gserviceaccount.com from the name.
    The server rejects an unencrypted connectionThe instance enforces encrypted connections and the client sent noneConnect with TLS (sslmode=verify-full and the server CA), or go through the Auth Proxy or a connector, which encrypt for you.
    FATAL: sorry, too many clients alreadyMore connections than max_connections, which depends on instance memoryPool connections in the application or with a pooler, close idle ones, and raise the flag or the machine size only if the real load needs it.
    The instance is unreachable for a minute or twoA failover, a maintenance restart or a flag change that needs a restartRetry with backoff in the client, set maintenance windows to quiet hours, and check the operations list for what happened.
    Operation failed because another operation is already in progressCloud SQL runs one administrative operation at a time per instanceWait for the running operation (backup, maintenance or update) to finish, or cancel it if it allows, and then try again.
    The disk is full and writes failStorage auto-increase was off or reached its limitIncrease the storage (it can’t be reduced), find the cause (logs, bloat, temporary files) and turn on auto-increase with a monitored limit.
    Replica lag growsHeavy writes on the primary, or a replica that is too smallMatch the replica’s size to the primary, look for long-running queries on the replica, and watch the replication lag metric.
    Private IP creation fails with a range or peering errorThe allocated range is too small or private services access isn’t connectedReserve a larger internal range, create the private connection to Google services, and try again.
    A deleted instance’s name can’t be reusedCloud SQL holds the name for a while after deletionPick a new name, or include a suffix in automation, so a rebuild doesn’t wait.

    Use cases: when and where to use it

    Good fit

    • Web and mobile app back ends on MySQL, PostgreSQL or SQL Server that want a managed database
    • Applications on Cloud Run, GKE or Compute Engine that need a private, IAM-controlled database connection
    • Lift-and-shift of existing MySQL or PostgreSQL databases with Database Migration Service
    • Read-only copies for reports and analytics refreshes
    • Smaller and mid-sized line-of-business systems that need HA and backups with little effort
    • Development and test databases that can be cloned and deleted

    Consider something else

    Pros: why consider it?

    Why teams choose it

    • Simple to start, and the three engines are ones teams already know
    • Auth Proxy, connectors and IAM sign-in remove most of the connection-security chores
    • High availability, backups and point-in-time recovery are settings, not projects
    • Enterprise Plus offers a higher availability commitment with near-zero planned downtime
    • Clones and read replicas make test copies and reporting easy
    • Fits naturally with Cloud Run, GKE, BigQuery and Database Migration Service

    Trade-offs to weigh

    • A single primary for writes, so write scale is limited by the machine size
    • The standby in a high availability pair can’t serve reads
    • Only one administrative operation can run on an instance at a time
    • No superuser, and only a supported list of extensions and flags
    • Enterprise Plus costs noticeably more per vCPU
    • Private IP needs network groundwork, and mistakes there are hard to see

    Common threats, vulnerabilities & risks

    RiskSeverityWhy it mattersMitigation
    A public IP with wide authorised networksHighOpening a range such as 0.0.0.0/0 puts the database on the internet.Use a private IP, and connect through the Auth Proxy or connectors. Keep authorised networks empty or narrow.
    Shared built-in user passwordsHighThe default admin user can do anything, and passwords end up in config files.Use IAM database authentication, keep the admin password in Secret Manager, and create least-privilege roles.
    A restore that has never been triedHighYou can’t tell how long recovery takes or whether the backups hold what you expect.Clone or restore to a new instance on a schedule, check the data and time it.
    No high availability in productionMediumA zone problem or maintenance means downtime until the instance returns.Turn on regional high availability for production, and practise a manual failover.
    Short log retentionMediumPoint-in-time recovery only reaches as far back as the logs are kept.Set the transaction log days to match the time you’d need to notice a mistake, and keep the backup count higher than that.
    Deleting an instance by mistakeMediumDeletion removes the data and, with it, backups that belong to the instance.Turn on deletion protection, and keep exports or backups in another project.
    Over-broad IAM rolesMediumCloud SQL admin rights can create, delete and export instances.Give people cloudsql.client or instanceUser, keep cloudsql.admin for a small group, and use organisation policies.
    Running out of connections or diskLow–MedBoth stop applications suddenly, and storage can’t be reclaimed.Pool connections, set auto-increase with a limit, and alert on use.
    Unreviewed flags and extensionsLow–MedA flag change can restart the instance or alter behaviour.Keep flags in code, review changes and test them on a clone first.

    Performance optimisation

    • Choose the machine tier from measurements: CPU, memory and cache hit ratio. Memory-heavy databases usually need more RAM per vCPU than the default.
    • Pick SSD storage and size it for the IOPS you need, since throughput and IOPS scale with disk size.
    • Consider Enterprise Plus with the data cache for read-heavy workloads where reads from the persistent disk are the bottleneck.
    • Use connection pooling (in the application, a pooler, or the managed option where offered) when many short-lived clients connect, for example from Cloud Run.
    • Send reporting and read-heavy queries to read replicas, and monitor replica lag.
    • Find slow queries with Query insights, add indexes and check plans before upsizing.
    • Keep the application in the same Region and zone as the primary to keep latency down.
    • Keep transactions short and tune vacuum or purge settings so tables don’t bloat.

    Reduce monthly cost

    FinOps is the habit of managing cloud spend together with engineering. These are the FinOps checks that matter most for Cloud SQL.

    • Use single-zone instances for development and test. Regional high availability roughly doubles the instance cost.
    • Stop non-production instances when nobody is using them. Compute billing pauses, but storage still bills.
    • Prefer the Enterprise edition unless you need what Enterprise Plus adds, since Enterprise Plus costs more per vCPU.
    • Right-size from Cloud Monitoring graphs, and move to a smaller machine when the use is low.
    • Look at committed use discounts for instances that will run for a year or three.
    • Keep the backup count and log retention to what recovery needs, because extra backups cost storage.
    • Delete unused replicas, clones and old exports, which keep billing for storage and compute.
    • Avoid cross-Region traffic between the app and the database, which adds network charges and latency.
    • Turn on storage auto-increase with a limit instead of over-provisioning, remembering that storage can’t shrink.
    • Add labels to instances for owner and environment, and set budgets by label.

    Treat the figures and offers here as illustrations taken from Google's public pages. Edition, machine tier, Region and date all move them, so confirm current numbers first (see Pricing).

    Security optimisation

    • Give instances a private IP, turn off the public IP where you can, and reach the database through the Auth Proxy or a language connector.
    • Set SSL mode to encrypted only, and verify the server certificate in clients that connect directly.
    • Use IAM database authentication for people and service accounts, and keep any built-in user passwords in Secret Manager.
    • Grant roles/cloudsql.client and roles/cloudsql.instanceUser to the identities that need to connect, and keep roles/cloudsql.admin for a small team.
    • Create separate database roles for owners, migrations and applications, and grant only the privileges each needs.
    • Use customer-managed encryption keys (CMEK) where policy requires them, and restrict key access.
    • Wrap the project in VPC Service Controls and organisation policies, for example to require private IP and to restrict Regions.
    • Turn on audit logs (admin and data access where needed) and database logging, and alert on failed logins and flag changes.
    • Turn on deletion protection and keep backups or exports in a separate project.
    • Review authorised networks, flags and users regularly, and manage them in code.

    Governance & compliance

    Guardrails

    • Label rules for instances (owner, environment, data class, cost centre) checked at creation
    • An organisation policy that requires private IP and restricts Regions
    • A shared Terraform module for instances with HA, backups, logging and SSL already set
    • A list of approved engines, versions, editions and machine tiers, with a retirement date for each version

    Continuous checks (organisation policy and Security Command Center)

    • “constraints/sql.restrictPublicIp” to stop instances having public IPs
    • “constraints/sql.restrictAuthorizedNetworks” to block open ranges
    • “constraints/gcp.resourceLocations” to limit where instances can be created
    • Security Command Center findings for public instances, unencrypted connections and missing backups
    • A scheduled report of non-production instances that have run longer than a set time

    Cloud Audit Logs show who changed an instance, Cloud Asset Inventory and Security Command Center track configuration and posture, Dataplex can catalogue data, and the Compliance resource centre holds reports. Duties are divided as usual: Google runs the platform, the patching and the failover machinery, and you are responsible for the data, the roles, the network exposure and how recovery is tested.

    Reduce carbon footprint

    • Match the machine to the load. Spare vCPUs and memory draw power around the clock.
    • Stop development instances outside working hours, and delete clones and replicas after use.
    • Use read replicas only where reads need them.
    • Index and cache so queries read less data and the same instance serves more.
    • Keep backup and log retention to what recovery needs.
    • Pick a Region with lower carbon intensity for work that isn’t tied to a place. Google publishes carbon-free energy percentages for each Region.
    • Carbon Footprint in the Cloud Console reports emissions for your account. Check how it counts Cloud SQL before you quote a number from it.

    Pricing

    Purchase options

    Compute Per vCPU and GB hour

    Billed for the vCPUs and memory of the instance for each hour it runs. Regional high availability doubles it, and Enterprise Plus carries a higher rate.

    Storage Per GB-month

    SSD or HDD storage is billed for what you provision, whether or not it’s full. Auto-increase only adds storage.

    Backups and logs Per GB-month

    Backups and the log archive used for point-in-time recovery are billed by size, so retention settings change the cost.

    Network and extras Varies

    Traffic leaving the Region or going to the internet, read replicas (billed as instances), the data cache and committed use discounts are separate lines.

    What you actually pay for

    • vCPU and memory hours by edition, doubled by regional high availability
    • Storage by type and size
    • Backup and log storage by size and retention
    • Network egress, for example cross-Region replicas or traffic to the internet
    • Read replicas and clones, billed like instances

    Prices depend on the edition, machine, Region and engine, and change over time. Google Cloud has offered new customers trial credits rather than a permanent free database tier, so check the current terms. See the official Cloud SQL pricing page and the Google Cloud Pricing Calculator for current figures, and the Google Cloud Free Program page for what a new account receives.

    Important code references

    The same orders database on Google Cloud: a PostgreSQL 16 instance with a private IP, a standby in another zone, 14 backups with point-in-time recovery and IAM sign-in, plus a read replica and a clone for a restore test. The gcloud and Terraform tabs build it. The Python tab connects with the Cloud SQL connector, and the C# tab goes through the Auth Proxy. Both place an order in a transaction. The project, network and service account names are examples. Private IP needs private services access on the network first (the Terraform tab shows it), and a high availability instance bills from creation, so delete the test instance afterwards.

    # Names are examples. Mumbai is the example Region. Private IP needs private services access on the VPC first:
    #   gcloud compute addresses create google-managed-services-default --global --purpose=VPC_PEERING --prefix-length=16 --network=default
    #   gcloud services vpc-peerings connect --service=servicenetworking.googleapis.com --ranges=google-managed-services-default --network=default
    PROJECT=my-project
    REGION=asia-south1
    APP_SA=orders-app@$PROJECT.iam.gserviceaccount.com
    
    gcloud services enable sqladmin.googleapis.com servicenetworking.googleapis.com --project=$PROJECT
    
    # A private, highly available PostgreSQL 16 instance with IAM sign-in
    gcloud sql instances create orders-db --project=$PROJECT --region=$REGION \
      --database-version=POSTGRES_16 --edition=ENTERPRISE --tier=db-custom-2-7680 \
      --availability-type=REGIONAL \
      --storage-type=SSD --storage-size=100 --storage-auto-increase \
      --network=projects/$PROJECT/global/networks/default --no-assign-ip \
      --ssl-mode=ENCRYPTED_ONLY \
      --backup-start-time=21:00 --retained-backups-count=14 \
      --enable-point-in-time-recovery --retained-transaction-log-days=7 \
      --database-flags=cloudsql.iam_authentication=on \
      --deletion-protection
    
    gcloud sql databases create orders --instance=orders-db --project=$PROJECT
    
    # An IAM-authenticated database user for the application's service account (note: no .gserviceaccount.com)
    gcloud sql users create orders-app@$PROJECT.iam --instance=orders-db --project=$PROJECT --type=cloud_iam_service_account
    gcloud projects add-iam-policy-binding $PROJECT --member=serviceAccount:$APP_SA --role=roles/cloudsql.client
    gcloud projects add-iam-policy-binding $PROJECT --member=serviceAccount:$APP_SA --role=roles/cloudsql.instanceUser
    
    # A read replica for reporting
    gcloud sql instances create orders-db-replica --project=$PROJECT --region=$REGION \
      --master-instance-name=orders-db --tier=db-custom-2-7680
    
    # Practise the restore: clone the instance as it was at a chosen moment (UTC)
    gcloud sql instances clone orders-db orders-db-restore-test --project=$PROJECT \
      --point-in-time=2026-10-29T08:30:00Z
    
    # Clean up the test copy
    gcloud sql instances delete orders-db-restore-test --project=$PROJECT --quiet
    # Assumes the google provider version 5 or later and the default VPC network
    variable "project" { type = string }
    variable "region"  { default = "asia-south1" }
    
    provider "google" {
      project = var.project
      region  = var.region
    }
    
    resource "google_project_service" "services" {
      for_each           = toset(["sqladmin.googleapis.com", "servicenetworking.googleapis.com"])
      service            = each.value
      disable_on_destroy = false
    }
    
    data "google_compute_network" "default" {
      name = "default"
    }
    
    # Private services access: a reserved range plus the private connection to Google's services
    resource "google_compute_global_address" "private_range" {
      name          = "google-managed-services-default"
      purpose       = "VPC_PEERING"
      address_type  = "INTERNAL"
      prefix_length = 16
      network       = data.google_compute_network.default.id
    }
    
    resource "google_service_networking_connection" "private" {
      network                 = data.google_compute_network.default.id
      service                 = "servicenetworking.googleapis.com"
      reserved_peering_ranges = [google_compute_global_address.private_range.name]
      depends_on              = [google_project_service.services]
    }
    
    resource "google_service_account" "app" {
      account_id   = "orders-app"
      display_name = "Orders application"
    }
    
    resource "google_project_iam_member" "app_client" {
      for_each = toset(["roles/cloudsql.client", "roles/cloudsql.instanceUser"])
      project  = var.project
      role     = each.value
      member   = "serviceAccount:${google_service_account.app.email}"
    }
    
    resource "google_sql_database_instance" "orders" {
      name                = "orders-db"
      region              = var.region
      database_version    = "POSTGRES_16"
      deletion_protection = true
    
      settings {
        tier              = "db-custom-2-7680"
        edition           = "ENTERPRISE"
        availability_type = "REGIONAL"
        disk_type         = "PD_SSD"
        disk_size         = 100
        disk_autoresize   = true
    
        backup_configuration {
          enabled                        = true
          start_time                     = "21:00"
          point_in_time_recovery_enabled = true
          transaction_log_retention_days = 7
    
          backup_retention_settings {
            retained_backups = 14
            retention_unit   = "COUNT"
          }
        }
    
        ip_configuration {
          ipv4_enabled    = false
          private_network = data.google_compute_network.default.id
          ssl_mode        = "ENCRYPTED_ONLY"
        }
    
        database_flags {
          name  = "cloudsql.iam_authentication"
          value = "on"
        }
    
        insights_config {
          query_insights_enabled = true
        }
    
        user_labels = { owner = "orders-team" }
      }
    
      depends_on = [google_service_networking_connection.private]
    }
    
    resource "google_sql_database" "orders" {
      name     = "orders"
      instance = google_sql_database_instance.orders.name
    }
    
    # IAM database user for the app (for Postgres the service account name drops ".gserviceaccount.com")
    resource "google_sql_user" "app" {
      name     = trimsuffix(google_service_account.app.email, ".gserviceaccount.com")
      instance = google_sql_database_instance.orders.name
      type     = "CLOUD_IAM_SERVICE_ACCOUNT"
    }
    
    # A read replica for reporting
    resource "google_sql_database_instance" "orders_replica" {
      name                 = "orders-db-replica"
      region               = var.region
      database_version     = "POSTGRES_16"
      master_instance_name = google_sql_database_instance.orders.name
      deletion_protection  = false
    
      settings {
        tier    = "db-custom-2-7680"
        edition = "ENTERPRISE"
    
        ip_configuration {
          ipv4_enabled    = false
          private_network = data.google_compute_network.default.id
        }
      }
    }
    # pip install "cloud-sql-python-connector[pg8000]"
    # Runs as the service account (or your own account with application default credentials). No password is stored.
    import time
    
    import pg8000
    from google.cloud.sql.connector import Connector, IPTypes
    
    INSTANCE = "my-project:asia-south1:orders-db"      # project:region:instance
    DB_USER = "orders-app@my-project.iam"              # the IAM user, without .gserviceaccount.com
    DB_NAME = "orders"
    
    connector = Connector(refresh_strategy="lazy")     # "lazy" suits Cloud Run and other CPU-throttled hosts
    
    
    def connect():
        """The connector checks IAM, encrypts the connection and sends an access token as the password."""
        return connector.connect(
            INSTANCE, "pg8000", user=DB_USER, db=DB_NAME,
            enable_iam_auth=True, ip_type=IPTypes.PRIVATE)
    
    
    def place_order(conn, customer_id, total_cents):
        """Insert one order in a transaction and return its id."""
        cur = conn.cursor()
        try:
            cur.execute(
                "INSERT INTO orders (customer_id, total_cents) VALUES (%s, %s) RETURNING id",
                (customer_id, total_cents))
            order_id = cur.fetchone()[0]
            conn.commit()
            return order_id
        except Exception:
            conn.rollback()
            raise
        finally:
            cur.close()
    
    
    def with_retry(action, attempts=3):
        """Retry on connection failures, which is what a failover or a maintenance restart looks like to the app."""
        for attempt in range(1, attempts + 1):
            conn = None
            try:
                conn = connect()
                return action(conn)
            except (pg8000.exceptions.InterfaceError, OSError):
                if attempt == attempts:
                    raise
                time.sleep(2 * attempt)
            finally:
                if conn is not None:
                    conn.close()
    
    
    if __name__ == "__main__":
        try:
            print("Created order", with_retry(lambda c: place_order(c, 42, 129900)))
        finally:
            connector.close()
    // Program.cs: connect through the Cloud SQL Auth Proxy and insert an order in a transaction
    // NuGet package: Npgsql
    // Start the proxy first (it signs in with IAM and encrypts the connection to the instance):
    //   ./cloud-sql-proxy --private-ip --auto-iam-authn my-project:asia-south1:orders-db
    using Npgsql;
    
    var builder = new NpgsqlConnectionStringBuilder
    {
        Host = "127.0.0.1",                   // the proxy listens here; it handles TLS and the IAM token
        Port = 5432,
        Database = "orders",
        Username = "orders-app@my-project.iam",
        SslMode = SslMode.Disable,            // only the hop to the local proxy is unencrypted
        Timeout = 5
    };
    
    await using var dataSource = NpgsqlDataSource.Create(builder.ConnectionString);
    await using var connection = await dataSource.OpenConnectionAsync();
    await using var transaction = await connection.BeginTransactionAsync();
    
    const string sql = "INSERT INTO orders (customer_id, total_cents) VALUES (@customerId, @totalCents) RETURNING id";
    await using var insert = new NpgsqlCommand(sql, connection, transaction);
    insert.Parameters.AddWithValue("customerId", 42L);
    insert.Parameters.AddWithValue("totalCents", 129900);
    
    var orderId = (long)(await insert.ExecuteScalarAsync())!;
    await transaction.CommitAsync();
    Console.WriteLine($"Created order {orderId}");

    Best videos to explore

    Short walkthrough videos for this service are being prepared. They will appear here and load only when you press play. Until then, follow CloudBrum on YouTube for new videos.

    Introduction to Cloud SQLVideo coming soon · Beginner
    High availability, replicas and backups in Cloud SQLVideo coming soon · Intermediate
    Connecting to Cloud SQL safely: private IP, Auth Proxy, IAMVideo coming soon · Intermediate
    Cloud SQL Enterprise versus Enterprise PlusVideo coming soon · Advanced

    Interview questions

    BasicWhat is Cloud SQL?

    It’s Google Cloud’s managed relational database service for MySQL, PostgreSQL and SQL Server. Google runs the server, applies patches, takes backups and handles failover, and you choose the engine, the machine size, the Region and the settings, and manage the data and users.

    BasicWhat is the difference between the Enterprise and Enterprise Plus editions?

    Enterprise suits general workloads. Enterprise Plus targets heavier or more critical ones, with a higher availability commitment, near-zero downtime for planned maintenance, longer transaction log retention for recovery and an optional local SSD data cache, at a higher price per vCPU. Check which versions and Regions offer it.

    BasicHow does high availability work in Cloud SQL?

    With regional high availability, Cloud SQL runs a standby instance in another zone of the same Region and copies data to it synchronously. If the primary or its zone fails, the standby takes over automatically and keeps the same IP address. The standby doesn’t serve queries, so you add read replicas to scale reads.

    IntermediateHow do you connect an application to Cloud SQL without opening the database to the internet?

    Give the instance a private IP through private services access, and have the application connect from inside the VPC. Use the Cloud SQL Auth Proxy or a language connector, which check IAM permission and encrypt the connection, and sign in with IAM database authentication so no password is stored.

    IntermediateHow do you restore a Cloud SQL database to a moment before a bad change?

    Use point-in-time recovery, which combines the backups with the retained transaction logs. Clone the instance to the chosen time, check that the data is right, and then repoint the application to the clone or copy the data back. How far back you can go depends on the log retention you set, so choose that to match how quickly you’d notice a mistake.

    IntermediateWhat are the limits of a read replica?

    It copies the primary asynchronously, so it can lag and may serve slightly old data. It’s read-only, it’s billed as a separate instance, and promoting it breaks the link to the primary. It’s good for reports and for scaling reads, and it can also serve as part of a disaster recovery plan, especially across Regions.

    AdvancedIAM login to a PostgreSQL instance fails. What do you check?

    Confirm the instance flag cloudsql.iam_authentication is on (changing it restarts the instance), that the database user exists with the IAM type and the right name (for a service account, the email without .gserviceaccount.com), and that the identity has roles/cloudsql.instanceUser and, if it uses the proxy or a connector, roles/cloudsql.client. Then check the client is actually requesting an access token.

    AdvancedDesign the database layer for a service that must survive the loss of a Region.

    Keep the primary in one Region with regional high availability, and add a cross-Region read replica that you can promote. Rehearse the promotion, keep infrastructure code that rebuilds networking and permissions in the second Region, and make the application’s connection settings changeable quickly. Cross-Region replication is asynchronous, so state the RPO honestly, and consider Cloud Spanner if the target is near-zero loss across Regions.

    AdvancedAn application on Cloud Run exhausts the database connections after a traffic spike. What changes do you make?

    Cap each Cloud Run instance’s pool size and its maximum instances so the total stays below max_connections, use a pooler or the managed pooling option, close connections when idle, and cache what you can. Raising the flag or the machine size is a last step, since each connection also costs memory on the server.

    AdvancedYou must upgrade a major PostgreSQL version with little downtime. What is your approach?

    Test first on a clone of production, checking extensions and query plans. Then use Cloud SQL’s in-place major version upgrade in a quiet window, or migrate with Database Migration Service to a new instance and cut over. Take a backup before, expect a restart and a statistics rebuild, and have a rollback plan that points the application back at the old instance.

    Similar or alternative services on other clouds

    CapabilityAWSAzureGoogle Cloud
    ServiceAmazon RDSAzure Database for PostgreSQL, for MySQL and SQL DatabaseCloud SQL
    Higher service tierInstance class families (m, r, x) and Multi-AZ DB clusterMemory Optimized tier and the faster disk typeEnterprise Plus edition
    Failover designMulti-AZ standby in another zoneZone-redundant standbyRegional HA standby in another zone, same IP address
    Connecting privatelyPrivate subnets and security groupsVNet integration and a private DNS zonePrivate IP through private services access, plus the Auth Proxy
    Identity at loginIAM tokensEntra tokensIAM database authentication
    Log window for recoveryBackup retention up to 35 daysRetention 7 to 35 daysLog days 1 to 7 (Enterprise) or up to 35 (Enterprise Plus)
    Copy for testingRestore snapshot or point in time to a new instanceRestore to a new serverClone an instance, optionally to a point in time
    Move a database inAWS Database Migration ServiceAzure Database Migration ServiceDatabase Migration Service

    Cloud SQL is the closest match to a single-writer managed database. When you outgrow one writer, Google points to Cloud Spanner for global scale and AlloyDB for faster PostgreSQL, while Firestore and Bigtable cover non-relational data. Applications that use it often run on Compute Engine or Cloud Run functions.

    Did you find this article helpful?

    Your answer helps us improve this page for the next reader.

    Sources and further reading

    CloudBrum wrote this page in its own words, using the provider’s public documentation listed below as the reference. Features, limits, names and prices change, so confirm anything that matters on the provider’s own pages before you decide.