Compare commits
No commits in common. "main" and "test" have entirely different histories.
6 changed files with 136 additions and 366 deletions
1
.gitignore
vendored
1
.gitignore
vendored
|
|
@ -1,4 +1,3 @@
|
|||
node_modules
|
||||
.vscode-test/
|
||||
*.vsix
|
||||
.vscode/bookmarks.json
|
||||
68
CHANGELOG.md
68
CHANGELOG.md
|
|
@ -1,71 +1,9 @@
|
|||
# Change Log
|
||||
|
||||
## [Unreleased] <sub><sup><sub>_(not ordered)_</sub></sup></sub>
|
||||
All notable changes to the "dwm-git-simpleuse" extension will be documented in this file.
|
||||
|
||||
- Task API
|
||||
- Upload only active file
|
||||
- Make it possible to receive a webhook to send info to user => maybe not possible
|
||||
- clean code (more)
|
||||
- check if commit msg was already pushed with `git log main --format=%s` and propose increment
|
||||
- make a better Readme.md
|
||||
- rename extension
|
||||
- better logo ?
|
||||
- description in package.json
|
||||
- if possible verify credential manager
|
||||
- if possible, Show a list of available repositories
|
||||
Check [Keep a Changelog](http://keepachangelog.com/) for recommendations on how to structure this file.
|
||||
|
||||
## [0.3.1] - 2024-07-19
|
||||
|
||||
- fix initRepo command
|
||||
|
||||
## [0.3.0] - 2024-07-19
|
||||
|
||||
- fix autoIncrement > if 2x same number, it incremented the wrong one
|
||||
- check for conflicts before push
|
||||
- clickable link to file
|
||||
- keep lastGitCommitMsg through vscode restart
|
||||
- trim commit message before push
|
||||
- clean code
|
||||
- check if in git repository before running commands => better
|
||||
- "fix" "Merge branch 'main' of https://[...]" in commit message => `git pull --rebase`
|
||||
- fix/improve error output
|
||||
- change `git pull --ff` to `git pull --rebase --autostash` to make it possible to pull when there are uncommited changes
|
||||
|
||||
## [0.2.0] - 2024-07-19
|
||||
|
||||
- No git msgs as errors
|
||||
- Added status bar item (show loading/error)
|
||||
- Log now goes to an outputLogChannel
|
||||
- check if in git repository before running commands
|
||||
- can "disable" extention if not in git repository
|
||||
|
||||
## [0.1.3] - 2024-07-18
|
||||
|
||||
- Fixed "commit message auto increment"
|
||||
- Fixed commit message couldn't have `'` in it
|
||||
- added `--ff` to git pull
|
||||
|
||||
## [0.1.2] - 2024-07-11
|
||||
|
||||
- Fixed "initialize existing repository" command
|
||||
- Renamed commands with "gitDWM : " prefix
|
||||
|
||||
## [0.1.0] - 2024-04-10
|
||||
|
||||
- Choose commmit message
|
||||
- Commit message auto increment
|
||||
- Command to initialize existing repository
|
||||
- Activation event set to "onStartupFinished"
|
||||
|
||||
## [0.0.2] - 2024-02-02
|
||||
|
||||
- Renamed command to something else than "helloworld" => ("full push")
|
||||
|
||||
## [0.0.1] - 2024-02-01
|
||||
## [Unreleased]
|
||||
|
||||
- Initial release
|
||||
|
||||
## [removed from plan]
|
||||
|
||||
- message on quit (vscode) if not everything is pushed => doesn't seem possible with vsocde api
|
||||
- status bar item onClick doesn't realy check if outputLogChannel is opened => not possible to fix because of vscode API
|
||||
|
|
|
|||
|
|
@ -1,3 +1,3 @@
|
|||
This extention is in beta, some errors may occur,
|
||||
errors given through vscode notifications can be ignored for most of them,
|
||||
it needs to and will improve over time.
|
||||
it needs and will improve over time.
|
||||
|
|
|
|||
312
extension.js
312
extension.js
|
|
@ -1,248 +1,98 @@
|
|||
// The module 'vscode' contains the VS Code extensibility API
|
||||
// Import the module and reference it with the alias vscode in your code below
|
||||
const vscode = require("vscode");
|
||||
const util = require("node:util");
|
||||
const chp = require("child_process");
|
||||
const execP = util.promisify(chp.exec);
|
||||
|
||||
let isOutPutChannelVisible = false,
|
||||
logOutputChannel,
|
||||
statusBarItem;
|
||||
// This method is called when your extension is activated
|
||||
// Your extension is activated the very first time the command is executed
|
||||
|
||||
/**
|
||||
* @param {vscode.ExtensionContext} context
|
||||
*/
|
||||
async function activate(context) {
|
||||
let disposable;
|
||||
function activate(context) {
|
||||
// Use the console to output diagnostic information (console.log) and errors (console.error)
|
||||
// This line of code will only be executed once when your extension is activated
|
||||
console.log("yo!");
|
||||
|
||||
logOutputChannel = makeLogOutputChannel("gitDWMSimpleUse");
|
||||
statusBarItem = makeStatusBarItem();
|
||||
context.subscriptions.push(
|
||||
vscode.commands.registerCommand("gitDWMSimpleUse.ToggleOutputChannel", () => {
|
||||
if (isOutPutChannelVisible) logOutputChannel.hide();
|
||||
else logOutputChannel.show(true);
|
||||
isOutPutChannelVisible = !isOutPutChannelVisible;
|
||||
})
|
||||
);
|
||||
try {
|
||||
process.chdir(vscode.workspace.workspaceFolders[0].uri.fsPath);
|
||||
} catch (err) {
|
||||
vscode.window.showErrorMessage(err);
|
||||
}
|
||||
chp.execFile("git", ["pull"], (err, stdout, stderr) => {
|
||||
if (err) {
|
||||
vscode.window.showErrorMessage("GITPULL : " + err.message);
|
||||
return;
|
||||
}
|
||||
if (stderr) {
|
||||
vscode.window.showErrorMessage("GITPULL : " + stderr);
|
||||
return;
|
||||
}
|
||||
vscode.window.showInformationMessage("GITPULL : " + stdout);
|
||||
});
|
||||
|
||||
try {
|
||||
process.chdir(vscode.workspace.workspaceFolders[0].uri.fsPath);
|
||||
} catch (err) {
|
||||
vscode.window.showErrorMessage(err);
|
||||
}
|
||||
// The command has been defined in the package.json file
|
||||
// Now provide the implementation of the command with registerCommand
|
||||
// The commandId parameter must match the command field in package.json
|
||||
let disposable = vscode.commands.registerCommand(
|
||||
"dwm-git-simpleuse.helloWorld",
|
||||
function () {
|
||||
chp.exec(
|
||||
"git add . && git commit -am 'test77' && git pull && git push",
|
||||
{ cwd: vscode.workspace.workspaceFolders[0].uri.fsPath },
|
||||
(err, stdout, stderr) => {
|
||||
if (err) {
|
||||
vscode.window.showErrorMessage(err.message);
|
||||
return;
|
||||
}
|
||||
if (stderr) {
|
||||
vscode.window.showErrorMessage(stderr);
|
||||
return;
|
||||
}
|
||||
vscode.window.showInformationMessage(stdout);
|
||||
}
|
||||
);
|
||||
/* try {
|
||||
process.chdir(vscode.workspace.workspaceFolders[0].uri.fsPath);
|
||||
} catch (err) {
|
||||
vscode.window.showErrorMessage(err);
|
||||
} */
|
||||
/* chp.execFile("git", ["add", "*"], (err, stdout, stderr) => {
|
||||
if (err) {
|
||||
vscode.window.showErrorMessage("GITADD : " + err.message);
|
||||
return;
|
||||
}
|
||||
if (stderr) {
|
||||
vscode.window.showErrorMessage("GITADD : " + stderr);
|
||||
return;
|
||||
}
|
||||
vscode.window.showInformationMessage("GITADD : " + stdout);
|
||||
});
|
||||
chp.execFile(
|
||||
"git",
|
||||
["commit", "-m test7", "-a"],
|
||||
(err, stdout, stderr) => {
|
||||
if (err) {
|
||||
vscode.window.showErrorMessage("GITCOM : " + err.message);
|
||||
return;
|
||||
}
|
||||
if (stderr) {
|
||||
vscode.window.showErrorMessage("GITCOM : " + stderr);
|
||||
return;
|
||||
}
|
||||
vscode.window.showInformationMessage("GITCOM : " + stdout);
|
||||
}
|
||||
); */
|
||||
}
|
||||
);
|
||||
|
||||
if (await isInGitRepo()) {
|
||||
statusBarItem.show();
|
||||
if (!(await hasConflicts(true)))
|
||||
makeSpawn("openPull", "git pull --rebase --autostash", { shell: true });
|
||||
}
|
||||
|
||||
context.subscriptions.push(makeDocumentLinkProvider());
|
||||
|
||||
disposable = vscode.commands.registerCommand("dwm-git-simpleuse.fullPush", async function () {
|
||||
if (
|
||||
!(await isInGitRepo(true)) ||
|
||||
(await hasConflicts(true)) ||
|
||||
(await isWorkingTreeClean(true))
|
||||
)
|
||||
return;
|
||||
|
||||
let commitMsg = await vscode.window.showInputBox({
|
||||
placeHolder: "commit message",
|
||||
prompt: "choose your commit message",
|
||||
value: ((await context.workspaceState.get("lastGitCommitMsg")) || "").incrementSuffixe(),
|
||||
});
|
||||
if (commitMsg === undefined) return;
|
||||
commitMsg = commitMsg.trim();
|
||||
if (!commitMsg.length) {
|
||||
vscode.window.showErrorMessage("commit message needed");
|
||||
return;
|
||||
}
|
||||
|
||||
context.workspaceState.update("lastGitCommitMsg", commitMsg);
|
||||
|
||||
await makeSpawn("fullPush-pull", `git pull --rebase --autostash`, { shell: true });
|
||||
if (await hasConflicts(true)) return;
|
||||
makeSpawn(
|
||||
"fullPush",
|
||||
`git add . && git commit -am "${commitMsg.replace(/"/g, '\\"')}" && git push`,
|
||||
{ shell: true }
|
||||
);
|
||||
});
|
||||
context.subscriptions.push(disposable);
|
||||
|
||||
disposable = vscode.commands.registerCommand("dwm-git-simpleuse.initRepo", async function () {
|
||||
if (await isInGitRepo()) {
|
||||
vscode.window.showErrorMessage("Already in a git repository");
|
||||
return;
|
||||
}
|
||||
|
||||
let gitLink = await vscode.window.showInputBox({
|
||||
placeHolder: "git repo link",
|
||||
prompt: "Initialize a git repository",
|
||||
value: await vscode.env.clipboard.readText(),
|
||||
});
|
||||
if (gitLink === undefined) return;
|
||||
gitLink = gitLink.trim();
|
||||
if (!gitLink.match(/^https?:\/\/\S+\.git$/).length) {
|
||||
vscode.window.showErrorMessage("Link not valid");
|
||||
return;
|
||||
}
|
||||
|
||||
let gitBranch = await vscode.window.showInputBox({
|
||||
placeHolder: "git branch",
|
||||
prompt: "choose wich branch to use (defaults to 'main')",
|
||||
value: "main",
|
||||
});
|
||||
if (gitBranch === undefined) return;
|
||||
gitBranch = gitBranch.trim();
|
||||
if (!gitBranch.length) gitBranch = "main";
|
||||
|
||||
makeSpawn(
|
||||
"initRepo",
|
||||
`git init && git remote add origin ${gitLink} && git fetch && git checkout -ft origin/${gitBranch}`,
|
||||
{ shell: true }
|
||||
);
|
||||
});
|
||||
context.subscriptions.push(disposable);
|
||||
context.subscriptions.push(disposable);
|
||||
}
|
||||
|
||||
// This method is called when your extension is deactivated
|
||||
function deactivate() {}
|
||||
|
||||
module.exports = {
|
||||
activate,
|
||||
deactivate,
|
||||
activate,
|
||||
deactivate,
|
||||
};
|
||||
|
||||
function makeSpawn(name, command, options = {}) {
|
||||
return new Promise((resolve) => {
|
||||
statusBarItem.text = "$(loading~spin) GitDWMSU";
|
||||
statusBarItem.tooltip = name;
|
||||
let spawn = chp.spawn(`${command} 2>&1 || echo 'gitSU_error'`, options);
|
||||
spawn.stdout.on("data", (d) => {
|
||||
if (/\n\s*gitSU_error[\s\n]*$/.test(d.toString())) {
|
||||
statusBarItem.backgroundColor = new vscode.ThemeColor("statusBarItem.errorBackground");
|
||||
setTimeout(() => {
|
||||
statusBarItem.backgroundColor = new vscode.ThemeColor("statusBarItem.background");
|
||||
}, 5000);
|
||||
vscode.window.showErrorMessage(`[${name}] An error occurred`, "Show").then((e) => {
|
||||
if (e == "Show") {
|
||||
logOutputChannel.show(true);
|
||||
isOutPutChannelVisible = true;
|
||||
}
|
||||
});
|
||||
logOutputChannel.error(`[${name}] ${d.toString().replace(/\n\s*gitSU_error[\s]*/, "")}`);
|
||||
} else logOutputChannel.info(`[${name}] ${d.toString()}`);
|
||||
});
|
||||
spawn.stderr.on("data", (d) => {
|
||||
logOutputChannel.error(`[${name}] ${d.toString()}`);
|
||||
});
|
||||
spawn.on("close", (c) => {
|
||||
logOutputChannel.trace(`[${name}] child process exited with code ${c}`);
|
||||
statusBarItem.text = "$(remote) GitDWMSU";
|
||||
statusBarItem.tooltip = "";
|
||||
resolve();
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
async function isWorkingTreeClean(doActions = false) {
|
||||
const { stdout } = await execP(`git status --porcelain`);
|
||||
if (doActions && stdout.trim() == "") vscode.window.showErrorMessage(`Working tree is clean`);
|
||||
return stdout.trim() == "";
|
||||
}
|
||||
|
||||
async function isInGitRepo(doActions = false) {
|
||||
const { stdout } = await execP(`git rev-parse --is-inside-work-tree || echo false`);
|
||||
if (doActions && stdout.trim() !== "true") vscode.window.showErrorMessage("Not a git repository");
|
||||
return stdout.trim() === "true";
|
||||
}
|
||||
|
||||
async function hasConflicts(doActions = false) {
|
||||
const { stdout } = await execP(`git diff --name-only --diff-filter=U`);
|
||||
if (doActions && stdout.trim() != "") {
|
||||
vscode.window
|
||||
.showErrorMessage(
|
||||
`You have to resolve conflicts :\n${stdout.trim().replace("\n", ", ")}`,
|
||||
"Show files",
|
||||
"Git pull"
|
||||
)
|
||||
.then(async (e) => {
|
||||
if (e == "Show files") {
|
||||
logOutputChannel.show(true);
|
||||
isOutPutChannelVisible = true;
|
||||
} else if (e == "Git pull" && !(await hasConflicts(true))) {
|
||||
makeSpawn("openPull", "git pull --rebase --autostash", { shell: true });
|
||||
}
|
||||
});
|
||||
logOutputChannel.error(
|
||||
"[conflicts] Conflicted files : \n" +
|
||||
stdout
|
||||
.split("\n")
|
||||
.filter((e) => e.trim().length)
|
||||
.map((e) => `F:${e}#`)
|
||||
.join("\n")
|
||||
);
|
||||
}
|
||||
return stdout.trim() != "";
|
||||
}
|
||||
|
||||
String.prototype.incrementSuffixe = function () {
|
||||
const match = this.match(/\s*\((\d+)\)\s*$/);
|
||||
return match
|
||||
? this.replace(new RegExp(`${match[0].escapeRegex()}$`), ` (${+match[1] + 1})`)
|
||||
: this.trim().length
|
||||
? this + " (1)"
|
||||
: this.trim();
|
||||
};
|
||||
|
||||
String.prototype.escapeRegex = function () {
|
||||
return this.replace(/[/\-\\^$*+?.()|[\]{}]/g, "\\$&");
|
||||
};
|
||||
|
||||
function makeLogOutputChannel(name) {
|
||||
return vscode.window.createOutputChannel(name, {
|
||||
log: true,
|
||||
logLevel: 3,
|
||||
});
|
||||
}
|
||||
|
||||
function makeStatusBarItem() {
|
||||
let s = vscode.window.createStatusBarItem(vscode.StatusBarAlignment.Left, 100);
|
||||
s.text = "$(remote) GitDWMSU";
|
||||
s.command = "gitDWMSimpleUse.ToggleOutputChannel";
|
||||
return s;
|
||||
}
|
||||
|
||||
function makeDocumentLinkProvider() {
|
||||
return vscode.languages.registerDocumentLinkProvider(
|
||||
{ language: "log", scheme: "output" },
|
||||
{
|
||||
provideDocumentLinks(doc) {
|
||||
const links = [];
|
||||
|
||||
const regex = /F(ile|older)?:([^#]+)#/g;
|
||||
for (let line = 0; line < doc.lineCount; line++) {
|
||||
let text = doc.lineAt(line).text;
|
||||
let match;
|
||||
while ((match = regex.exec(text)) !== null) {
|
||||
const _index = match.index + 2 + (match[1] ? match[1].length : 0);
|
||||
const range = new vscode.Range(
|
||||
new vscode.Position(line, _index),
|
||||
new vscode.Position(line, _index + match[2].length)
|
||||
);
|
||||
links.push(
|
||||
new vscode.DocumentLink(
|
||||
range,
|
||||
vscode.Uri.file(
|
||||
(match[1] ? "" : `${vscode.workspace.workspaceFolders[0].uri.fsPath}/`) + match[2]
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
return links;
|
||||
},
|
||||
}
|
||||
);
|
||||
}
|
||||
|
|
|
|||
4
package-lock.json
generated
4
package-lock.json
generated
|
|
@ -1,12 +1,12 @@
|
|||
{
|
||||
"name": "dwm-git-simpleuse",
|
||||
"version": "0.3.1",
|
||||
"version": "0.0.1",
|
||||
"lockfileVersion": 3,
|
||||
"requires": true,
|
||||
"packages": {
|
||||
"": {
|
||||
"name": "dwm-git-simpleuse",
|
||||
"version": "0.3.1",
|
||||
"version": "0.0.1",
|
||||
"dependencies": {
|
||||
"child_process": "^1.0.2"
|
||||
},
|
||||
|
|
|
|||
109
package.json
109
package.json
|
|
@ -1,65 +1,48 @@
|
|||
{
|
||||
"name": "dwm-git-simpleuse",
|
||||
"displayName": "DWM_git_simpleUse",
|
||||
"icon": "img/icon.png",
|
||||
"description": "",
|
||||
"publisher": "nyncral",
|
||||
"version": "0.3.1",
|
||||
"engines": {
|
||||
"vscode": "^1.85.0"
|
||||
},
|
||||
"categories": [
|
||||
"Other"
|
||||
],
|
||||
"activationEvents": [
|
||||
"onStartupFinished"
|
||||
],
|
||||
"main": "./extension.js",
|
||||
"contributes": {
|
||||
"commands": [
|
||||
{
|
||||
"command": "dwm-git-simpleuse.fullPush",
|
||||
"title": "gitDWM : full push"
|
||||
},
|
||||
{
|
||||
"command": "dwm-git-simpleuse.initRepo",
|
||||
"title": "gitDWM : initialize existing repository"
|
||||
}
|
||||
],
|
||||
"keybindings": [
|
||||
{
|
||||
"command": "dwm-git-simpleuse.fullPush",
|
||||
"key": "ctrl+alt+s"
|
||||
}
|
||||
],
|
||||
"configuration": {
|
||||
"type": "object",
|
||||
"title": "DWM Git Simple Use Configuration",
|
||||
"properties": {
|
||||
"dwm-git-simpleuse.isEnabled": {
|
||||
"type": "boolean",
|
||||
"default": true,
|
||||
"description": "Enable DWM Git Simple Use extension",
|
||||
"scope": "resource"
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"scripts": {
|
||||
"lint": "eslint .",
|
||||
"pretest": "npm run lint",
|
||||
"test": "vscode-test"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/mocha": "^10.0.6",
|
||||
"@types/node": "18.x",
|
||||
"@types/vscode": "^1.85.0",
|
||||
"@vscode/test-cli": "^0.0.4",
|
||||
"@vscode/test-electron": "^2.3.8",
|
||||
"eslint": "^8.56.0",
|
||||
"typescript": "^5.3.3"
|
||||
},
|
||||
"dependencies": {
|
||||
"child_process": "^1.0.2"
|
||||
}
|
||||
"name": "dwm-git-simpleuse",
|
||||
"displayName": "DWM_git_simpleUse",
|
||||
"icon": "img/icon.png",
|
||||
"description": "",
|
||||
"publisher": "nyncral",
|
||||
"version": "0.0.1",
|
||||
"engines": {
|
||||
"vscode": "^1.85.0"
|
||||
},
|
||||
"categories": [
|
||||
"Other"
|
||||
],
|
||||
"activationEvents": [],
|
||||
"main": "./extension.js",
|
||||
"contributes": {
|
||||
"commands": [
|
||||
{
|
||||
"command": "dwm-git-simpleuse.helloWorld",
|
||||
"title": "HelloWorld23"
|
||||
}
|
||||
],
|
||||
"keybindings": [
|
||||
{
|
||||
"command": "dwm-git-simpleuse.helloWorld",
|
||||
"key": "ctrl+alt+r",
|
||||
"mac": "cmd+alt+r"
|
||||
}
|
||||
]
|
||||
},
|
||||
"scripts": {
|
||||
"lint": "eslint .",
|
||||
"pretest": "npm run lint",
|
||||
"test": "vscode-test"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/mocha": "^10.0.6",
|
||||
"@types/node": "18.x",
|
||||
"@types/vscode": "^1.85.0",
|
||||
"@vscode/test-cli": "^0.0.4",
|
||||
"@vscode/test-electron": "^2.3.8",
|
||||
"eslint": "^8.56.0",
|
||||
"typescript": "^5.3.3"
|
||||
},
|
||||
"dependencies": {
|
||||
"child_process": "^1.0.2"
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue