Terhubung menggunakan Cloud SQL Language Connectors

Konektor Cloud SQL adalah library yang menyediakan enkripsi dan otorisasi berbasis Identity and Access Management (IAM) saat terhubung ke instance Cloud SQL. Klien tidak dapat menyediakan jalur jaringan ke instance Cloud SQL jika belum ada.

Cara lain untuk terhubung ke instance Cloud SQL mencakup menggunakan klien database atau Proxy Auth Cloud SQL. Lihat halaman Tentang opsi koneksi untuk mengetahui informasi selengkapnya tentang cara terhubung ke instance Cloud SQL.

Halaman ini membahas Konektor Cloud SQL berikut:

  • Konektor Java Cloud SQL
  • Konektor Python Cloud SQL (Buka di Colab)
  • Konektor Go Cloud SQL
  • Konektor Node.js Cloud SQL

Manfaat

Menggunakan konektor Cloud SQL memberikan manfaat berikut:

  • Otorisasi IAM: Menggunakan izin IAM untuk mengontrol siapa atau apa yang dapat terhubung ke instance Cloud SQL Anda.
  • Kepraktisan: Menghapus persyaratan untuk mengelola sertifikat SSL, mengonfigurasi aturan firewall, atau mengaktifkan jaringan yang diizinkan.

Sebelum memulai

  • Aktifkan Cloud SQL Admin API.

    Mengaktifkan API

  • Buat instance Cloud SQL, termasuk mengonfigurasi pengguna default.

    Untuk mengetahui informasi selengkapnya tentang cara membuat instance, lihat Membuat instance.

    Untuk mengetahui informasi selengkapnya tentang cara mengonfigurasi pengguna default, lihat Menyetel sandi untuk akun pengguna default.

  • Konfigurasi peran dan izin yang diperlukan untuk terhubung ke instance Cloud SQL.

Penyiapan

Java

Konektor Java Cloud SQL adalah library yang memberikan otorisasi dan enkripsi berbasis IAM saat terhubung ke instance Cloud SQL. Kode ini tidak dapat menyediakan jalur jaringan ke instance Cloud SQL jika belum ada.

Penginstalan

Guna mengetahui petunjuk tentang cara mem-build dan menggunakan driver untuk JDBC dan R2DBC dengan Konektor Java Cloud SQL, lihat link berikut:

Untuk contoh library ini yang digunakan dalam konteks aplikasi, lihat aplikasi sampel ini.

Authentication

Library ini menggunakan Kredensial Default Aplikasi untuk mengautentikasi koneksi ke server Cloud SQL.

Untuk mengaktifkan kredensial secara lokal, gunakan perintah gcloud berikut:

    gcloud auth application-default login
    

Hubungkan dengan Intellij

Untuk menghubungkan IntelliJ ke instance Cloud SQL Anda, Anda akan perlu untuk menambahkan library sebagai jar dengan dependensi di bagian File Tambahan pada halaman setelan driver. Misalnya, fat jar bawaan dapat ditemukan di halaman Rilis Konektor Java Cloud SQL untuk tujuan ini.

Python

Konektor Python Cloud SQL adalah library yang dapat digunakan bersama driver database agar pengguna dengan izin yang memadai dapat terhubung ke database Cloud SQL tanpa harus memasukkan IP ke daftar yang diizinkan secara manual atau mengelola sertifikat SSL.

Untuk contoh interaktif penggunaan Konektor Python Cloud SQL, buka notebook Konektor Python Cloud SQL.

Driver yang saat ini didukung untuk SQL Server adalah pytds .

Penginstalan

Untuk menginstal rilis terbaru, ikuti petunjuk ini.

Authentication

Library ini menggunakan Kredensial Default Aplikasi untuk mengautentikasi koneksi ke server Cloud SQL.

Untuk mengaktifkan kredensial secara lokal, gunakan perintah gcloud berikut:

    gcloud auth application-default login
    

Go

Konektor Go Cloud SQL adalah konektor Cloud SQL yang dirancang untuk digunakan dengan bahasa Go. Untuk meningkatkan keamanan, konektor ini menggunakan enkripsi TLS 1.3 yang tangguh dan diautentikasi secara manual antara konektor klien dan proxy sisi server, terlepas dari protokol database.

Penginstalan

Anda dapat menginstal repo ini dengan go get:

    go get cloud.google.com/go/cloudsqlconn
    

Node.js

Node.js Connector adalah library yang dirancang untuk digunakan bersama runtime Node.js yang memungkinkan Anda untuk terhubung dengan aman ke instance Cloud SQL Anda.

Penginstalan

Anda dapat menginstal library dengan npm install:

    npm install @google-cloud/cloud-sql-connector
    

Penggunaan

Java

Untuk menemukan cuplikan ini dalam konteks aplikasi web, lihat README pada GitHub.


import com.zaxxer.hikari.HikariConfig;
import com.zaxxer.hikari.HikariDataSource;
import javax.sql.DataSource;

public class ConnectorConnectionPoolFactory extends ConnectionPoolFactory {

  // Note: Saving credentials in environment variables is convenient, but not
  // secure - consider a more secure solution such as
  // Cloud Secret Manager (https://cloud.google.com/secret-manager) to help
  // keep secrets safe.
  private static final String INSTANCE_CONNECTION_NAME =
      System.getenv("INSTANCE_CONNECTION_NAME");
  private static final String DB_USER = System.getenv("DB_USER");
  private static final String DB_PASS = System.getenv("DB_PASS");
  private static final String DB_NAME = System.getenv("DB_NAME");

  public static DataSource createConnectionPool() {
    // The configuration object specifies behaviors for the connection pool.
    HikariConfig config = new HikariConfig();

    // The following is equivalent to setting the config options below:
    // jdbc:sqlserver://;user=<DB_USER>;password=<DB_PASS>;databaseName=<DB_NAME>;
    // socketFactoryClass=com.google.cloud.sql.sqlserver.SocketFactory;
    // socketFactoryConstructorArg=<INSTANCE_CONNECTION_NAME>

    // See the link below for more info on building a JDBC URL for the Cloud SQL JDBC Socket Factory
    // https://github.com/GoogleCloudPlatform/cloud-sql-jdbc-socket-factory#creating-the-jdbc-url

    // Configure which instance and what database user to connect with.
    config
        .setDataSourceClassName("com.microsoft.sqlserver.jdbc.SQLServerDataSource");
    config.setUsername(DB_USER); // e.g. "root", "sqlserver"
    config.setPassword(DB_PASS); // e.g. "my-password"
    config.addDataSourceProperty("databaseName", DB_NAME);

    config.addDataSourceProperty("socketFactoryClass",
        "com.google.cloud.sql.sqlserver.SocketFactory");
    config.addDataSourceProperty("socketFactoryConstructorArg", INSTANCE_CONNECTION_NAME);

    // The Java Connector provides SSL encryption, so it should be disabled
    // at the driver level.
    config.addDataSourceProperty("encrypt", "false");

    // ... Specify additional connection properties here.
    // ...

    // Initialize the connection pool using the configuration object.
    return new HikariDataSource(config);
  }
}

Python

Lihat Cara menggunakan Konektor ini untuk petunjuk mendetail tentang menggunakan library. Lihat contoh kode pengujian koneksi di GitHub.

import os

from google.cloud.sql.connector import Connector, IPTypes
import pytds

import sqlalchemy

def connect_with_connector() -> sqlalchemy.engine.base.Engine:
    """
    Initializes a connection pool for a Cloud SQL instance of SQL Server.

    Uses the Cloud SQL Python Connector package.
    """
    # Note: Saving credentials in environment variables is convenient, but not
    # secure - consider a more secure solution such as
    # Cloud Secret Manager (https://cloud.google.com/secret-manager) to help
    # keep secrets safe.

    instance_connection_name = os.environ[
        "INSTANCE_CONNECTION_NAME"
    ]  # e.g. 'project:region:instance'
    db_user = os.environ.get("DB_USER", "")  # e.g. 'my-db-user'
    db_pass = os.environ["DB_PASS"]  # e.g. 'my-db-password'
    db_name = os.environ["DB_NAME"]  # e.g. 'my-database'

    ip_type = IPTypes.PRIVATE if os.environ.get("PRIVATE_IP") else IPTypes.PUBLIC

    connector = Connector(ip_type)

    connect_args = {}
    # If your SQL Server instance requires SSL, you need to download the CA
    # certificate for your instance and include cafile={path to downloaded
    # certificate} and validate_host=False. This is a workaround for a known issue.
    if os.environ.get("DB_ROOT_CERT"):  # e.g. '/path/to/my/server-ca.pem'
        connect_args = {
            "cafile": os.environ["DB_ROOT_CERT"],
            "validate_host": False,
        }

    def getconn() -> pytds.Connection:
        conn = connector.connect(
            instance_connection_name,
            "pytds",
            user=db_user,
            password=db_pass,
            db=db_name,
            **connect_args
        )
        return conn

    pool = sqlalchemy.create_engine(
        "mssql+pytds://",
        creator=getconn,
        # ...
    )
    return pool

Go

Lihat Penggunaan untuk mengetahui petunjuk mendetail tentang cara menggunakan library. Lihat contoh kode pengujian koneksi di GitHub.

package cloudsql

import (
	"context"
	"database/sql"
	"fmt"
	"log"
	"net"
	"os"

	"cloud.google.com/go/cloudsqlconn"
	mssql "github.com/denisenkom/go-mssqldb"
)

type csqlDialer struct {
	dialer     *cloudsqlconn.Dialer
	connName   string
	usePrivate bool
}

// DialContext adheres to the mssql.Dialer interface.
func (c *csqlDialer) DialContext(ctx context.Context, network, addr string) (net.Conn, error) {
	var opts []cloudsqlconn.DialOption
	if c.usePrivate {
		opts = append(opts, cloudsqlconn.WithPrivateIP())
	}
	return c.dialer.Dial(ctx, c.connName, opts...)
}

func connectWithConnector() (*sql.DB, error) {
	mustGetenv := func(k string) string {
		v := os.Getenv(k)
		if v == "" {
			log.Fatalf("Fatal Error in connect_connector.go: %s environment variable not set.\n", k)
		}
		return v
	}
	// Note: Saving credentials in environment variables is convenient, but not
	// secure - consider a more secure solution such as
	// Cloud Secret Manager (https://cloud.google.com/secret-manager) to help
	// keep secrets safe.
	var (
		dbUser                 = mustGetenv("DB_USER")                  // e.g. 'my-db-user'
		dbPwd                  = mustGetenv("DB_PASS")                  // e.g. 'my-db-password'
		dbName                 = mustGetenv("DB_NAME")                  // e.g. 'my-database'
		instanceConnectionName = mustGetenv("INSTANCE_CONNECTION_NAME") // e.g. 'project:region:instance'
		usePrivate             = os.Getenv("PRIVATE_IP")
	)

	dbURI := fmt.Sprintf("user id=%s;password=%s;database=%s;", dbUser, dbPwd, dbName)
	c, err := mssql.NewConnector(dbURI)
	if err != nil {
		return nil, fmt.Errorf("mssql.NewConnector: %w", err)
	}
	dialer, err := cloudsqlconn.NewDialer(context.Background())
	if err != nil {
		return nil, fmt.Errorf("cloudsqlconn.NewDailer: %w", err)
	}
	c.Dialer = &csqlDialer{
		dialer:     dialer,
		connName:   instanceConnectionName,
		usePrivate: usePrivate != "",
	}

	dbPool := sql.OpenDB(c)
	if err != nil {
		return nil, fmt.Errorf("sql.Open: %w", err)
	}
	return dbPool, nil
}

Node.js

Untuk petunjuk mendetail tentang penggunaan library, lihat Penggunaan.

const {Connection} = require('tedious');
const {Connector} = require('@google-cloud/cloud-sql-connector');

// In case the PRIVATE_IP environment variable is defined then we set
// the ipType=PRIVATE for the new connector instance, otherwise defaults
// to public ip type.
const getIpType = () =>
  process.env.PRIVATE_IP === '1' || process.env.PRIVATE_IP === 'true'
    ? 'PRIVATE'
    : 'PUBLIC';

// connectWithConnector initializes a TCP connection
// to a Cloud SQL instance of SQL Server.
const connectWithConnector = async config => {
  // Note: Saving credentials in environment variables is convenient, but not
  // secure - consider a more secure solution such as
  // Cloud Secret Manager (https://cloud.google.com/secret-manager) to help
  // keep secrets safe.
  const connector = new Connector();
  const clientOpts = await connector.getTediousOptions({
    instanceConnectionName: process.env.INSTANCE_CONNECTION_NAME,
    ipType: getIpType(),
  });
  const dbConfig = {
    // Please note that the `server` property here is not used and is only
    // defined due to a bug in the tedious driver
    // (ref: https://github.com/tediousjs/tedious/issues/1541)
    // With that in mind, do not try to change this value since it will have no
    // impact in how the connector works, this sample will be updated to remove
    // this property declaration as soon as the tedious driver bug is fixed
    server: '0.0.0.0', // e.g. '127.0.0.1'
    authentication: {
      type: 'default',
      options: {
        userName: process.env.DB_USER, // e.g. 'my-db-user'
        password: process.env.DB_PASS, // e.g. 'my-db-password'
      },
    },
    options: {
      ...clientOpts,
      // Please note that the `port` property here is not used and is only
      // defined due to a bug in the tedious driver
      // (ref: https://github.com/tediousjs/tedious/issues/1541)
      // With that in mind, do not try to change this value since it will have
      // no impact in how the connector works, this sample will be updated to
      // remove this property declaration as soon as the tedious driver bug is
      // fixed
      port: 9999,
      database: process.env.DB_NAME, // e.g. 'my-database'
      useColumnNames: true,
    },
    // ... Specify additional properties here.
    ...config,
  };

  // Establish a connection to the database.
  return new Connection(dbConfig);
};

Memecahkan masalah

Versi driver

Pastikan Anda menggunakan versi terbaru Konektor Cloud SQL dan driver database Anda untuk menghindari ketidakcocokan. Beberapa versi driver lama tidak didukung

Jalur koneksi

Konektor Cloud SQL memberikan otorisasi untuk koneksi, tetapi tidak menyediakan jalur baru ke konektivitas. Misalnya, agar dapat terhubung ke instance Cloud SQL menggunakan alamat IP Pribadi, aplikasi Anda harus sudah memiliki akses VPC.

Men-debug masalah koneksi

Untuk mendapatkan bantuan tambahan terkait masalah koneksi, lihat halaman Memecahkan masalah dan Men-debug masalah koneksi.

Langkah selanjutnya