diff --git a/apps/meteor/app/custom-oauth/index.js b/apps/meteor/app/custom-oauth/index.js deleted file mode 100644 index ca00a734e0d..00000000000 --- a/apps/meteor/app/custom-oauth/index.js +++ /dev/null @@ -1,8 +0,0 @@ -import { Meteor } from 'meteor/meteor'; - -if (Meteor.isClient) { - module.exports = require('./client/custom_oauth_client.js'); -} -if (Meteor.isServer) { - module.exports = require('./server/custom_oauth_server.js'); -} diff --git a/apps/meteor/app/custom-oauth/server/custom_oauth_server.d.ts b/apps/meteor/app/custom-oauth/server/custom_oauth_server.d.ts index e0554f0b609..670b803ebef 100644 --- a/apps/meteor/app/custom-oauth/server/custom_oauth_server.d.ts +++ b/apps/meteor/app/custom-oauth/server/custom_oauth_server.d.ts @@ -2,4 +2,6 @@ export class CustomOAuth { constructor(name: string, options: Record); getIdentity(accessToken: string, query: Record): any; + + configure(options: Record): any; } diff --git a/apps/meteor/app/dolphin/client/index.ts b/apps/meteor/app/dolphin/client/index.ts index 96b9b521322..0cc16f78319 100644 --- a/apps/meteor/app/dolphin/client/index.ts +++ b/apps/meteor/app/dolphin/client/index.ts @@ -1,2 +1,2 @@ -import '../lib/common'; +import './lib'; import './login-button.css'; diff --git a/apps/meteor/app/dolphin/client/lib.ts b/apps/meteor/app/dolphin/client/lib.ts new file mode 100644 index 00000000000..9fa11208d3c --- /dev/null +++ b/apps/meteor/app/dolphin/client/lib.ts @@ -0,0 +1,29 @@ +import { Meteor } from 'meteor/meteor'; +import { Tracker } from 'meteor/tracker'; + +import { settings } from '../../settings/client'; +import { CustomOAuth } from '../../custom-oauth/client/custom_oauth_client'; + +const config = { + serverURL: '', + authorizePath: '/m/oauth2/auth/', + tokenPath: '/m/oauth2/token/', + identityPath: '/m/oauth2/api/me/', + scope: 'basic', + addAutopublishFields: { + forLoggedInUser: ['services.dolphin'], + forOtherUsers: ['services.dolphin.name'], + }, + accessTokenParam: 'access_token', +}; + +const Dolphin = new CustomOAuth('dolphin', config); + +Meteor.startup(() => + Tracker.autorun(function () { + if (settings.get('Accounts_OAuth_Dolphin_URL')) { + config.serverURL = settings.get('Accounts_OAuth_Dolphin_URL'); + return Dolphin.configure(config); + } + }), +); diff --git a/apps/meteor/app/dolphin/lib/common.js b/apps/meteor/app/dolphin/lib/common.js deleted file mode 100644 index f175eeade6b..00000000000 --- a/apps/meteor/app/dolphin/lib/common.js +++ /dev/null @@ -1,63 +0,0 @@ -import { Meteor } from 'meteor/meteor'; -import { Tracker } from 'meteor/tracker'; -import { ServiceConfiguration } from 'meteor/service-configuration'; - -import { settings } from '../../settings'; -import { CustomOAuth } from '../../custom-oauth'; -import { callbacks } from '../../../lib/callbacks'; - -const config = { - serverURL: '', - authorizePath: '/m/oauth2/auth/', - tokenPath: '/m/oauth2/token/', - identityPath: '/m/oauth2/api/me/', - scope: 'basic', - addAutopublishFields: { - forLoggedInUser: ['services.dolphin'], - forOtherUsers: ['services.dolphin.name'], - }, - accessTokenParam: 'access_token', -}; - -const Dolphin = new CustomOAuth('dolphin', config); - -function DolphinOnCreateUser(options, user) { - if (user && user.services && user.services.dolphin && user.services.dolphin.NickName) { - user.username = user.services.dolphin.NickName; - } - return options; -} - -if (Meteor.isServer) { - Meteor.startup(async () => { - settings.watch('Accounts_OAuth_Dolphin_URL', (value) => { - config.serverURL = value; - return Dolphin.configure(config); - }); - - if (settings.get('Accounts_OAuth_Dolphin_URL')) { - const data = { - buttonLabelText: settings.get('Accounts_OAuth_Dolphin_button_label_text'), - buttonColor: settings.get('Accounts_OAuth_Dolphin_button_color'), - buttonLabelColor: settings.get('Accounts_OAuth_Dolphin_button_label_color'), - clientId: settings.get('Accounts_OAuth_Dolphin_id'), - secret: settings.get('Accounts_OAuth_Dolphin_secret'), - serverURL: settings.get('Accounts_OAuth_Dolphin_URL'), - loginStyle: settings.get('Accounts_OAuth_Dolphin_login_style'), - }; - - await ServiceConfiguration.configurations.upsertAsync({ service: 'dolphin' }, { $set: data }); - } - - callbacks.add('beforeCreateUser', DolphinOnCreateUser, callbacks.priority.HIGH, 'dolphin'); - }); -} else { - Meteor.startup(() => - Tracker.autorun(function () { - if (settings.get('Accounts_OAuth_Dolphin_URL')) { - config.serverURL = settings.get('Accounts_OAuth_Dolphin_URL'); - return Dolphin.configure(config); - } - }), - ); -} diff --git a/apps/meteor/app/dolphin/server/index.ts b/apps/meteor/app/dolphin/server/index.ts index e44dbe195ef..cf327e4971b 100644 --- a/apps/meteor/app/dolphin/server/index.ts +++ b/apps/meteor/app/dolphin/server/index.ts @@ -1 +1 @@ -import '../lib/common'; +import './lib'; diff --git a/apps/meteor/app/dolphin/server/lib.ts b/apps/meteor/app/dolphin/server/lib.ts new file mode 100644 index 00000000000..f6693807996 --- /dev/null +++ b/apps/meteor/app/dolphin/server/lib.ts @@ -0,0 +1,52 @@ +import { Meteor } from 'meteor/meteor'; +import { ServiceConfiguration } from 'meteor/service-configuration'; +import type { IUser } from '@rocket.chat/core-typings'; + +import { settings } from '../../settings/server'; +import { CustomOAuth } from '../../custom-oauth/server/custom_oauth_server'; +import { callbacks } from '../../../lib/callbacks'; + +const config = { + serverURL: '', + authorizePath: '/m/oauth2/auth/', + tokenPath: '/m/oauth2/token/', + identityPath: '/m/oauth2/api/me/', + scope: 'basic', + addAutopublishFields: { + forLoggedInUser: ['services.dolphin'], + forOtherUsers: ['services.dolphin.name'], + }, + accessTokenParam: 'access_token', +}; + +const Dolphin = new CustomOAuth('dolphin', config); + +function DolphinOnCreateUser(options: any, user?: IUser) { + if (user?.services?.dolphin?.NickName) { + user.username = user.services.dolphin.NickName; + } + return options; +} + +Meteor.startup(async () => { + settings.watch('Accounts_OAuth_Dolphin_URL', (value) => { + config.serverURL = value; + return Dolphin.configure(config); + }); + + if (settings.get('Accounts_OAuth_Dolphin_URL')) { + const data = { + buttonLabelText: settings.get('Accounts_OAuth_Dolphin_button_label_text'), + buttonColor: settings.get('Accounts_OAuth_Dolphin_button_color'), + buttonLabelColor: settings.get('Accounts_OAuth_Dolphin_button_label_color'), + clientId: settings.get('Accounts_OAuth_Dolphin_id'), + secret: settings.get('Accounts_OAuth_Dolphin_secret'), + serverURL: settings.get('Accounts_OAuth_Dolphin_URL'), + loginStyle: settings.get('Accounts_OAuth_Dolphin_login_style'), + }; + + await ServiceConfiguration.configurations.upsertAsync({ service: 'dolphin' }, { $set: data }); + } + + callbacks.add('beforeCreateUser', DolphinOnCreateUser, callbacks.priority.HIGH, 'dolphin'); +}); diff --git a/apps/meteor/app/drupal/client/index.ts b/apps/meteor/app/drupal/client/index.ts index 96b9b521322..0cc16f78319 100644 --- a/apps/meteor/app/drupal/client/index.ts +++ b/apps/meteor/app/drupal/client/index.ts @@ -1,2 +1,2 @@ -import '../lib/common'; +import './lib'; import './login-button.css'; diff --git a/apps/meteor/app/drupal/lib/common.js b/apps/meteor/app/drupal/client/lib.ts similarity index 61% rename from apps/meteor/app/drupal/lib/common.js rename to apps/meteor/app/drupal/client/lib.ts index 9090b3d75e2..89454e43e6b 100644 --- a/apps/meteor/app/drupal/lib/common.js +++ b/apps/meteor/app/drupal/client/lib.ts @@ -1,13 +1,14 @@ import { Meteor } from 'meteor/meteor'; import { Tracker } from 'meteor/tracker'; +import type { OauthConfig } from '@rocket.chat/core-typings'; -import { settings } from '../../settings'; -import { CustomOAuth } from '../../custom-oauth'; +import { settings } from '../../settings/client'; +import { CustomOAuth } from '../../custom-oauth/client/custom_oauth_client'; // Drupal Server CallBack URL needs to be http(s)://{rocketchat.server}[:port]/_oauth/drupal // In RocketChat -> Administration the URL needs to be http(s)://{drupal.server}/ -const config = { +const config: OauthConfig = { serverURL: '', identityPath: '/oauth2/UserInfo', authorizePath: '/oauth2/authorize', @@ -25,20 +26,11 @@ const config = { const Drupal = new CustomOAuth('drupal', config); -if (Meteor.isServer) { - Meteor.startup(function () { - settings.watch('API_Drupal_URL', function (value) { - config.serverURL = value; +Meteor.startup(function () { + Tracker.autorun(function () { + if (settings.get('API_Drupal_URL')) { + config.serverURL = settings.get('API_Drupal_URL'); Drupal.configure(config); - }); + } }); -} else { - Meteor.startup(function () { - Tracker.autorun(function () { - if (settings.get('API_Drupal_URL')) { - config.serverURL = settings.get('API_Drupal_URL'); - Drupal.configure(config); - } - }); - }); -} +}); diff --git a/apps/meteor/app/drupal/server/index.ts b/apps/meteor/app/drupal/server/index.ts index e44dbe195ef..cf327e4971b 100644 --- a/apps/meteor/app/drupal/server/index.ts +++ b/apps/meteor/app/drupal/server/index.ts @@ -1 +1 @@ -import '../lib/common'; +import './lib'; diff --git a/apps/meteor/app/drupal/server/lib.ts b/apps/meteor/app/drupal/server/lib.ts new file mode 100644 index 00000000000..ca07a8d7390 --- /dev/null +++ b/apps/meteor/app/drupal/server/lib.ts @@ -0,0 +1,33 @@ +import { Meteor } from 'meteor/meteor'; +import type { OauthConfig } from '@rocket.chat/core-typings'; + +import { settings } from '../../settings/server'; +import { CustomOAuth } from '../../custom-oauth/server/custom_oauth_server'; + +// Drupal Server CallBack URL needs to be http(s)://{rocketchat.server}[:port]/_oauth/drupal +// In RocketChat -> Administration the URL needs to be http(s)://{drupal.server}/ + +const config: OauthConfig = { + serverURL: '', + identityPath: '/oauth2/UserInfo', + authorizePath: '/oauth2/authorize', + tokenPath: '/oauth2/token', + scope: 'openid email profile offline_access', + tokenSentVia: 'payload', + usernameField: 'preferred_username', + mergeUsers: true, + addAutopublishFields: { + forLoggedInUser: ['services.drupal'], + forOtherUsers: ['services.drupal.name'], + }, + accessTokenParam: 'access_token', +}; + +const Drupal = new CustomOAuth('drupal', config); + +Meteor.startup(function () { + settings.watch('API_Drupal_URL', function (value) { + config.serverURL = value; + Drupal.configure(config); + }); +}); diff --git a/apps/meteor/app/github-enterprise/client/index.ts b/apps/meteor/app/github-enterprise/client/index.ts index c43a3da658b..7a032388cc0 100644 --- a/apps/meteor/app/github-enterprise/client/index.ts +++ b/apps/meteor/app/github-enterprise/client/index.ts @@ -1,2 +1,2 @@ -import '../lib/common'; +import './lib'; import './github-enterprise-login-button.css'; diff --git a/apps/meteor/app/github-enterprise/lib/common.js b/apps/meteor/app/github-enterprise/client/lib.ts similarity index 57% rename from apps/meteor/app/github-enterprise/lib/common.js rename to apps/meteor/app/github-enterprise/client/lib.ts index b1b07abc6cb..9d9eae61400 100644 --- a/apps/meteor/app/github-enterprise/lib/common.js +++ b/apps/meteor/app/github-enterprise/client/lib.ts @@ -1,13 +1,14 @@ import { Meteor } from 'meteor/meteor'; import { Tracker } from 'meteor/tracker'; +import type { OauthConfig } from '@rocket.chat/core-typings'; -import { CustomOAuth } from '../../custom-oauth'; -import { settings } from '../../settings'; +import { CustomOAuth } from '../../custom-oauth/client/custom_oauth_client'; +import { settings } from '../../settings/client'; // GitHub Enterprise Server CallBack URL needs to be http(s)://{rocketchat.server}[:port]/_oauth/github_enterprise // In RocketChat -> Administration the URL needs to be http(s)://{github.enterprise.server}/ -const config = { +const config: OauthConfig = { serverURL: '', identityPath: '/api/v3/user', authorizePath: '/login/oauth/authorize', @@ -19,21 +20,11 @@ const config = { }; const GitHubEnterprise = new CustomOAuth('github_enterprise', config); - -if (Meteor.isServer) { - Meteor.startup(function () { - settings.watch('API_GitHub_Enterprise_URL', function (value) { - config.serverURL = value; +Meteor.startup(function () { + Tracker.autorun(function () { + if (settings.get('API_GitHub_Enterprise_URL')) { + config.serverURL = settings.get('API_GitHub_Enterprise_URL'); GitHubEnterprise.configure(config); - }); - }); -} else { - Meteor.startup(function () { - Tracker.autorun(function () { - if (settings.get('API_GitHub_Enterprise_URL')) { - config.serverURL = settings.get('API_GitHub_Enterprise_URL'); - GitHubEnterprise.configure(config); - } - }); + } }); -} +}); diff --git a/apps/meteor/app/github-enterprise/server/index.ts b/apps/meteor/app/github-enterprise/server/index.ts index e44dbe195ef..cf327e4971b 100644 --- a/apps/meteor/app/github-enterprise/server/index.ts +++ b/apps/meteor/app/github-enterprise/server/index.ts @@ -1 +1 @@ -import '../lib/common'; +import './lib'; diff --git a/apps/meteor/app/github-enterprise/server/lib.ts b/apps/meteor/app/github-enterprise/server/lib.ts new file mode 100644 index 00000000000..f8adfb841b8 --- /dev/null +++ b/apps/meteor/app/github-enterprise/server/lib.ts @@ -0,0 +1,28 @@ +import { Meteor } from 'meteor/meteor'; +import type { OauthConfig } from '@rocket.chat/core-typings'; + +import { CustomOAuth } from '../../custom-oauth/server/custom_oauth_server'; +import { settings } from '../../settings/server'; + +// GitHub Enterprise Server CallBack URL needs to be http(s)://{rocketchat.server}[:port]/_oauth/github_enterprise +// In RocketChat -> Administration the URL needs to be http(s)://{github.enterprise.server}/ + +const config: OauthConfig = { + serverURL: '', + identityPath: '/api/v3/user', + authorizePath: '/login/oauth/authorize', + tokenPath: '/login/oauth/access_token', + addAutopublishFields: { + forLoggedInUser: ['services.github-enterprise'], + forOtherUsers: ['services.github-enterprise.username'], + }, +}; + +const GitHubEnterprise = new CustomOAuth('github_enterprise', config); + +Meteor.startup(function () { + settings.watch('API_GitHub_Enterprise_URL', function (value) { + config.serverURL = value; + GitHubEnterprise.configure(config); + }); +}); diff --git a/apps/meteor/app/gitlab/client/index.ts b/apps/meteor/app/gitlab/client/index.ts index 4af49250347..e73c8e10b1a 100644 --- a/apps/meteor/app/gitlab/client/index.ts +++ b/apps/meteor/app/gitlab/client/index.ts @@ -1,2 +1,2 @@ -import '../lib/common'; +import './lib'; import './gitlab-login-button.css'; diff --git a/apps/meteor/app/gitlab/client/lib.ts b/apps/meteor/app/gitlab/client/lib.ts new file mode 100644 index 00000000000..7c0644b6721 --- /dev/null +++ b/apps/meteor/app/gitlab/client/lib.ts @@ -0,0 +1,44 @@ +import { Meteor } from 'meteor/meteor'; +import { Tracker } from 'meteor/tracker'; +import type { OauthConfig } from '@rocket.chat/core-typings'; + +import { settings } from '../../settings/client'; +import { CustomOAuth } from '../../custom-oauth/client/custom_oauth_client'; + +const config: OauthConfig = { + serverURL: 'https://gitlab.com', + identityPath: '/api/v4/user', + scope: 'read_user', + mergeUsers: false, + addAutopublishFields: { + forLoggedInUser: ['services.gitlab'], + forOtherUsers: ['services.gitlab.username'], + }, + accessTokenParam: 'access_token', +}; + +const Gitlab = new CustomOAuth('gitlab', config); + +Meteor.startup(function () { + Tracker.autorun(function () { + let anyChange = false; + if (settings.get('API_Gitlab_URL')) { + config.serverURL = settings.get('API_Gitlab_URL').trim().replace(/\/*$/, ''); + anyChange = true; + } + + if (settings.get('Accounts_OAuth_Gitlab_identity_path')) { + config.identityPath = settings.get('Accounts_OAuth_Gitlab_identity_path').trim() || config.identityPath; + anyChange = true; + } + + if (settings.get('Accounts_OAuth_Gitlab_merge_users')) { + config.mergeUsers = true; + anyChange = true; + } + + if (anyChange) { + Gitlab.configure(config); + } + }); +}); diff --git a/apps/meteor/app/gitlab/lib/common.js b/apps/meteor/app/gitlab/lib/common.js deleted file mode 100644 index 5e3bd994184..00000000000 --- a/apps/meteor/app/gitlab/lib/common.js +++ /dev/null @@ -1,57 +0,0 @@ -import { Meteor } from 'meteor/meteor'; -import { Tracker } from 'meteor/tracker'; -import _ from 'underscore'; - -import { settings } from '../../settings'; -import { CustomOAuth } from '../../custom-oauth'; - -const config = { - serverURL: 'https://gitlab.com', - identityPath: '/api/v4/user', - scope: 'read_user', - mergeUsers: false, - addAutopublishFields: { - forLoggedInUser: ['services.gitlab'], - forOtherUsers: ['services.gitlab.username'], - }, - accessTokenParam: 'access_token', -}; - -const Gitlab = new CustomOAuth('gitlab', config); - -if (Meteor.isServer) { - Meteor.startup(function () { - const updateConfig = _.debounce(() => { - config.serverURL = settings.get('API_Gitlab_URL').trim().replace(/\/*$/, '') || config.serverURL; - config.identityPath = settings.get('Accounts_OAuth_Gitlab_identity_path') || config.identityPath; - config.mergeUsers = Boolean(settings.get('Accounts_OAuth_Gitlab_merge_users')); - Gitlab.configure(config); - }, 300); - - settings.watchMultiple(['API_Gitlab_URL', 'Accounts_OAuth_Gitlab_identity_path', 'Accounts_OAuth_Gitlab_merge_users'], updateConfig); - }); -} else { - Meteor.startup(function () { - Tracker.autorun(function () { - let anyChange = false; - if (settings.get('API_Gitlab_URL')) { - config.serverURL = settings.get('API_Gitlab_URL').trim().replace(/\/*$/, ''); - anyChange = true; - } - - if (settings.get('Accounts_OAuth_Gitlab_identity_path')) { - config.identityPath = settings.get('Accounts_OAuth_Gitlab_identity_path').trim() || config.identityPath; - anyChange = true; - } - - if (settings.get('Accounts_OAuth_Gitlab_merge_users')) { - config.mergeUsers = true; - anyChange = true; - } - - if (anyChange) { - Gitlab.configure(config); - } - }); - }); -} diff --git a/apps/meteor/app/gitlab/server/index.ts b/apps/meteor/app/gitlab/server/index.ts index e44dbe195ef..cf327e4971b 100644 --- a/apps/meteor/app/gitlab/server/index.ts +++ b/apps/meteor/app/gitlab/server/index.ts @@ -1 +1 @@ -import '../lib/common'; +import './lib'; diff --git a/apps/meteor/app/gitlab/server/lib.ts b/apps/meteor/app/gitlab/server/lib.ts new file mode 100644 index 00000000000..0800b654b65 --- /dev/null +++ b/apps/meteor/app/gitlab/server/lib.ts @@ -0,0 +1,31 @@ +import { Meteor } from 'meteor/meteor'; +import _ from 'underscore'; +import type { OauthConfig } from '@rocket.chat/core-typings'; + +import { settings } from '../../settings/server'; +import { CustomOAuth } from '../../custom-oauth/server/custom_oauth_server'; + +const config: OauthConfig = { + serverURL: 'https://gitlab.com', + identityPath: '/api/v4/user', + scope: 'read_user', + mergeUsers: false, + addAutopublishFields: { + forLoggedInUser: ['services.gitlab'], + forOtherUsers: ['services.gitlab.username'], + }, + accessTokenParam: 'access_token', +}; + +const Gitlab = new CustomOAuth('gitlab', config); + +Meteor.startup(function () { + const updateConfig = _.debounce(() => { + config.serverURL = settings.get('API_Gitlab_URL').trim().replace(/\/*$/, '') || config.serverURL; + config.identityPath = settings.get('Accounts_OAuth_Gitlab_identity_path') || config.identityPath; + config.mergeUsers = Boolean(settings.get('Accounts_OAuth_Gitlab_merge_users')); + Gitlab.configure(config); + }, 300); + + settings.watchMultiple(['API_Gitlab_URL', 'Accounts_OAuth_Gitlab_identity_path', 'Accounts_OAuth_Gitlab_merge_users'], updateConfig); +}); diff --git a/apps/meteor/app/nextcloud/client/index.ts b/apps/meteor/app/nextcloud/client/index.ts index e44dbe195ef..cf327e4971b 100644 --- a/apps/meteor/app/nextcloud/client/index.ts +++ b/apps/meteor/app/nextcloud/client/index.ts @@ -1 +1 @@ -import '../lib/common'; +import './lib'; diff --git a/apps/meteor/app/nextcloud/client/lib.ts b/apps/meteor/app/nextcloud/client/lib.ts new file mode 100644 index 00000000000..f3562a3c258 --- /dev/null +++ b/apps/meteor/app/nextcloud/client/lib.ts @@ -0,0 +1,40 @@ +import { Meteor } from 'meteor/meteor'; +import { Tracker } from 'meteor/tracker'; +import _ from 'underscore'; +import type { OauthConfig } from '@rocket.chat/core-typings'; + +import { settings } from '../../settings/client'; +import { CustomOAuth } from '../../custom-oauth/client/custom_oauth_client'; + +const config: OauthConfig = { + serverURL: '', + tokenPath: '/index.php/apps/oauth2/api/v1/token', + tokenSentVia: 'header', + authorizePath: '/index.php/apps/oauth2/authorize', + identityPath: '/ocs/v2.php/cloud/user?format=json', + scope: 'openid', + addAutopublishFields: { + forLoggedInUser: ['services.nextcloud'], + forOtherUsers: ['services.nextcloud.name'], + }, +}; + +const Nextcloud = new CustomOAuth('nextcloud', config); + +const fillServerURL = _.debounce((): void => { + const nextcloudURL = settings.get('Accounts_OAuth_Nextcloud_URL'); + if (!nextcloudURL) { + if (nextcloudURL === undefined) { + return fillServerURL(); + } + return; + } + config.serverURL = nextcloudURL.trim().replace(/\/*$/, ''); + return Nextcloud.configure(config); +}, 100); + +Meteor.startup(function () { + Tracker.autorun(function () { + return fillServerURL(); + }); +}); diff --git a/apps/meteor/app/nextcloud/lib/common.js b/apps/meteor/app/nextcloud/lib/common.js deleted file mode 100644 index 5943f21388c..00000000000 --- a/apps/meteor/app/nextcloud/lib/common.js +++ /dev/null @@ -1,46 +0,0 @@ -import { Meteor } from 'meteor/meteor'; -import { Tracker } from 'meteor/tracker'; -import _ from 'underscore'; - -import { settings } from '../../settings'; -import { CustomOAuth } from '../../custom-oauth'; - -const config = { - serverURL: '', - tokenPath: '/index.php/apps/oauth2/api/v1/token', - tokenSentVia: 'header', - authorizePath: '/index.php/apps/oauth2/authorize', - identityPath: '/ocs/v2.php/cloud/user?format=json', - scope: 'openid', - addAutopublishFields: { - forLoggedInUser: ['services.nextcloud'], - forOtherUsers: ['services.nextcloud.name'], - }, -}; - -const Nextcloud = new CustomOAuth('nextcloud', config); - -const fillServerURL = _.debounce( - () => { - const nextcloudURL = settings.get('Accounts_OAuth_Nextcloud_URL'); - if (!nextcloudURL) { - if (nextcloudURL === undefined) { - return fillServerURL(); - } - return; - } - config.serverURL = nextcloudURL.trim().replace(/\/*$/, ''); - return Nextcloud.configure(config); - }, - Meteor.isServer ? 1000 : 100, -); - -Meteor.startup(function () { - if (Meteor.isServer) { - settings.watch('Accounts_OAuth_Nextcloud_URL', () => fillServerURL()); - } else { - Tracker.autorun(function () { - return fillServerURL(); - }); - } -}); diff --git a/apps/meteor/app/nextcloud/server/index.ts b/apps/meteor/app/nextcloud/server/index.ts index 9bc28dcb60a..732ad0a2f4a 100644 --- a/apps/meteor/app/nextcloud/server/index.ts +++ b/apps/meteor/app/nextcloud/server/index.ts @@ -1,2 +1,2 @@ -import '../lib/common'; +import './lib'; import './addWebdavServer'; diff --git a/apps/meteor/app/nextcloud/server/lib.ts b/apps/meteor/app/nextcloud/server/lib.ts new file mode 100644 index 00000000000..5f2830b5dd4 --- /dev/null +++ b/apps/meteor/app/nextcloud/server/lib.ts @@ -0,0 +1,37 @@ +import { Meteor } from 'meteor/meteor'; +import _ from 'underscore'; +import type { OauthConfig } from '@rocket.chat/core-typings'; + +import { settings } from '../../settings/server'; +import { CustomOAuth } from '../../custom-oauth/server/custom_oauth_server'; + +const config: OauthConfig = { + serverURL: '', + tokenPath: '/index.php/apps/oauth2/api/v1/token', + tokenSentVia: 'header', + authorizePath: '/index.php/apps/oauth2/authorize', + identityPath: '/ocs/v2.php/cloud/user?format=json', + scope: 'openid', + addAutopublishFields: { + forLoggedInUser: ['services.nextcloud'], + forOtherUsers: ['services.nextcloud.name'], + }, +}; + +const Nextcloud = new CustomOAuth('nextcloud', config); + +const fillServerURL = _.debounce((): void => { + const nextcloudURL = settings.get('Accounts_OAuth_Nextcloud_URL'); + if (!nextcloudURL) { + if (nextcloudURL === undefined) { + return fillServerURL(); + } + return; + } + config.serverURL = nextcloudURL.trim().replace(/\/*$/, ''); + return Nextcloud.configure(config); +}, 1000); + +Meteor.startup(function () { + settings.watch('Accounts_OAuth_Nextcloud_URL', () => fillServerURL()); +}); diff --git a/apps/meteor/app/tokenpass/client/index.ts b/apps/meteor/app/tokenpass/client/index.ts index e44dbe195ef..cf327e4971b 100644 --- a/apps/meteor/app/tokenpass/client/index.ts +++ b/apps/meteor/app/tokenpass/client/index.ts @@ -1 +1 @@ -import '../lib/common'; +import './lib'; diff --git a/apps/meteor/app/tokenpass/lib/common.js b/apps/meteor/app/tokenpass/client/lib.ts similarity index 53% rename from apps/meteor/app/tokenpass/lib/common.js rename to apps/meteor/app/tokenpass/client/lib.ts index 46e9f0151e7..90164c81f3f 100644 --- a/apps/meteor/app/tokenpass/lib/common.js +++ b/apps/meteor/app/tokenpass/client/lib.ts @@ -1,10 +1,11 @@ import { Meteor } from 'meteor/meteor'; import { Tracker } from 'meteor/tracker'; +import type { OauthConfig } from '@rocket.chat/core-typings'; -import { settings } from '../../settings'; -import { CustomOAuth } from '../../custom-oauth'; +import { settings } from '../../settings/client'; +import { CustomOAuth } from '../../custom-oauth/client/custom_oauth_client'; -const config = { +const config: OauthConfig = { serverURL: '', identityPath: '/oauth/user', authorizePath: '/oauth/authorize', @@ -22,20 +23,11 @@ const config = { const Tokenpass = new CustomOAuth('tokenpass', config); -if (Meteor.isServer) { - Meteor.startup(function () { - settings.watch('API_Tokenpass_URL', function (value) { - config.serverURL = value; +Meteor.startup(function () { + Tracker.autorun(function () { + if (settings.get('API_Tokenpass_URL')) { + config.serverURL = settings.get('API_Tokenpass_URL'); Tokenpass.configure(config); - }); + } }); -} else { - Meteor.startup(function () { - Tracker.autorun(function () { - if (settings.get('API_Tokenpass_URL')) { - config.serverURL = settings.get('API_Tokenpass_URL'); - Tokenpass.configure(config); - } - }); - }); -} +}); diff --git a/apps/meteor/app/tokenpass/server/index.ts b/apps/meteor/app/tokenpass/server/index.ts index e44dbe195ef..cf327e4971b 100644 --- a/apps/meteor/app/tokenpass/server/index.ts +++ b/apps/meteor/app/tokenpass/server/index.ts @@ -1 +1 @@ -import '../lib/common'; +import './lib'; diff --git a/apps/meteor/app/tokenpass/server/lib.ts b/apps/meteor/app/tokenpass/server/lib.ts new file mode 100644 index 00000000000..1ced83aa300 --- /dev/null +++ b/apps/meteor/app/tokenpass/server/lib.ts @@ -0,0 +1,30 @@ +import { Meteor } from 'meteor/meteor'; +import type { OauthConfig } from '@rocket.chat/core-typings'; + +import { settings } from '../../settings/server'; +import { CustomOAuth } from '../../custom-oauth/server/custom_oauth_server'; + +const config: OauthConfig = { + serverURL: '', + identityPath: '/oauth/user', + authorizePath: '/oauth/authorize', + tokenPath: '/oauth/access-token', + scope: 'user', + tokenSentVia: 'payload', + usernameField: 'username', + mergeUsers: true, + addAutopublishFields: { + forLoggedInUser: ['services.tokenpass'], + forOtherUsers: ['services.tokenpass.name'], + }, + accessTokenParam: 'access_token', +}; + +const Tokenpass = new CustomOAuth('tokenpass', config); + +Meteor.startup(function () { + settings.watch('API_Tokenpass_URL', function (value) { + config.serverURL = value; + Tokenpass.configure(config); + }); +}); diff --git a/apps/meteor/app/wordpress/client/index.ts b/apps/meteor/app/wordpress/client/index.ts index 9763e2bec33..555f9f19df3 100644 --- a/apps/meteor/app/wordpress/client/index.ts +++ b/apps/meteor/app/wordpress/client/index.ts @@ -1,2 +1,2 @@ -import '../lib/common'; +import './lib'; import './wordpress-login-button.css'; diff --git a/apps/meteor/app/wordpress/client/lib.ts b/apps/meteor/app/wordpress/client/lib.ts new file mode 100644 index 00000000000..9d5e063bf25 --- /dev/null +++ b/apps/meteor/app/wordpress/client/lib.ts @@ -0,0 +1,80 @@ +import { Meteor } from 'meteor/meteor'; +import { Tracker } from 'meteor/tracker'; +import _ from 'underscore'; +import type { OauthConfig } from '@rocket.chat/core-typings'; + +import { settings } from '../../settings/client'; +import { CustomOAuth } from '../../custom-oauth/client/custom_oauth_client'; + +const config: OauthConfig = { + serverURL: '', + identityPath: '/oauth/me', + + addAutopublishFields: { + forLoggedInUser: ['services.wordpress'], + forOtherUsers: ['services.wordpress.user_login'], + }, + accessTokenParam: 'access_token', +}; + +const WordPress = new CustomOAuth('wordpress', config); + +const fillSettings = _.debounce(async (): Promise => { + config.serverURL = settings.get('API_Wordpress_URL'); + if (!config.serverURL) { + if (config.serverURL === undefined) { + return fillSettings(); + } + return; + } + + delete config.identityPath; + delete config.identityTokenSentVia; + delete config.authorizePath; + delete config.tokenPath; + delete config.scope; + + const serverType = settings.get('Accounts_OAuth_Wordpress_server_type'); + switch (serverType) { + case 'custom': + if (settings.get('Accounts_OAuth_Wordpress_identity_path')) { + config.identityPath = settings.get('Accounts_OAuth_Wordpress_identity_path'); + } + + if (settings.get('Accounts_OAuth_Wordpress_identity_token_sent_via')) { + config.identityTokenSentVia = settings.get('Accounts_OAuth_Wordpress_identity_token_sent_via'); + } + + if (settings.get('Accounts_OAuth_Wordpress_token_path')) { + config.tokenPath = settings.get('Accounts_OAuth_Wordpress_token_path'); + } + + if (settings.get('Accounts_OAuth_Wordpress_authorize_path')) { + config.authorizePath = settings.get('Accounts_OAuth_Wordpress_authorize_path'); + } + + if (settings.get('Accounts_OAuth_Wordpress_scope')) { + config.scope = settings.get('Accounts_OAuth_Wordpress_scope'); + } + break; + case 'wordpress-com': + config.identityPath = 'https://public-api.wordpress.com/rest/v1/me'; + config.identityTokenSentVia = 'header'; + config.authorizePath = 'https://public-api.wordpress.com/oauth2/authorize'; + config.tokenPath = 'https://public-api.wordpress.com/oauth2/token'; + config.scope = 'auth'; + break; + default: + config.identityPath = '/oauth/me'; + break; + } + + const result = WordPress.configure(config); + return result; +}, 100); + +Meteor.startup(function () { + return Tracker.autorun(function () { + return fillSettings(); + }); +}); diff --git a/apps/meteor/app/wordpress/lib/common.js b/apps/meteor/app/wordpress/lib/common.js deleted file mode 100644 index 767ab26bc5a..00000000000 --- a/apps/meteor/app/wordpress/lib/common.js +++ /dev/null @@ -1,107 +0,0 @@ -import { Meteor } from 'meteor/meteor'; -import { Tracker } from 'meteor/tracker'; -import { ServiceConfiguration } from 'meteor/service-configuration'; -import _ from 'underscore'; - -import { settings } from '../../settings'; -import { CustomOAuth } from '../../custom-oauth'; - -const config = { - serverURL: '', - identityPath: '/oauth/me', - - addAutopublishFields: { - forLoggedInUser: ['services.wordpress'], - forOtherUsers: ['services.wordpress.user_login'], - }, - accessTokenParam: 'access_token', -}; - -const WordPress = new CustomOAuth('wordpress', config); - -const fillSettings = _.debounce( - async () => { - config.serverURL = settings.get('API_Wordpress_URL'); - if (!config.serverURL) { - if (config.serverURL === undefined) { - return fillSettings(); - } - return; - } - - delete config.identityPath; - delete config.identityTokenSentVia; - delete config.authorizePath; - delete config.tokenPath; - delete config.scope; - - const serverType = settings.get('Accounts_OAuth_Wordpress_server_type'); - switch (serverType) { - case 'custom': - if (settings.get('Accounts_OAuth_Wordpress_identity_path')) { - config.identityPath = settings.get('Accounts_OAuth_Wordpress_identity_path'); - } - - if (settings.get('Accounts_OAuth_Wordpress_identity_token_sent_via')) { - config.identityTokenSentVia = settings.get('Accounts_OAuth_Wordpress_identity_token_sent_via'); - } - - if (settings.get('Accounts_OAuth_Wordpress_token_path')) { - config.tokenPath = settings.get('Accounts_OAuth_Wordpress_token_path'); - } - - if (settings.get('Accounts_OAuth_Wordpress_authorize_path')) { - config.authorizePath = settings.get('Accounts_OAuth_Wordpress_authorize_path'); - } - - if (settings.get('Accounts_OAuth_Wordpress_scope')) { - config.scope = settings.get('Accounts_OAuth_Wordpress_scope'); - } - break; - case 'wordpress-com': - config.identityPath = 'https://public-api.wordpress.com/rest/v1/me'; - config.identityTokenSentVia = 'header'; - config.authorizePath = 'https://public-api.wordpress.com/oauth2/authorize'; - config.tokenPath = 'https://public-api.wordpress.com/oauth2/token'; - config.scope = 'auth'; - break; - default: - config.identityPath = '/oauth/me'; - break; - } - - const result = WordPress.configure(config); - if (Meteor.isServer) { - const enabled = settings.get('Accounts_OAuth_Wordpress'); - if (enabled) { - await ServiceConfiguration.configurations.upsertAsync( - { - service: 'wordpress', - }, - { - $set: config, - }, - ); - } else { - await ServiceConfiguration.configurations.removeAsync({ - service: 'wordpress', - }); - } - } - - return result; - }, - Meteor.isServer ? 1000 : 100, -); - -if (Meteor.isServer) { - Meteor.startup(function () { - return settings.watchByRegex(/(API\_Wordpress\_URL)?(Accounts\_OAuth\_Wordpress\_)?/, () => fillSettings()); - }); -} else { - Meteor.startup(function () { - return Tracker.autorun(function () { - return fillSettings(); - }); - }); -} diff --git a/apps/meteor/app/wordpress/server/index.ts b/apps/meteor/app/wordpress/server/index.ts index e44dbe195ef..cf327e4971b 100644 --- a/apps/meteor/app/wordpress/server/index.ts +++ b/apps/meteor/app/wordpress/server/index.ts @@ -1 +1 @@ -import '../lib/common'; +import './lib'; diff --git a/apps/meteor/app/wordpress/server/lib.ts b/apps/meteor/app/wordpress/server/lib.ts new file mode 100644 index 00000000000..b1eb87ed6c4 --- /dev/null +++ b/apps/meteor/app/wordpress/server/lib.ts @@ -0,0 +1,94 @@ +import { Meteor } from 'meteor/meteor'; +import { ServiceConfiguration } from 'meteor/service-configuration'; +import _ from 'underscore'; +import type { OauthConfig } from '@rocket.chat/core-typings'; + +import { settings } from '../../settings/server'; +import { CustomOAuth } from '../../custom-oauth/server/custom_oauth_server'; + +const config: OauthConfig = { + serverURL: '', + identityPath: '/oauth/me', + + addAutopublishFields: { + forLoggedInUser: ['services.wordpress'], + forOtherUsers: ['services.wordpress.user_login'], + }, + accessTokenParam: 'access_token', +}; + +const WordPress = new CustomOAuth('wordpress', config); + +const fillSettings = _.debounce(async (): Promise => { + config.serverURL = settings.get('API_Wordpress_URL'); + if (!config.serverURL) { + if (config.serverURL === undefined) { + return fillSettings(); + } + return; + } + + delete config.identityPath; + delete config.identityTokenSentVia; + delete config.authorizePath; + delete config.tokenPath; + delete config.scope; + + const serverType = settings.get('Accounts_OAuth_Wordpress_server_type'); + switch (serverType) { + case 'custom': + if (settings.get('Accounts_OAuth_Wordpress_identity_path')) { + config.identityPath = settings.get('Accounts_OAuth_Wordpress_identity_path'); + } + + if (settings.get('Accounts_OAuth_Wordpress_identity_token_sent_via')) { + config.identityTokenSentVia = settings.get('Accounts_OAuth_Wordpress_identity_token_sent_via'); + } + + if (settings.get('Accounts_OAuth_Wordpress_token_path')) { + config.tokenPath = settings.get('Accounts_OAuth_Wordpress_token_path'); + } + + if (settings.get('Accounts_OAuth_Wordpress_authorize_path')) { + config.authorizePath = settings.get('Accounts_OAuth_Wordpress_authorize_path'); + } + + if (settings.get('Accounts_OAuth_Wordpress_scope')) { + config.scope = settings.get('Accounts_OAuth_Wordpress_scope'); + } + break; + case 'wordpress-com': + config.identityPath = 'https://public-api.wordpress.com/rest/v1/me'; + config.identityTokenSentVia = 'header'; + config.authorizePath = 'https://public-api.wordpress.com/oauth2/authorize'; + config.tokenPath = 'https://public-api.wordpress.com/oauth2/token'; + config.scope = 'auth'; + break; + default: + config.identityPath = '/oauth/me'; + break; + } + + const result = WordPress.configure(config); + const enabled = settings.get('Accounts_OAuth_Wordpress'); + if (enabled) { + await ServiceConfiguration.configurations.upsertAsync( + { + service: 'wordpress', + }, + { + $set: config, + }, + ); + } else { + await ServiceConfiguration.configurations.removeAsync({ + service: 'wordpress', + }); + } + + return result; +}, 1000); + +Meteor.startup(function () { + return settings.watchByRegex(/(API\_Wordpress\_URL)?(Accounts\_OAuth\_Wordpress\_)?/, () => fillSettings()); +}); diff --git a/packages/core-typings/src/ICustomOAuthConfig.ts b/packages/core-typings/src/ICustomOAuthConfig.ts new file mode 100644 index 00000000000..dfbddc5ce2d --- /dev/null +++ b/packages/core-typings/src/ICustomOAuthConfig.ts @@ -0,0 +1,16 @@ +export type OauthConfig = { + serverURL?: string; + identityPath?: string; + addAutopublishFields: { + forLoggedInUser: string[]; + forOtherUsers: string[]; + }; + accessTokenParam?: string; + identityTokenSentVia?: string; + authorizePath?: string; + tokenPath?: string; + scope?: string; + tokenSentVia?: string; + usernameField?: string; + mergeUsers?: boolean; +}; diff --git a/packages/core-typings/src/IUser.ts b/packages/core-typings/src/IUser.ts index 7f378f38d9a..72335fae61b 100644 --- a/packages/core-typings/src/IUser.ts +++ b/packages/core-typings/src/IUser.ts @@ -92,6 +92,9 @@ export interface IUserServices { refreshToken: string; serverURL: string; }; + dolphin?: { + NickName?: string; + }; } export interface IUserEmail { diff --git a/packages/core-typings/src/index.ts b/packages/core-typings/src/index.ts index ab68f219ed3..5ca27fa4d33 100644 --- a/packages/core-typings/src/index.ts +++ b/packages/core-typings/src/index.ts @@ -130,3 +130,4 @@ export * from './AppsTokens'; export * from './ILivechatUnitMonitor'; export * from './migrations/IControl'; +export * from './ICustomOAuthConfig';