diff --git a/lerna.json b/lerna.json index 7564ea387c..ff7e9cbe6f 100644 --- a/lerna.json +++ b/lerna.json @@ -1,5 +1,5 @@ { - "version": "1.0.46-alpha.3", + "version": "1.0.46-alpha.7", "npmClient": "yarn", "packages": [ "packages/*" diff --git a/packages/backend-core/package.json b/packages/backend-core/package.json index c4f7dd1ae8..762c58f880 100644 --- a/packages/backend-core/package.json +++ b/packages/backend-core/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/backend-core", - "version": "1.0.46-alpha.3", + "version": "1.0.46-alpha.7", "description": "Budibase backend core libraries used in server and worker", "main": "src/index.js", "author": "Budibase", diff --git a/packages/backend-core/src/constants.js b/packages/backend-core/src/constants.js index 604acb3540..559dc0e6b2 100644 --- a/packages/backend-core/src/constants.js +++ b/packages/backend-core/src/constants.js @@ -7,8 +7,8 @@ exports.Cookies = { CurrentApp: "budibase:currentapp", Auth: "budibase:auth", Init: "budibase:init", + DatasourceAuth: "budibase:datasourceauth", OIDC_CONFIG: "budibase:oidc:config", - RETURN_URL: "budibase:returnurl", } exports.Headers = { diff --git a/packages/backend-core/src/middleware/index.js b/packages/backend-core/src/middleware/index.js index f4231461af..0d01fb3952 100644 --- a/packages/backend-core/src/middleware/index.js +++ b/packages/backend-core/src/middleware/index.js @@ -7,6 +7,7 @@ const authenticated = require("./authenticated") const auditLog = require("./auditLog") const tenancy = require("./tenancy") const appTenancy = require("./appTenancy") +const datasourceGoogle = require("./passport/datasource/google") const csrf = require("./csrf") module.exports = { @@ -19,5 +20,8 @@ module.exports = { tenancy, appTenancy, authError, + datasource: { + google: datasourceGoogle, + }, csrf, } diff --git a/packages/backend-core/src/middleware/passport/datasource/google.js b/packages/backend-core/src/middleware/passport/datasource/google.js new file mode 100644 index 0000000000..bfc2e4a61e --- /dev/null +++ b/packages/backend-core/src/middleware/passport/datasource/google.js @@ -0,0 +1,76 @@ +const { getScopedConfig } = require("../../../db/utils") +const { getGlobalDB } = require("../../../tenancy") +const google = require("../google") +const { Configs, Cookies } = require("../../../constants") +const { clearCookie, getCookie } = require("../../../utils") +const { getDB } = require("../../../db") + +async function preAuth(passport, ctx, next) { + const db = getGlobalDB() + // get the relevant config + const config = await getScopedConfig(db, { + type: Configs.GOOGLE, + workspace: ctx.query.workspace, + }) + const publicConfig = await getScopedConfig(db, { + type: Configs.SETTINGS, + }) + let callbackUrl = `${publicConfig.platformUrl}/api/global/auth/datasource/google/callback` + const strategy = await google.strategyFactory(config, callbackUrl) + + if (!ctx.query.appId || !ctx.query.datasourceId) { + ctx.throw(400, "appId and datasourceId query params not present.") + } + + return passport.authenticate(strategy, { + scope: ["profile", "email", "https://www.googleapis.com/auth/spreadsheets"], + accessType: "offline", + prompt: "consent", + })(ctx, next) +} + +async function postAuth(passport, ctx, next) { + const db = getGlobalDB() + + const config = await getScopedConfig(db, { + type: Configs.GOOGLE, + workspace: ctx.query.workspace, + }) + + const publicConfig = await getScopedConfig(db, { + type: Configs.SETTINGS, + }) + + let callbackUrl = `${publicConfig.platformUrl}/api/global/auth/datasource/google/callback` + const strategy = await google.strategyFactory( + config, + callbackUrl, + (accessToken, refreshToken, profile, done) => { + clearCookie(ctx, Cookies.DatasourceAuth) + done(null, { accessToken, refreshToken }) + } + ) + + const authStateCookie = getCookie(ctx, Cookies.DatasourceAuth) + + return passport.authenticate( + strategy, + { successRedirect: "/", failureRedirect: "/error" }, + async (err, tokens) => { + // update the DB for the datasource with all the user info + const db = getDB(authStateCookie.appId) + const datasource = await db.get(authStateCookie.datasourceId) + if (!datasource.config) { + datasource.config = {} + } + datasource.config.auth = { type: "google", ...tokens } + await db.put(datasource) + ctx.redirect( + `/builder/app/${authStateCookie.appId}/data/datasource/${authStateCookie.datasourceId}` + ) + } + )(ctx, next) +} + +exports.preAuth = preAuth +exports.postAuth = postAuth diff --git a/packages/backend-core/src/utils.js b/packages/backend-core/src/utils.js index 85dd32946f..8c00f2a8b8 100644 --- a/packages/backend-core/src/utils.js +++ b/packages/backend-core/src/utils.js @@ -96,12 +96,7 @@ exports.getCookie = (ctx, name) => { * @param {string|object} value The value of cookie which will be set. * @param {object} opts options like whether to sign. */ -exports.setCookie = ( - ctx, - value, - name = "builder", - opts = { sign: true, requestDomain: false } -) => { +exports.setCookie = (ctx, value, name = "builder", opts = { sign: true }) => { if (value && opts && opts.sign) { value = jwt.sign(value, options.secretOrKey) } @@ -113,7 +108,7 @@ exports.setCookie = ( overwrite: true, } - if (environment.COOKIE_DOMAIN && !opts.requestDomain) { + if (environment.COOKIE_DOMAIN) { config.domain = environment.COOKIE_DOMAIN } diff --git a/packages/backend-core/yarn.lock b/packages/backend-core/yarn.lock index f28f2f932f..fc70e3d6a1 100644 --- a/packages/backend-core/yarn.lock +++ b/packages/backend-core/yarn.lock @@ -3410,9 +3410,9 @@ node-fetch@2.6.0: integrity sha512-8dG4H5ujfvFiqDmVu9fQ5bOHUC15JMjMY/Zumv26oOvvVJjM67KF8koCWIabKQ1GJIa9r2mMZscBq/TbdOcmNA== node-fetch@^2.6.1: - version "2.6.6" - resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.6.6.tgz#1751a7c01834e8e1697758732e9efb6eeadfaf89" - integrity sha512-Z8/6vRlTUChSdIgMa51jxQ4lrw/Jy5SOW10ObaA47/RElsAN2c5Pn8bTgFGWn/ibwzXTE8qwr1Yzx28vsecXEA== + version "2.6.7" + resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.6.7.tgz#24de9fba827e3b4ae44dc8b20256a379160052ad" + integrity sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ== dependencies: whatwg-url "^5.0.0" diff --git a/packages/bbui/package.json b/packages/bbui/package.json index ecc5bf5a1f..94649bff92 100644 --- a/packages/bbui/package.json +++ b/packages/bbui/package.json @@ -1,7 +1,7 @@ { "name": "@budibase/bbui", "description": "A UI solution used in the different Budibase projects.", - "version": "1.0.46-alpha.3", + "version": "1.0.46-alpha.7", "license": "MPL-2.0", "svelte": "src/index.js", "module": "dist/bbui.es.js", diff --git a/packages/bbui/src/Form/Core/Dropzone.svelte b/packages/bbui/src/Form/Core/Dropzone.svelte index f7fed78b70..6b8022a36c 100644 --- a/packages/bbui/src/Form/Core/Dropzone.svelte +++ b/packages/bbui/src/Form/Core/Dropzone.svelte @@ -147,7 +147,9 @@ {:else}
Sign in with Google
+