1- import * as cloudSqlAdminClient from "../gcp/cloudsql/cloudsqladmin" ;
2- import * as utils from "../utils" ;
31import * as clc from "colorette" ;
4- import { grantRolesToCloudSqlServiceAccount } from "./checkIam" ;
2+
3+ import * as cloudSqlAdminClient from "../gcp/cloudsql/cloudsqladmin" ;
54import { Instance } from "../gcp/cloudsql/types" ;
6- import { promiseWithSpinner } from "../utils" ;
75import { logger } from "../logger" ;
8- import { freeTrialTermsLink , checkFreeTrialInstanceUsed } from "./freeTrial" ;
6+ import { grantRolesToCloudSqlServiceAccount } from "./checkIam" ;
7+ import { checkFreeTrialInstanceUsed , freeTrialTermsLink } from "./freeTrial" ;
8+ import { promiseWithSpinner } from "../utils" ;
9+ import { trackGA4 } from "../track" ;
10+ import * as utils from "../utils" ;
911
1012const GOOGLE_ML_INTEGRATION_ROLE = "roles/aiplatform.user" ;
1113
14+ type SetupStats = {
15+ action : "get" | "update" | "create" ;
16+ databaseVersion ?: string ;
17+ dataconnectLabel ?: cloudSqlAdminClient . DataConnectLabel ;
18+ } ;
19+
1220/** Sets up a Cloud SQL instance, database and its permissions. */
1321export async function setupCloudSql ( args : {
1422 projectId : string ;
1523 location : string ;
1624 instanceId : string ;
1725 databaseId : string ;
1826 requireGoogleMlIntegration : boolean ;
27+ source : "init" | "mcp_init" | "deploy" ;
1928 dryRun ?: boolean ;
2029} ) : Promise < void > {
21- await upsertInstance ( { ...args } ) ;
2230 const { projectId, instanceId, requireGoogleMlIntegration, dryRun } = args ;
31+
32+ const startTime = Date . now ( ) ;
33+ const stats : SetupStats = { action : "get" } ;
34+ let success = false ;
35+ try {
36+ await upsertInstance ( stats , { ...args } ) ;
37+ success = true ;
38+ } finally {
39+ if ( ! dryRun ) {
40+ await trackGA4 (
41+ "dataconnect_cloud_sql" ,
42+ {
43+ source : args . source ,
44+ action : success ? stats . action : `${ stats . action } _error` ,
45+ location : args . location ,
46+ enable_google_ml_integration : args . requireGoogleMlIntegration . toString ( ) ,
47+ database_version : stats . databaseVersion ?. toLowerCase ( ) || "unknown" ,
48+ dataconnect_label : stats . dataconnectLabel || "unknown" ,
49+ } ,
50+ Date . now ( ) - startTime ,
51+ ) ;
52+ }
53+ }
54+
2355 if ( requireGoogleMlIntegration && ! dryRun ) {
2456 await grantRolesToCloudSqlServiceAccount ( projectId , instanceId , [ GOOGLE_ML_INTEGRATION_ROLE ] ) ;
2557 }
2658}
2759
28- async function upsertInstance ( args : {
29- projectId : string ;
30- location : string ;
31- instanceId : string ;
32- databaseId : string ;
33- requireGoogleMlIntegration : boolean ;
34- dryRun ?: boolean ;
35- } ) : Promise < void > {
60+ async function upsertInstance (
61+ stats : SetupStats ,
62+ args : {
63+ projectId : string ;
64+ location : string ;
65+ instanceId : string ;
66+ databaseId : string ;
67+ requireGoogleMlIntegration : boolean ;
68+ dryRun ?: boolean ;
69+ } ,
70+ ) : Promise < void > {
3671 const { projectId, instanceId, requireGoogleMlIntegration, dryRun } = args ;
3772 try {
3873 const existingInstance = await cloudSqlAdminClient . getInstance ( projectId , instanceId ) ;
3974 utils . logLabeledBullet (
4075 "dataconnect" ,
4176 `Found existing Cloud SQL instance ${ clc . bold ( instanceId ) } .` ,
4277 ) ;
78+ stats . databaseVersion = existingInstance . databaseVersion ;
79+ stats . dataconnectLabel = existingInstance . settings ?. userLabels ?. [ "firebase-data-connect" ] as
80+ | cloudSqlAdminClient . DataConnectLabel
81+ | undefined ;
82+
4383 const why = getUpdateReason ( existingInstance , requireGoogleMlIntegration ) ;
4484 if ( why ) {
4585 if ( dryRun ) {
@@ -55,6 +95,7 @@ async function upsertInstance(args: {
5595 `Cloud SQL instance ${ clc . bold ( instanceId ) } settings are not compatible with Firebase Data Connect. ` +
5696 why ,
5797 ) ;
98+ stats . action = "update" ;
5899 await promiseWithSpinner (
59100 ( ) =>
60101 cloudSqlAdminClient . updateInstanceForDataConnect (
@@ -71,7 +112,11 @@ async function upsertInstance(args: {
71112 throw err ;
72113 }
73114 // Cloud SQL instance is not found, start its creation.
74- await createInstance ( { ...args } ) ;
115+ stats . action = "create" ;
116+ stats . databaseVersion = cloudSqlAdminClient . DEFAULT_DATABASE_VERSION ;
117+ const freeTrialUsed = await checkFreeTrialInstanceUsed ( projectId ) ;
118+ stats . dataconnectLabel = freeTrialUsed ? "nt" : "ft" ;
119+ await createInstance ( { ...args , freeTrialLabel : stats . dataconnectLabel } ) ;
75120 }
76121}
77122
@@ -80,10 +125,11 @@ async function createInstance(args: {
80125 location : string ;
81126 instanceId : string ;
82127 requireGoogleMlIntegration : boolean ;
128+ freeTrialLabel : cloudSqlAdminClient . DataConnectLabel ;
83129 dryRun ?: boolean ;
84130} ) : Promise < void > {
85- const { projectId, location, instanceId, requireGoogleMlIntegration, dryRun } = args ;
86- const freeTrialUsed = await checkFreeTrialInstanceUsed ( projectId ) ;
131+ const { projectId, location, instanceId, requireGoogleMlIntegration, dryRun, freeTrialLabel } =
132+ args ;
87133 if ( dryRun ) {
88134 utils . logLabeledBullet (
89135 "dataconnect" ,
@@ -95,11 +141,11 @@ async function createInstance(args: {
95141 location,
96142 instanceId,
97143 enableGoogleMlIntegration : requireGoogleMlIntegration ,
98- freeTrial : ! freeTrialUsed ,
144+ freeTrialLabel ,
99145 } ) ;
100146 utils . logLabeledBullet (
101147 "dataconnect" ,
102- cloudSQLBeingCreated ( projectId , instanceId , ! freeTrialUsed ) ,
148+ cloudSQLBeingCreated ( projectId , instanceId , freeTrialLabel === "ft" ) ,
103149 ) ;
104150 }
105151}
0 commit comments