Fix CRLF and submodules with auto-generated copyright headers
We no longer add another character to the file every time it is committed, and instead now properly handle CRLF. Additionally submodules are no longer updated when they shouldn't be, without requiring a manual config edit.
This commit is contained in:
@@ -1,5 +1,4 @@
|
|||||||
# AUTOGENERATED COPYRIGHT HEADER START
|
# AUTOGENERATED COPYRIGHT HEADER START
|
||||||
# Copyright (C) NaN-NaN undefined
|
|
||||||
# Copyright (C) 2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
# Copyright (C) 2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
# AUTOGENERATED COPYRIGHT HEADER END
|
# AUTOGENERATED COPYRIGHT HEADER END
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
# AUTOGENERATED COPYRIGHT HEADER START
|
# AUTOGENERATED COPYRIGHT HEADER START
|
||||||
# Copyright (C) NaN-NaN undefined
|
|
||||||
# Copyright (C) 2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
# Copyright (C) 2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
# AUTOGENERATED COPYRIGHT HEADER END
|
# AUTOGENERATED COPYRIGHT HEADER END
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
# AUTOGENERATED COPYRIGHT HEADER START
|
# AUTOGENERATED COPYRIGHT HEADER START
|
||||||
# Copyright (C) NaN-NaN undefined
|
|
||||||
# Copyright (C) 2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
# Copyright (C) 2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
# AUTOGENERATED COPYRIGHT HEADER END
|
# AUTOGENERATED COPYRIGHT HEADER END
|
||||||
|
|
||||||
|
|||||||
@@ -1,3 +1,6 @@
|
|||||||
|
# AUTOGENERATED COPYRIGHT HEADER START
|
||||||
|
# Copyright (C) 2017-2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
|
# AUTOGENERATED COPYRIGHT HEADER END
|
||||||
# Build Directories
|
# Build Directories
|
||||||
/build
|
/build
|
||||||
/build32
|
/build32
|
||||||
|
|||||||
@@ -1,3 +1,6 @@
|
|||||||
|
# AUTOGENERATED COPYRIGHT HEADER START
|
||||||
|
# Copyright (C) 2017-2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
|
# AUTOGENERATED COPYRIGHT HEADER END
|
||||||
[submodule "cmake/cmake-version"]
|
[submodule "cmake/cmake-version"]
|
||||||
path = cmake/cmake-version
|
path = cmake/cmake-version
|
||||||
url = https://github.com/Xaymar/cmake-version.git
|
url = https://github.com/Xaymar/cmake-version.git
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
## AUTOGENERATED COPYRIGHT HEADER START
|
# AUTOGENERATED COPYRIGHT HEADER START
|
||||||
# Copyright (C) 2017-2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
# Copyright (C) 2017-2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
# AUTOGENERATED COPYRIGHT HEADER END
|
# AUTOGENERATED COPYRIGHT HEADER END
|
||||||
cmake_minimum_required(VERSION 3.26...3.29.2 FATAL_ERROR)
|
cmake_minimum_required(VERSION 3.26...3.29.2 FATAL_ERROR)
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
## AUTOGENERATED COPYRIGHT HEADER START
|
# AUTOGENERATED COPYRIGHT HEADER START
|
||||||
# Copyright (C) 2017-2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
# Copyright (C) 2017-2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
# AUTOGENERATED COPYRIGHT HEADER END
|
# AUTOGENERATED COPYRIGHT HEADER END
|
||||||
project(code_compiler
|
project(code_compiler
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
# AUTOGENERATED COPYRIGHT HEADER START
|
# AUTOGENERATED COPYRIGHT HEADER START
|
||||||
# Copyright (C) NaN-NaN undefined
|
|
||||||
# Copyright (C) 2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
# Copyright (C) 2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
# AUTOGENERATED COPYRIGHT HEADER END
|
# AUTOGENERATED COPYRIGHT HEADER END
|
||||||
/stranded2
|
/stranded2
|
||||||
|
|||||||
@@ -1,3 +1,6 @@
|
|||||||
|
; AUTOGENERATED COPYRIGHT HEADER START
|
||||||
|
; Copyright (C) 2017 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
|
; AUTOGENERATED COPYRIGHT HEADER END
|
||||||
; Ein simpler Lexer Test
|
; Ein simpler Lexer Test
|
||||||
Local Variable = 1.0
|
Local Variable = 1.0
|
||||||
Local Variable2$ = "Hallo Welt"
|
Local Variable2$ = "Hallo Welt"
|
||||||
|
|||||||
@@ -1,3 +1,6 @@
|
|||||||
|
; AUTOGENERATED COPYRIGHT HEADER START
|
||||||
|
; Copyright (C) 2017 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
|
; AUTOGENERATED COPYRIGHT HEADER END
|
||||||
Graphics 800,600,32,2
|
Graphics 800,600,32,2
|
||||||
SetBuffer BackBuffer()
|
SetBuffer BackBuffer()
|
||||||
|
|
||||||
|
|||||||
@@ -1,3 +1,6 @@
|
|||||||
|
; AUTOGENERATED COPYRIGHT HEADER START
|
||||||
|
; Copyright (C) 2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
|
; AUTOGENERATED COPYRIGHT HEADER END
|
||||||
Local iValue = 1, iValue2 = 1.2, iValue3 = "Hello World"
|
Local iValue = 1, iValue2 = 1.2, iValue3 = "Hello World"
|
||||||
; iValue should be 1
|
; iValue should be 1
|
||||||
; iValue2 should be 1, and print a warning
|
; iValue2 should be 1, and print a warning
|
||||||
|
|||||||
@@ -1 +1,4 @@
|
|||||||
|
; AUTOGENERATED COPYRIGHT HEADER START
|
||||||
|
; Copyright (C) 2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
|
; AUTOGENERATED COPYRIGHT HEADER END
|
||||||
Local iValue = 2
|
Local iValue = 2
|
||||||
@@ -1,3 +1,6 @@
|
|||||||
|
; AUTOGENERATED COPYRIGHT HEADER START
|
||||||
|
; Copyright (C) 2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
|
; AUTOGENERATED COPYRIGHT HEADER END
|
||||||
Include "004-incl.bb"
|
Include "004-incl.bb"
|
||||||
; Should be parsed as:
|
; Should be parsed as:
|
||||||
; Include(String("test.bb"))
|
; Include(String("test.bb"))
|
||||||
|
|||||||
+85
-27
@@ -1,8 +1,6 @@
|
|||||||
// AUTOGENERATED COPYRIGHT HEADER START
|
// AUTOGENERATED COPYRIGHT HEADER START
|
||||||
// Copyright (C) NaN-NaN undefined
|
|
||||||
// Copyright (C) 2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
// Copyright (C) 2024 Michael Fabian 'Xaymar' Dirks <info@xaymar.com>
|
||||||
// AUTOGENERATED COPYRIGHT HEADER END
|
// AUTOGENERATED COPYRIGHT HEADER END
|
||||||
|
|
||||||
const ignoreList = [
|
const ignoreList = [
|
||||||
/^\.git$/gi,
|
/^\.git$/gi,
|
||||||
/^cmake\/clang$/gi,
|
/^cmake\/clang$/gi,
|
||||||
@@ -39,6 +37,10 @@ const formatStyleList = {
|
|||||||
], exts: [
|
], exts: [
|
||||||
".iss",
|
".iss",
|
||||||
".iss.in",
|
".iss.in",
|
||||||
|
".bb",
|
||||||
|
".b3d",
|
||||||
|
".b2d",
|
||||||
|
".bpl"
|
||||||
],
|
],
|
||||||
prepend: [
|
prepend: [
|
||||||
`; ${sectionStart}`,
|
`; ${sectionStart}`,
|
||||||
@@ -111,6 +113,7 @@ const PATH = require("node:path");
|
|||||||
const FS = require("node:fs");
|
const FS = require("node:fs");
|
||||||
const FSPROMISES = require("node:fs/promises");
|
const FSPROMISES = require("node:fs/promises");
|
||||||
const OS = require("os");
|
const OS = require("os");
|
||||||
|
const READLINE = require('node:readline');
|
||||||
|
|
||||||
if (!debug)
|
if (!debug)
|
||||||
console.debug = function() {}
|
console.debug = function() {}
|
||||||
@@ -191,11 +194,12 @@ class RateLimiter {
|
|||||||
}
|
}
|
||||||
|
|
||||||
let abortAllWork = false;
|
let abortAllWork = false;
|
||||||
let gitRL = new RateLimiter(1);
|
let gitRL = new RateLimiter(3);
|
||||||
let workRL = new RateLimiter();
|
let workRL = new RateLimiter();
|
||||||
let gitCurrentFiles;
|
let gitCurrentFiles;
|
||||||
let gitUserName;
|
let gitUserName;
|
||||||
let gitUserMail;
|
let gitUserMail;
|
||||||
|
let gitSubmodules;
|
||||||
let gitDate = (new Date()).toISOString();
|
let gitDate = (new Date()).toISOString();
|
||||||
|
|
||||||
/** Run a process asynchronously, returning an array of messages.
|
/** Run a process asynchronously, returning an array of messages.
|
||||||
@@ -265,6 +269,8 @@ async function runProcessAsync(path, args, options) {
|
|||||||
async function git_isIgnored(path) {
|
async function git_isIgnored(path) {
|
||||||
console.debug(arguments.callee.name, Array.from(arguments));
|
console.debug(arguments.callee.name, Array.from(arguments));
|
||||||
let rpath = PATH.relative(process.cwd(), path).replaceAll(PATH.sep, PATH.posix.sep);
|
let rpath = PATH.relative(process.cwd(), path).replaceAll(PATH.sep, PATH.posix.sep);
|
||||||
|
|
||||||
|
// Check manual ignore list.
|
||||||
for (let ignore of ignoreList) {
|
for (let ignore of ignoreList) {
|
||||||
if (ignore instanceof RegExp) {
|
if (ignore instanceof RegExp) {
|
||||||
if (ignore.global) {
|
if (ignore.global) {
|
||||||
@@ -282,6 +288,15 @@ async function git_isIgnored(path) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Check if this happens to be (in) a submodule.
|
||||||
|
let modules = await git_subModules()
|
||||||
|
for (let module of modules) {
|
||||||
|
if (rpath.startsWith(module)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Finally check if git ignores this file.
|
||||||
let result = await gitRL.queue(runProcessAsync, "git", ["check-ignore", path], {});
|
let result = await gitRL.queue(runProcessAsync, "git", ["check-ignore", path], {});
|
||||||
return (result[0] == 0)
|
return (result[0] == 0)
|
||||||
}
|
}
|
||||||
@@ -299,6 +314,31 @@ async function git_getCurrentAuthor() {
|
|||||||
return commitFormat.replace("%aI", gitDate).replace("%aN", gitUserName).replace("%aE", gitUserMail);
|
return commitFormat.replace("%aI", gitDate).replace("%aN", gitUserName).replace("%aE", gitUserMail);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async function git_subModules() {
|
||||||
|
if (!gitSubmodules) {
|
||||||
|
gitSubmodules = new Set();
|
||||||
|
|
||||||
|
let gitmodules = PATH.join(process.cwd(), ".gitmodules");
|
||||||
|
if ((await FSPROMISES.stat(gitmodules)).isFile()) {
|
||||||
|
let gmfs = FS.createReadStream(gitmodules);
|
||||||
|
const rl = READLINE.createInterface({
|
||||||
|
input: gmfs,
|
||||||
|
crlfDelay: Infinity
|
||||||
|
});
|
||||||
|
for await(const line of rl) {
|
||||||
|
let parts = line.trim().split("=");
|
||||||
|
if (parts.length > 1) {
|
||||||
|
if(parts[0].trim() == "path") {
|
||||||
|
gitSubmodules.add(parts[1].trim());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return gitSubmodules;
|
||||||
|
}
|
||||||
|
|
||||||
async function git_isInCurrentCommit(file) {
|
async function git_isInCurrentCommit(file) {
|
||||||
console.debug(arguments.callee.name, Array.from(arguments));
|
console.debug(arguments.callee.name, Array.from(arguments));
|
||||||
if (!gitCurrentFiles) {
|
if (!gitCurrentFiles) {
|
||||||
@@ -444,39 +484,46 @@ async function updateFile(file) {
|
|||||||
}
|
}
|
||||||
console.log(`Updating file '${file}'...`);
|
console.log(`Updating file '${file}'...`);
|
||||||
|
|
||||||
|
// ToDo: Do we actually need to read the file first, or can we use the same rw stream?
|
||||||
// File contents.
|
// File contents.
|
||||||
let content = await FSPROMISES.readFile(file);
|
let contentBuf = await FSPROMISES.readFile(file);
|
||||||
let eol = (content.indexOf("\r\n") != -1 ? OS.EOL : "\n");
|
let eol = contentBuf.indexOf("\r\n") != -1 ? "\r\n" : "\n";
|
||||||
let insert = Buffer.from(header.join(eol) + eol);
|
let headerBuf = Buffer.from(header.join(eol) + eol, "utf8");
|
||||||
|
|
||||||
// Find the starting point.
|
// Find the starting point.
|
||||||
let startHeader = content.indexOf(sectionStart);
|
let startHeader = contentBuf.indexOf(Buffer.from(header[0], "utf8"));
|
||||||
startHeader = content.lastIndexOf(eol, startHeader);
|
if (startHeader != -1) {
|
||||||
startHeader += Buffer.from(eol).byteLength;
|
//startHeader = contentBuf.lastIndexOf(eolBuf, startHeader);
|
||||||
|
//startHeader += eolb.byteLength;
|
||||||
|
}
|
||||||
|
console.log(sectionStart, startHeader);
|
||||||
|
|
||||||
// Find the ending point.
|
// Find the ending point.
|
||||||
let endHeader = content.indexOf(sectionEnd);
|
let endHeader = contentBuf.lastIndexOf(Buffer.from(header[header.length - 1], "utf8"));
|
||||||
endHeader = content.indexOf(eol, endHeader);
|
if (endHeader != -1) {
|
||||||
endHeader += Buffer.from(eol).byteLength;
|
endHeader += Buffer.from(header[header.length - 1], "utf8").byteLength;
|
||||||
|
endHeader += Buffer.byteLength(eol, "utf8");
|
||||||
|
}
|
||||||
|
console.log(sectionEnd, endHeader);
|
||||||
|
|
||||||
|
// Last check for early-exit here.
|
||||||
if (abortAllWork) {
|
if (abortAllWork) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
let fd = await FSPROMISES.open(file, "w");
|
let fd = await FSPROMISES.open(file, "w");
|
||||||
let fp = [];
|
if (startHeader == -1 || (endHeader < startHeader)) {
|
||||||
if ((startHeader >= 0) && (endHeader > startHeader)) {
|
fd.write(headerBuf, 0, null, 0);
|
||||||
|
fd.write(contentBuf, 0, null, headerBuf.byteLength);
|
||||||
|
} else {
|
||||||
let pos = 0;
|
let pos = 0;
|
||||||
|
|
||||||
if (startHeader > 0) {
|
if (startHeader > 0) {
|
||||||
fd.write(content, 0, startHeader, 0);
|
fd.write(contentBuf, 0, startHeader - Buffer.byteLength(eol, "utf8").byteLength, 0);
|
||||||
pos += startHeader;
|
pos += startHeader;
|
||||||
}
|
}
|
||||||
fd.write(insert, 0, undefined, pos);
|
fd.write(headerBuf, 0, null, pos); pos += headerBuf.byteLength;
|
||||||
pos += insert.byteLength;
|
fd.write(contentBuf, endHeader, null, pos);
|
||||||
fd.write(content, endHeader, undefined, pos);
|
|
||||||
} else {
|
|
||||||
fd.write(insert, 0, undefined, 0);
|
|
||||||
fd.write(content, 0, undefined, insert.byteLength);
|
|
||||||
}
|
}
|
||||||
await fd.close();
|
await fd.close();
|
||||||
} catch (ex) {
|
} catch (ex) {
|
||||||
@@ -490,11 +537,14 @@ async function updateFile(file) {
|
|||||||
|
|
||||||
async function scanPath(path) {
|
async function scanPath(path) {
|
||||||
console.debug(arguments.callee.name, Array.from(arguments));
|
console.debug(arguments.callee.name, Array.from(arguments));
|
||||||
|
|
||||||
// Abort here if the user aborted the process, or if the path is ignored.
|
// Abort here if the user aborted the process, or if the path is ignored.
|
||||||
if (abortAllWork) {
|
if (abortAllWork) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
console.log(`Scanning path '${path}'...`);
|
||||||
|
|
||||||
let promises = [];
|
let promises = [];
|
||||||
|
|
||||||
await workRL.queue(async () => {
|
await workRL.queue(async () => {
|
||||||
@@ -511,7 +561,6 @@ async function scanPath(path) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (file.isDirectory()) {
|
if (file.isDirectory()) {
|
||||||
console.log(`Scanning path '${fullname}'...`);
|
|
||||||
promises.push(scanPath(fullname));
|
promises.push(scanPath(fullname));
|
||||||
} else {
|
} else {
|
||||||
promises.push(updateFile(fullname));
|
promises.push(updateFile(fullname));
|
||||||
@@ -535,6 +584,7 @@ async function scanPath(path) {
|
|||||||
console.debug(root_path, PROCESS.argv, PROCESS.execArgv);
|
console.debug(root_path, PROCESS.argv, PROCESS.execArgv);
|
||||||
|
|
||||||
var args = PROCESS.argv.slice(2);
|
var args = PROCESS.argv.slice(2);
|
||||||
|
let promises = new Array();
|
||||||
while (args.length > 0) {
|
while (args.length > 0) {
|
||||||
// Try to place ourselves where git actually is.
|
// Try to place ourselves where git actually is.
|
||||||
while (!is_git_directory) {
|
while (!is_git_directory) {
|
||||||
@@ -543,7 +593,7 @@ async function scanPath(path) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
let entries = await FSPROMISES.readdir(PROCESS.cwd());
|
let entries = await FSPROMISES.readdir(PROCESS.cwd());
|
||||||
if (entries.includes(".git")) {
|
if (entries.includes(".git") && ((await FSPROMISES.stat(PATH.join(PROCESS.cwd(), ".git"))).isDirectory())) {
|
||||||
console.log(`Found .git at '${process.cwd()}'.`);
|
console.log(`Found .git at '${process.cwd()}'.`);
|
||||||
is_git_directory = true;
|
is_git_directory = true;
|
||||||
} else {
|
} else {
|
||||||
@@ -558,6 +608,12 @@ async function scanPath(path) {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (abortAllWork) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
git_getCurrentAuthor();
|
||||||
|
|
||||||
// Then proceed with normal work.
|
// Then proceed with normal work.
|
||||||
let path = PATH.normalize(PATH.relative(process.cwd(), PATH.resolve(root_path, args[0])));
|
let path = PATH.normalize(PATH.relative(process.cwd(), PATH.resolve(root_path, args[0])));
|
||||||
|
|
||||||
@@ -567,15 +623,17 @@ async function scanPath(path) {
|
|||||||
if (await git_isIgnored(path)) {
|
if (await git_isIgnored(path)) {
|
||||||
console.log(`Ignoring path '${path}'...`);
|
console.log(`Ignoring path '${path}'...`);
|
||||||
} else if(pathStat.isDirectory()) {
|
} else if(pathStat.isDirectory()) {
|
||||||
console.log(`Scanning path '${path}'...`);
|
//await scanPath(path);
|
||||||
await scanPath(path);
|
promises.push(scanPath(path));
|
||||||
} else {
|
} else {
|
||||||
await updateFile(path);
|
//await updateFile(path);
|
||||||
|
promises.push(updateFile(path));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Slice off the first argument and continue.
|
// Slice off the first argument and continue.
|
||||||
args = args.slice(1);
|
args = args.slice(1);
|
||||||
}
|
}
|
||||||
|
await Promise.all(promises);
|
||||||
console.log("Done");
|
console.log("Done");
|
||||||
})();
|
})();
|
||||||
|
|||||||
Reference in New Issue
Block a user