提交 5b072977 编写于 作者: C Christian Svensson 提交者: Fatih Acet

Support for multiple Gitlab instances

上级 396a1776
......@@ -3,3 +3,4 @@
- Matthias Wirtz [@swiffer](https://gitlab.com/swiffer)
- Amanda Cameron [@AmandaCameron](https://gitlab.com/AmandaCameron)
- Roman Levin [@romanlevin](https://gitlab.com/romanlevin)
- Christian Svensson [@csvn](https://gitlab.com/csvn)
......@@ -46,6 +46,7 @@ To use this extension, you need to create a GitLab Personal Access Token and giv
##### Step 2: Add token to GitLab Workflow Extension
- Open up Command Palette by pressing `Cmd+Shift+P`.
- Search for "GitLab: Set GitLab Personal Access Token" and hit Enter.
- Enter the URL to the Gitlab instance the PAT should apply to and hit Enter.
- Extension will ask for your PAT. Paste your PAT and hit Enter. _It won't be visible and accessible to others._
That's it. 🏁
......@@ -62,6 +63,10 @@ You can start using this extension right away. If your project has a pipeline fo
![https://gitlab.com/fatihacet/gitlab-vscode-extension/raw/master/src/assets/pipeline-actions.png](https://gitlab.com/fatihacet/gitlab-vscode-extension/raw/master/src/assets/pipeline-actions.png)
## Multiple Gitlab instances
To enable Gitlab Workflow extension to work with different Gitlab instances, each token is assigned to a Gitlab instance URL. For the extension to selected the correct token for a specific workspace, the option [`gitlab.instanceUrl`](#configuration-options) can be used. This option can be set in the current workspace's `.vscode/settings.json` file.
## Features in depth
### Advanced Search
......
const vscode = require('vscode');
const opn = require('opn');
const openers = require('./openers');
const statusBar = require('./status_bar');
const tokenInput = require('./token_input');
const gitLabService = require('./gitlab_service');
const tokenService = require('./token_service');
const pipelineActionsPicker = require('./pipeline_actions_picker');
const searchInput = require('./search_input');
const snippetInput = require('./snippet_input');
......@@ -21,8 +19,8 @@ const registerCommands = () => {
const commands = {
'gl.showIssuesAssigedToMe': openers.showIssues,
'gl.showMergeRequestsAssigedToMe': openers.showMergeRequests,
'gl.setToken': tokenInput.showInput.bind(null, context),
'gl.removeToken': tokenInput.removeToken.bind(null, context),
'gl.setToken': tokenInput.showInput,
'gl.removeToken': tokenInput.removeTokenPicker,
'gl.openActiveFile': openers.openActiveFile,
'gl.openCurrentMergeRequest': openers.openCurrentMergeRequest,
'gl.openCreateNewIssue': openers.openCreateNewIssue,
......@@ -45,44 +43,8 @@ const registerCommands = () => {
};
const init = () => {
const token = context.globalState.get('glToken');
if (token) {
gitLabService._setGLToken(token);
statusBar.init(context);
} else {
askForToken();
}
}
const askForToken = () => {
const gs = context.globalState;
if (!gs.get('glToken') && !gs.get('askedForToken')) {
const message = 'GitLab Workflow: Please set GitLab Personal Access Token to setup this extension.';
const setButton = { title: 'Set Token Now', action: 'set' };
const readMore = { title: 'Read More', action: 'more' };
gs.update('askedForToken', true);
vscode.window.showInformationMessage(message, readMore, setButton)
.then((item) => {
if (item) {
const { action } = item;
if (action === 'set') {
vscode.commands.executeCommand('gl.setToken');
} else {
opn('https://gitlab.com/fatihacet/gitlab-vscode-extension#setup');
}
}
});
}
tokenService.init(context);
}
const deactivate = () => {
statusBar.dispose();
};
exports.init = init;
exports.activate = activate;
exports.deactivate = deactivate;
......@@ -2,14 +2,15 @@ const vscode = require('vscode');
const opn = require('opn');
const request = require('request-promise');
const gitService = require('./git_service');
const tokenService = require('./token_service');
const statusBar = require('./status_bar');
let glToken = null;
let branchMR = null;
async function fetch(path, method = 'GET', data = null) {
const { instanceUrl } = vscode.workspace.getConfiguration('gitlab');
const apiRoot = `${instanceUrl}/api/v4`;
const glToken = tokenService.getToken(instanceUrl);
if (!glToken) {
return vscode.window.showInformationMessage('GitLab Workflow: Cannot make request. No token found.');
......@@ -206,14 +207,6 @@ async function validateCIConfig(content) {
return response;
}
/**
* @private
* @param {string} token GL PAT
*/
const _setGLToken = (token) => {
glToken = token;
}
exports.fetchUser = fetchUser;
exports.fetchMyOpenMergeRequests = fetchMyOpenMergeRequests;
exports.fetchOpenMergeRequestForCurrentBranch = fetchOpenMergeRequestForCurrentBranch;
......@@ -223,4 +216,3 @@ exports.handlePipelineAction = handlePipelineAction;
exports.fetchMRIssues = fetchMRIssues;
exports.createSnippet = createSnippet;
exports.validateCIConfig = validateCIConfig;
exports._setGLToken = _setGLToken;
......@@ -4,8 +4,10 @@ const gitLabService = require('./gitlab_service');
let context = null;
let pipelineStatusBarItem = null;
let pipelinesStatusTimer = null;
let mrStatusBarItem = null;
let mrIssueStatusBarItem = null;
let mrStatusTimer = null;
let issue = null;
let mr = null;
const { showIssueLinkOnStatusBar } = vscode.workspace.getConfiguration('gitlab');
......@@ -60,7 +62,7 @@ async function refreshPipelines() {
const initPipelineStatus = () => {
pipelineStatusBarItem = createStatusBarItem('$(info) GitLab: Fetching pipeline...', 'gl.pipelineActions');
setInterval(() => { refreshPipelines() }, 30000);
pipelinesStatusTimer = setInterval(() => { refreshPipelines() }, 30000);
refreshPipelines();
}
......@@ -76,7 +78,7 @@ const initMrStatus = () => {
});
mrStatusBarItem = createStatusBarItem('$(info) GitLab: Finding MR...', cmdName);
setInterval(() => { fetchBranchMr() }, 60000);
mrStatusTimer = setInterval(() => { fetchBranchMr() }, 60000);
fetchBranchMr();
}
......@@ -147,6 +149,16 @@ const dispose = () => {
if (showIssueLinkOnStatusBar) {
mrIssueStatusBarItem.dispose();
}
if (pipelinesStatusTimer) {
clearInterval(pipelinesStatusTimer);
pipelinesStatusTimer = null;
}
if (mrStatusTimer) {
clearInterval(mrStatusTimer);
mrStatusTimer = null;
}
}
exports.init = init;
......
const { URL } = require('url');
const vscode = require('vscode');
const extension = require('./extension');
const tokenService = require('./token_service');
async function showInput() {
const instance = await vscode.window.showInputBox({
ignoreFocusOut: true,
value: 'https://gitlab.com',
placeHolder: 'E.g. https://gitlab.com',
prompt: 'URL to Gitlab instance',
validateInput: urlValidator,
});
async function showInput(context) {
const token = await vscode.window.showInputBox({
ignoreFocusOut: true,
password: true,
placeHolder: 'Paste your GitLab Personal Access Token...',
});
if (token) {
context.globalState.update('glToken', token);
extension.init();
if (instance && token) {
tokenService.setToken(instance, token);
}
}
const removeToken = (context) => {
context.globalState.update('glToken', null);
extension.deactivate();
};
async function removeTokenPicker() {
const instanceUrls = tokenService.getInstanceUrls();
const selectedInstanceUrl = await vscode.window.showQuickPick(instanceUrls, {
ignoreFocusOut: true,
placeHolder: 'Select Gitlab instance for PAT removal',
});
if (selectedInstanceUrl) {
tokenService.setToken(selectedInstanceUrl, undefined);
}
}
const urlValidator = (value) => {
try {
new URL(value);
} catch (_err) {
return `Gitlab instance "${value}" is not a valid URL`;
}
}
exports.showInput = showInput;
exports.removeToken = removeToken;
exports.removeTokenPicker = removeTokenPicker;
const vscode = require('vscode');
const opn = require('opn');
const statusBar = require('./status_bar');
let context = null;
let active = false;
const init = (ctx) => {
context = ctx;
migrateLegacyToken();
askForToken();
updateExtensionStatus();
watchConfigurationChanges();
}
const getToken = (instanceUrl = currentInstanceUrl()) => {
return getGlTokenMap()[instanceUrl];
}
const setToken = (instanceUrl, token) => {
const tokenMap = getGlTokenMap();
if (token) {
tokenMap[instanceUrl] = token;
} else {
delete tokenMap[instanceUrl];
}
context.globalState.update('glTokens', tokenMap);
updateExtensionStatus();
}
const getInstanceUrls = () => {
return Object.keys(getGlTokenMap());
}
const updateExtensionStatus = () => {
const tokenExists = !!getToken();
if (!active && tokenExists) {
statusBar.init(context);
active = true;
} else if (active && !tokenExists) {
statusBar.dispose();
active = false;
}
}
const watchConfigurationChanges = () => {
vscode.workspace.onDidChangeConfiguration(e => {
if (e.affectsConfiguration('gitlab')) {
updateExtensionStatus();
}
});
}
const migrateLegacyToken = () => {
const token = context.globalState.get('glToken');
if (token) {
const instanceUrl = currentInstanceUrl();
if (!getToken(instanceUrl)) {
setToken(instanceUrl, token);
}
context.globalState.update('glToken', null);
}
}
const currentInstanceUrl = () => {
return vscode.workspace.getConfiguration('gitlab').instanceUrl;
}
const getGlTokenMap = () => {
return context.globalState.get('glTokens', {});
}
const askForToken = () => {
if (!getToken() && !context.workspaceState.get('askedForToken')) {
const message = 'GitLab Workflow: Please set GitLab Personal Access Token to setup this extension.';
const setButton = { title: 'Set Token Now', action: 'set' };
const readMore = { title: 'Read More', action: 'more' };
context.workspaceState.update('askedForToken', true);
vscode.window.showInformationMessage(message, readMore, setButton)
.then((item) => {
if (item) {
const { action } = item;
if (action === 'set') {
vscode.commands.executeCommand('gl.setToken');
} else {
opn('https://gitlab.com/fatihacet/gitlab-vscode-extension#setup');
}
}
});
}
}
exports.init = init;
exports.getToken = getToken;
exports.setToken = setToken;
exports.getInstanceUrls = getInstanceUrls;
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册