From f1f0798d303f73f0b8583458d7b0315770610b39 Mon Sep 17 00:00:00 2001 From: 0fatal <72899968+0fatal@users.noreply.github.com> Date: Thu, 4 Jan 2024 17:50:11 +0800 Subject: [PATCH] fix(runtime): wait for db ready (#1774) --- runtimes/nodejs/src/db.ts | 25 ++++++++++++++++++++++--- runtimes/nodejs/src/handler/router.ts | 9 ++++++++- 2 files changed, 30 insertions(+), 4 deletions(-) diff --git a/runtimes/nodejs/src/db.ts b/runtimes/nodejs/src/db.ts index 0b3f50f043..e2386fd465 100644 --- a/runtimes/nodejs/src/db.ts +++ b/runtimes/nodejs/src/db.ts @@ -6,6 +6,7 @@ import { MongoAccessor } from 'database-proxy' import Config from './config' import { MongoClient } from 'mongodb' +import { logger } from './support/logger' /** * Database Management @@ -29,9 +30,27 @@ export class DatabaseAgent { return this.client.db() } - static initialize() { - this._client = new MongoClient(Config.DB_URI) - return this._client.connect() + static async initialize() { + const client = new MongoClient(Config.DB_URI) + + let retryDelay = 1000 // 1s + const maxDelay = 30 * 1000 // 30s + + while (true) { + try { + this._client = await client.connect() + logger.info('db connected') + return this._client + } catch (error) { + if (retryDelay > maxDelay) { + retryDelay = 1000 + logger.warn('connect db failed, try again...') + } + + await new Promise((resolve) => setTimeout(resolve, retryDelay)) + retryDelay *= 2 + } + } } /** diff --git a/runtimes/nodejs/src/handler/router.ts b/runtimes/nodejs/src/handler/router.ts index be5d084b76..425aeb43fa 100644 --- a/runtimes/nodejs/src/handler/router.ts +++ b/runtimes/nodejs/src/handler/router.ts @@ -12,6 +12,7 @@ import { handleDatabaseProxy } from './db-proxy' import { handlePackageTypings } from './typings' import { generateUUID } from '../support/utils' import { handleInvokeFunction } from './invoke' +import { DatabaseAgent } from '../db' /** * multer uploader config @@ -36,7 +37,13 @@ export const router = Router() router.post('/proxy/:policy', handleDatabaseProxy) router.get('/_/typing/package', handlePackageTypings) -router.get('/_/healthz', (_req, res) => res.status(200).send('ok')) +router.get('/_/healthz', (_req, res) => { + if (DatabaseAgent.client) { + res.status(200).send('ok') + } else { + res.status(503).send('db is not ready') + } +}) /** * Invoke cloud function through HTTP request.