virtual-code-owners 2.1.0 → 2.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -45,8 +45,8 @@ have the following choices:
45
45
 
46
46
  ### VIRTUAL-CODEOWNERS.txt
47
47
 
48
- `VIRTUAL_CODEOWNERS.txt` is a regular, valid GitHub [CODEOWNERS](https://docs.github.com/en/repositories/managing-your-repositorys-settings-and-features/customizing-your-repository/about-code-owners#codeowners-and-branch-protection) file.
49
- The only difference between VIRTUAL-CODEOWNERS and a CODEOWNERS file is that
48
+ `VIRTUAL_CODEOWNERS.txt` is a regular, valid GitHub [CODEOWNERS](https://docs.github.com/en/repositories/managing-your-repositorys-settings-and-features/customizing-your-repository/about-code-owners) file.
49
+ The only difference between VIRTUAL-CODEOWNERS.txt and a CODEOWNERS file is that
50
50
  the _teams_ the former uses might not exist yet, except in a `virtual-teams.yml`.
51
51
 
52
52
  Example:
@@ -54,7 +54,7 @@ Example:
54
54
  ```
55
55
  #! comments that start with #! won't appear in the CODEOWNERS output e.g.
56
56
  #! this is not the CODEOWNERS file - to get that one run
57
- #! npx virtual-code-owners VIRTUAL-CODE-OWNERS.txt virtual-teams.yml > CODEOWNERS
57
+ #! npx virtual-code-owners
58
58
  #! on this.
59
59
  #!
60
60
  # Regular comments are retained
@@ -73,6 +73,7 @@ libs/components/ @ch/ux
73
73
  A valid YAML file that contains a list of teams, with for each team its members:
74
74
 
75
75
  ```yaml
76
+ # yaml-language-server: $schema=https://raw.githubusercontent.com/sverweij/virtual-code-owners/main/src/virtual-teams.schema.json
76
77
  ch/after-sales:
77
78
  - john-doe-ch
78
79
  - pete-peterson-ch
@@ -114,14 +115,10 @@ team name and _virtual-code-owners_ will leave the real name alone.
114
115
 
115
116
  - Currently only works for _usernames_ to identify team members - not for e-mail
116
117
  addresses.
117
- - If people are in more than one team, chances are they get mentioned multiple
118
- times on the same line if both teams are code owners of the same part of the
119
- code. While maybe not _looking_ ideal, the resulting code owners file is still
120
- valid & ready to rock'n roll.
121
118
  - _virtual-code-owners_ assumes the VIRTUAL-CODEOWNERS.txt is a valid CODEOWNERS
122
119
  file and the virtual-teams.yml is a valid yaml file with teams names as keys
123
120
  and team members as arrays under these. It will likely throw errors when this
124
- assumption is not met, but the error-messages might not be as clear as possible.
121
+ assumption is not met, but the error-messages might not be cryptic.
125
122
 
126
123
  ### Why the `.txt` extension?
127
124
 
@@ -5,42 +5,52 @@ const DEFAULT_GENERATED_WARNING = `#${EOL}` +
5
5
  `# To make changes:${EOL}` +
6
6
  `#${EOL}` +
7
7
  `# - edit .github/VIRTUAL-CODEOWNERS.txt${EOL}` +
8
+ `# - and/ or add team members to .github/virtual-teams.yml${EOL}` +
8
9
  `# - run 'npx virtual-code-owners'${EOL}` +
9
10
  `#${EOL}${EOL}`;
10
- function replaceTeamNames(pLine, pTeamMap) {
11
- let lReturnValue = pLine;
12
- for (let lTeamName of Object.keys(pTeamMap)) {
13
- lReturnValue = lReturnValue.replace(new RegExp(`(\\s)@${lTeamName}(\\s|$)`, "g"), `$1${pTeamMap[lTeamName].map((pUserName) => `@${pUserName}`).join(" ")}$2`);
14
- }
15
- return lReturnValue;
11
+ const LINE_PATTERN = /^(?<filesPattern>[^\s]+\s+)(?<userNames>.*)$/;
12
+ export function convert(pCodeOwnersFileAsString, pTeamMap, pGeneratedWarning = DEFAULT_GENERATED_WARNING) {
13
+ return `${pGeneratedWarning}${pCodeOwnersFileAsString
14
+ .split(EOL)
15
+ .filter(shouldAppearInResult)
16
+ .map(convertLine(pTeamMap))
17
+ .map(deduplicateUserNames)
18
+ .join(EOL)}`;
19
+ }
20
+ function shouldAppearInResult(pLine) {
21
+ return !pLine.trimStart().startsWith("#!");
16
22
  }
17
23
  function convertLine(pTeamMap) {
18
24
  return (pUntreatedLine) => {
19
- const lTrimmedLine = pUntreatedLine.trimStart();
25
+ const lTrimmedLine = pUntreatedLine.trim();
20
26
  if (lTrimmedLine.startsWith("#") || lTrimmedLine === "") {
21
27
  return pUntreatedLine;
22
28
  }
23
29
  else {
24
- return replaceTeamNames(pUntreatedLine, pTeamMap);
30
+ return replaceTeamNames(lTrimmedLine, pTeamMap);
25
31
  }
26
32
  };
27
33
  }
28
- function deduplicateUserNames(pLine) {
29
- const lTrimmedLine = pLine.trim();
30
- const lSplitLine = lTrimmedLine.match(/^(?<filesPattern>[^\s]+)(?<theRest>.*)$/);
31
- if (lTrimmedLine.startsWith("#") || !lSplitLine?.groups) {
32
- return pLine;
34
+ function replaceTeamNames(pTrimmedLine, pTeamMap) {
35
+ const lSplitLine = pTrimmedLine.match(LINE_PATTERN);
36
+ if (!lSplitLine?.groups) {
37
+ return pTrimmedLine;
33
38
  }
34
- return `${lSplitLine.groups.filesPattern} ${Array.from(new Set(lSplitLine.groups.theRest.trim().split(/\s+/))).join(" ")}`;
39
+ let lUserNames = lSplitLine.groups.userNames.trim();
40
+ for (let lTeamName of Object.keys(pTeamMap)) {
41
+ lUserNames = lUserNames.replace(new RegExp(`(\\s|^)@${lTeamName}(\\s|$)`, "g"), `$1${stringifyTeamMembers(pTeamMap, lTeamName)}$2`);
42
+ }
43
+ return `${lSplitLine.groups.filesPattern}${lUserNames}`;
35
44
  }
36
- function shouldAppearInResult(pLine) {
37
- return !pLine.trimStart().startsWith("#!");
45
+ function stringifyTeamMembers(pTeamMap, pTeamName) {
46
+ return pTeamMap[pTeamName].map((pUserName) => `@${pUserName}`).join(" ");
38
47
  }
39
- export function convert(pCodeOwnersFileAsString, pTeamMap, pGeneratedWarning = DEFAULT_GENERATED_WARNING) {
40
- return `${pGeneratedWarning}${pCodeOwnersFileAsString
41
- .split(EOL)
42
- .filter(shouldAppearInResult)
43
- .map(convertLine(pTeamMap))
44
- .map(deduplicateUserNames)
45
- .join(EOL)}`;
48
+ function deduplicateUserNames(pTrimmedLine) {
49
+ const lSplitLine = pTrimmedLine.match(LINE_PATTERN);
50
+ if (pTrimmedLine.startsWith("#") || !lSplitLine?.groups) {
51
+ return pTrimmedLine;
52
+ }
53
+ return `${lSplitLine.groups.filesPattern}${Array.from(new Set(lSplitLine.groups.userNames.trim().split(/\s+/)))
54
+ .sort()
55
+ .join(" ")}`;
46
56
  }
package/dist/version.js CHANGED
@@ -1 +1 @@
1
- export const VERSION = "2.1.0";
1
+ export const VERSION = "2.2.0";
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "virtual-code-owners",
3
- "version": "2.1.0",
3
+ "version": "2.2.0",
4
4
  "description": "Merges a VIRTUAL-CODEOWNERS.txt and a virtual-teams.yml into CODEOWNERS",
5
5
  "type": "module",
6
6
  "exports": {
@@ -54,17 +54,17 @@
54
54
  "devDependencies": {
55
55
  "@types/js-yaml": "4.0.5",
56
56
  "@types/mocha": "10.0.1",
57
- "@types/node": "18.14.6",
57
+ "@types/node": "18.15.3",
58
58
  "c8": "7.13.0",
59
- "dependency-cruiser": "12.10.0",
59
+ "dependency-cruiser": "12.10.2",
60
60
  "husky": "8.0.3",
61
- "lint-staged": "13.1.2",
61
+ "lint-staged": "13.2.0",
62
62
  "mocha": "10.2.0",
63
63
  "prettier": "2.8.4",
64
64
  "ts-node": "10.9.1",
65
- "typescript": "4.9.5",
65
+ "typescript": "5.0.2",
66
66
  "upem": "7.3.2",
67
- "watskeburt": "0.10.0"
67
+ "watskeburt": "0.10.1"
68
68
  },
69
69
  "dependencies": {
70
70
  "commander": "10.0.0",