@hanseltime/template-repo-sync 1.1.0 → 1.3.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.
Files changed (72) hide show
  1. package/CHANGELOG.md +14 -0
  2. package/README.md +14 -0
  3. package/docs/merge-plugins/CURRENT_PLUGINS.md +168 -0
  4. package/docs/merge-plugins/DEVELOPMENT.md +129 -0
  5. package/docs/merge-plugins/README.md +85 -0
  6. package/lib/cjs/checkout-drivers/git-checkout.d.ts +8 -0
  7. package/lib/cjs/checkout-drivers/git-checkout.js +17 -0
  8. package/lib/cjs/checkout-drivers/index.d.ts +2 -0
  9. package/lib/cjs/checkout-drivers/index.js +18 -0
  10. package/lib/cjs/checkout-drivers/types.d.ts +14 -0
  11. package/lib/cjs/checkout-drivers/types.js +2 -0
  12. package/lib/cjs/clone-drivers/git-clone.d.ts +2 -1
  13. package/lib/cjs/clone-drivers/git-clone.js +4 -1
  14. package/lib/cjs/clone-drivers/types.d.ts +12 -1
  15. package/lib/cjs/plugins/json-merge.js +30 -7
  16. package/lib/cjs/template-sync.d.ts +13 -0
  17. package/lib/cjs/template-sync.js +47 -8
  18. package/lib/cjs/types.d.ts +1 -1
  19. package/lib/esm/checkout-drivers/git-checkout.js +17 -0
  20. package/lib/esm/checkout-drivers/index.js +18 -0
  21. package/lib/esm/checkout-drivers/types.js +2 -0
  22. package/lib/esm/clone-drivers/git-clone.js +4 -1
  23. package/lib/esm/plugins/json-merge.js +30 -7
  24. package/lib/esm/template-sync.js +47 -8
  25. package/package.json +5 -8
  26. package/src/checkout-drivers/git-checkout.spec.ts +58 -0
  27. package/src/checkout-drivers/git-checkout.ts +22 -0
  28. package/src/checkout-drivers/index.ts +2 -0
  29. package/src/checkout-drivers/types.ts +14 -0
  30. package/src/clone-drivers/git-clone.ts +6 -2
  31. package/src/clone-drivers/types.ts +13 -1
  32. package/src/plugins/json-merge.spec.ts +86 -0
  33. package/src/plugins/json-merge.ts +9 -7
  34. package/src/template-sync.spec.ts +53 -2
  35. package/src/template-sync.ts +46 -9
  36. package/src/types.ts +1 -1
  37. package/test-fixtures/testGitRepo/README.md +17 -0
  38. package/test-fixtures/testGitRepo/gitDir/COMMIT_EDITMSG +14 -0
  39. package/test-fixtures/testGitRepo/gitDir/HEAD +1 -0
  40. package/test-fixtures/testGitRepo/gitDir/config +7 -0
  41. package/test-fixtures/testGitRepo/gitDir/description +1 -0
  42. package/test-fixtures/testGitRepo/gitDir/hooks/applypatch-msg.sample +15 -0
  43. package/test-fixtures/testGitRepo/gitDir/hooks/commit-msg.sample +24 -0
  44. package/test-fixtures/testGitRepo/gitDir/hooks/fsmonitor-watchman.sample +174 -0
  45. package/test-fixtures/testGitRepo/gitDir/hooks/post-update.sample +8 -0
  46. package/test-fixtures/testGitRepo/gitDir/hooks/pre-applypatch.sample +14 -0
  47. package/test-fixtures/testGitRepo/gitDir/hooks/pre-commit.sample +49 -0
  48. package/test-fixtures/testGitRepo/gitDir/hooks/pre-merge-commit.sample +13 -0
  49. package/test-fixtures/testGitRepo/gitDir/hooks/pre-push.sample +53 -0
  50. package/test-fixtures/testGitRepo/gitDir/hooks/pre-rebase.sample +169 -0
  51. package/test-fixtures/testGitRepo/gitDir/hooks/pre-receive.sample +24 -0
  52. package/test-fixtures/testGitRepo/gitDir/hooks/prepare-commit-msg.sample +42 -0
  53. package/test-fixtures/testGitRepo/gitDir/hooks/push-to-checkout.sample +78 -0
  54. package/test-fixtures/testGitRepo/gitDir/hooks/sendemail-validate.sample +77 -0
  55. package/test-fixtures/testGitRepo/gitDir/hooks/update.sample +128 -0
  56. package/test-fixtures/testGitRepo/gitDir/index +0 -0
  57. package/test-fixtures/testGitRepo/gitDir/info/exclude +6 -0
  58. package/test-fixtures/testGitRepo/gitDir/logs/HEAD +5 -0
  59. package/test-fixtures/testGitRepo/gitDir/logs/refs/heads/master +2 -0
  60. package/test-fixtures/testGitRepo/gitDir/logs/refs/heads/test-branch +2 -0
  61. package/test-fixtures/testGitRepo/gitDir/objects/4b/825dc642cb6eb9a060e54bf8d69288fbee4904 +0 -0
  62. package/test-fixtures/testGitRepo/gitDir/objects/6e/187bee8d02f39d0a1be8331dd8fe6a00c9b613 +0 -0
  63. package/test-fixtures/testGitRepo/gitDir/objects/73/185f1f3f5a6345e087d9f46dc4af77cc59449f +2 -0
  64. package/test-fixtures/testGitRepo/gitDir/objects/90/e7ea1089f939840e9649fd617584c1ad117159 +3 -0
  65. package/test-fixtures/testGitRepo/gitDir/objects/ba/99a452b9097047e9bfa8d5a08b3e452fcb364a +0 -0
  66. package/test-fixtures/testGitRepo/gitDir/objects/c5/8d400177cd5180b8566f82a127fafc5bf394b7 +0 -0
  67. package/test-fixtures/testGitRepo/gitDir/objects/e2/e668265db019249a7e8296d85f79000e3d71cf +0 -0
  68. package/test-fixtures/testGitRepo/gitDir/objects/e4/243e430c1ab69f3e344249f5b1859e90abc883 +1 -0
  69. package/test-fixtures/testGitRepo/gitDir/objects/ec/6c1cb72312605282ac61858cf1eaf1ea9f1d02 +0 -0
  70. package/test-fixtures/testGitRepo/gitDir/objects/fc/89cecc4ac0b5b075bd7d0ce9e09b2f50598b82 +0 -0
  71. package/test-fixtures/testGitRepo/gitDir/refs/heads/master +1 -0
  72. package/test-fixtures/testGitRepo/gitDir/refs/heads/test-branch +1 -0
package/CHANGELOG.md CHANGED
@@ -1,3 +1,17 @@
1
+ # [1.3.0](https://github.com/HanseltimeIndustries/template-repo-sync/compare/v1.2.0...v1.3.0) (2024-06-09)
2
+
3
+
4
+ ### Features
5
+
6
+ * support specifying the template branch ([54bad24](https://github.com/HanseltimeIndustries/template-repo-sync/commit/54bad24935bb8609617b8d30409aa8a47fc64139))
7
+
8
+ # [1.2.0](https://github.com/HanseltimeIndustries/template-repo-sync/compare/v1.1.0...v1.2.0) (2024-03-11)
9
+
10
+
11
+ ### Features
12
+
13
+ * adding comment-json support for merges ([c4393aa](https://github.com/HanseltimeIndustries/template-repo-sync/commit/c4393aaa6bf3bb985670f4377f2a370338450618))
14
+
1
15
  # [1.1.0](https://github.com/HanseltimeIndustries/template-repo-sync/compare/v1.0.1...v1.1.0) (2024-03-04)
2
16
 
3
17
 
package/README.md CHANGED
@@ -13,6 +13,16 @@ best practice development patterns, then we naturally want to have a way to allo
13
13
  changes, while also having control over things that may be specifically changed due to their need to support something beyond the
14
14
  orgnaization standard.
15
15
 
16
+ - [Template Sync](#template-sync)
17
+ - [How to use this](#how-to-use-this)
18
+ - [Config file](#config-file)
19
+ - [File format](#file-format)
20
+ - [Example 1 - Using a custom plugin](#example-1---using-a-custom-plugin)
21
+ - [Example 2 - Using a custom plugin for some paths](#example-2---using-a-custom-plugin-for-some-paths)
22
+ - [From SHA/Tag directive](#from-shatag-directive)
23
+ - [Programmatic API](#programmatic-api)
24
+ <!-- Created with Markdown All In One VsCode Entension, rerun to update -->
25
+
16
26
  # How to use this
17
27
 
18
28
  This repository publishes a github action that can be used for ease of use in github. It also provides itself as an npm package
@@ -32,6 +42,10 @@ This library will always respect the overrides of the local template sync file i
32
42
  templates and their repos, will also provide a list of all files whose template sync behavior was either ignored or overridden by the local
33
43
  file. In this way, teams should be able to track (with a little extra CI/CD wiring) or at the very least, explicitly acknowledge a deviation.
34
44
 
45
+ All config files have the ability to write custom merge plugins either in repo or published as packages for larger use.
46
+
47
+ Please see the [plugins](./docs/merge-plugins/) documentation for more information beyond the simple examples in this readme.
48
+
35
49
  ### File format
36
50
 
37
51
  ```typescript
@@ -0,0 +1,168 @@
1
+ # Current Merge Plugins
2
+
3
+ This document lists all merge plugins that are provided provided as defaults for certain file extensions.
4
+ These should be found in the [plugins folder](src/plugins)
5
+
6
+ - [Current Merge Plugins](#current-merge-plugins)
7
+ - [Json Merge Plugin](#json-merge-plugin)
8
+ - [Configuration Options:](#configuration-options)
9
+ - [Simple merge spec](#simple-merge-spec)
10
+ - [JsonPath config](#jsonpath-config)
11
+ - [Example](#example)
12
+ - [About Comments](#about-comments)
13
+
14
+ <!-- Created with Markdown All In One VsCode Extension -->
15
+
16
+ ## Json Merge Plugin
17
+
18
+ The json merge plugin allows you to configure jsonpath based merges on any .json file.
19
+
20
+ ## Configuration Options:
21
+
22
+ ### Simple merge spec
23
+
24
+ At it's simplest, you can take advantage of lodash merge behavior by just specifying one of:
25
+
26
+ - overwrite - the template completely overwrites the file
27
+ - merge-template - keys are merged together with the template overwriting any matching keys on local file
28
+ - merge-current - keys are merged together with the local file keeping any keys that match in the template
29
+
30
+ Example config:
31
+
32
+ ```json
33
+ {
34
+ "merge": {
35
+ ".json": {
36
+ "rules": [
37
+ {
38
+ "glob": "metadata.json",
39
+ "options": "merge-template"
40
+ },
41
+ {
42
+ "glob": "template-lock.json",
43
+ "options": "overwrite"
44
+ },
45
+ {
46
+ "glob": "package.json",
47
+ "options": "merge-current"
48
+ }
49
+ ]
50
+ }
51
+ }
52
+ }
53
+ ```
54
+
55
+ ### JsonPath config
56
+
57
+ If you would like further control over what merges within a .json file, you can actually specify, via way of jsonpath operators,
58
+ the level of merge per field.
59
+
60
+ A few rules:
61
+
62
+ - Once you have provided jsonpath options, only the json path options (or new fields if the option is enabled) will be merged
63
+ - jsonpaths are run from first to last. This means you can layer merges.
64
+
65
+ ```typescript
66
+ interface Options {
67
+ /**
68
+ * If set to true, this means we won't add new properties from the template
69
+ */
70
+ ignoreNewProperties?: boolean;
71
+ /**
72
+ * If set to true, overwrite will apply undefined values as deleted for the jsonpaths
73
+ * or for values that are supposed to be merged on top of other values
74
+ */
75
+ missingIsDelete?: boolean;
76
+ /**
77
+ * Note, if multiple json paths match a rule, we pick the first one in the list that matches
78
+ */
79
+ paths: /**
80
+ * We only override jsonpaths. Anything not specified is kept the same.
81
+ */
82
+ [jsonPath: `$.${string}`, options: BaseJsonMergeOptions][];
83
+ }
84
+ ```
85
+
86
+ #### Example
87
+
88
+ This
89
+
90
+ ```json
91
+ {
92
+ "merge": {
93
+ ".json": {
94
+ "rules": [
95
+ {
96
+ "glob": "metadata.json",
97
+ "options": {
98
+ "ignoreNewProperties": false,
99
+ "missingIsDelete:": true,
100
+ "paths": [
101
+ ["$.path", "template-merge"] // if we delete path in the template, it will delete the path
102
+ ]
103
+ }
104
+ },
105
+ {
106
+ "glob": "template-lock.json",
107
+ "options": "overwrite"
108
+ },
109
+ {
110
+ "glob": "package.json",
111
+ "options": {
112
+ "ignoreNewProperties": false,
113
+ "paths": [
114
+ ["$.scripts.*", "template-merge"],
115
+ ["$.scripts.specific-script", "template-currrent"] // We end up keeping the current template
116
+ ]
117
+ }
118
+ }
119
+ ]
120
+ }
121
+ }
122
+ }
123
+ ```
124
+
125
+ ### About Comments
126
+
127
+ There are numerous json files that support comments now; tsconfig.json is a prime example of this. In order to support this,
128
+ this library makes use of comment-json for parsing and stringifying. This means that, minimally, you will not run into errors
129
+ when merging commented json files (and that you can comment on your templatesync config files).
130
+
131
+ One thing to note however, is that only include comments from the template if they are inside of an object that is being merged.
132
+ This is because this plugin has not yet defined a good configuration for merging comments. If you run into a pertinent need for this,
133
+ please feel free to open an issue and potentially contribute a fix in a PR.
134
+
135
+ Example of comment merging:
136
+
137
+ ```json
138
+ // In template
139
+
140
+ {
141
+ // I have a comment here
142
+ "newField": 44,
143
+ "overridingField": {
144
+ // Comment in here
145
+ "value": "v",
146
+ }
147
+ }
148
+
149
+ // In the extending repo
150
+ {
151
+ // My custom comment
152
+ "newField": 88,
153
+ "overridingField": 66
154
+ }
155
+
156
+ // After merging with template-merge
157
+ {
158
+ // My custom comment
159
+ "newField": 44,
160
+ "overridingField": {
161
+ // Comment in here
162
+ "value": "v",
163
+ }
164
+ }
165
+ ```
166
+
167
+ From the above example, you can see that we specifically keep as many of the comments as possible from the extending repo
168
+ and only the comment that was fully nested inside new value that we were adding was kept.
@@ -0,0 +1,129 @@
1
+ # Plugin Development
2
+
3
+ - [Plugin Development](#plugin-development)
4
+ - [Example: hello \<world\>](#example-hello-world) - [Example one: local file](#example-one-local-file) - [Example two: npm package](#example-two-npm-package)
5
+ <!-- Created with Markdown All In One VsCode Extension -->
6
+
7
+ The templatesync.json and templatesync.local.config files make use of a `"merge"` property where you can
8
+ customize the baseline behavior of ignore or overwrite from template.
9
+
10
+ This library provides a set of typescript types for you to create additional plugins.
11
+
12
+ At the core of it, you need to have a file or npm package that exposes the interface:
13
+
14
+ ```typescript
15
+ export interface MergePlugin<PluginOptions> {
16
+ /**
17
+ * This method will be called when a file from the template and it's analog in the downstream repo
18
+ * have some differences. The plugin must perform the merge and return the appropriate file contents
19
+ * as a string
20
+ *
21
+ * TODO: we may create a V2 plugin that could deal with large files and not pass around strings in memory,
22
+ * but for now, this is the current implementation
23
+ *
24
+ * @param current - The downstream repo's current file contents
25
+ * @param fromTemplateRepo - the current
26
+ * @param context - an object defining the context around the file and the specific options
27
+ */
28
+ merge(
29
+ current: string,
30
+ fromTemplateRepo: string,
31
+ context: MergeContext<PluginOptions>,
32
+ ): Promise<string>;
33
+ /**
34
+ * Given an options object for the merge, this validates the options object and returns error messages if there is anything wrong.
35
+ * @param options any json value that the user provided - must be validated against the expected options
36
+ */
37
+ validate(options: unknown): string[] | undefined;
38
+ }
39
+ ```
40
+
41
+ ## Example: hello \<world>
42
+
43
+ So let's say that we want to have a plugin that will take every file assigned to it, and just write hello {world} instead.
44
+ (Not much of a merge, but so it goes)
45
+
46
+ We will define and export an options object, validate function, and merge function
47
+
48
+ ```typescript
49
+ // src/hello-plugin.ts
50
+ import { MergePlugin, MergeContext } from '@hanseltime/template-repo-sync'
51
+
52
+ export interface HelloOptions: {
53
+ /** the name of the world we're greeting */
54
+ world: string
55
+ }
56
+
57
+ export const validate: MergePlugin<HelloOptions>['validate'] = (options: unknown) => {
58
+ const errors: string[] = [];
59
+ // In our case, we have decided you HAVE to use an object
60
+ if (typeof options !== 'object') {
61
+ errors.push('must provide an object');
62
+ return errors;
63
+ }
64
+
65
+ // make sure there aren't extra keys
66
+ const { world, ...rest } = options;
67
+ const unknownKeys = Object.keys(rest);
68
+ if (unknownKeys.length > 0 ) {
69
+ errors.push(`Unexpected options keys: ${unknownKeys.join(' ')}`);
70
+ }
71
+
72
+ if (!world) {
73
+ errors.push(`Must provide a valid world value`);
74
+ }
75
+
76
+ return errors
77
+ }
78
+
79
+ export const merge: MergePlugin<HelloOptions>['merge'] = async (current, fromTemplateRepo, options: HelloOptions) => {
80
+ // Note, we don't use the current with this simple plugin, but we would use the first 2 args normally
81
+ return `Hello ${options.world}`
82
+ }
83
+
84
+ ```
85
+
86
+ With all of that set up, as long as we have the package available to the pacakge manager running our script, we can use it:
87
+
88
+ ### Example one: local file
89
+
90
+ ```json
91
+ {
92
+ "merge": {
93
+ ".txt": {
94
+ "plugin": "dist/hello-plugin.js", // Note, we make it point to the compiled .js so you will need to build and commit the file
95
+ "rules": [
96
+ {
97
+ "glob": "**/*",
98
+ "options": {
99
+ "world": "chad"
100
+ }
101
+ }
102
+ ]
103
+ }
104
+ }
105
+ }
106
+ ```
107
+
108
+ ### Example two: npm package
109
+
110
+ Let's assume that you published this as an npm package to @myscope/hello-merge. Once you have install the pacakge to the project, you can
111
+ simply reference the package (assuming that it exposes the required functions as it's index file).
112
+
113
+ ```json
114
+ {
115
+ "merge": {
116
+ ".txt": {
117
+ "plugin": "@myscope/hello-merge",
118
+ "rules": [
119
+ {
120
+ "glob": "**/*",
121
+ "options": {
122
+ "world": "chad"
123
+ }
124
+ }
125
+ ]
126
+ }
127
+ }
128
+ }
129
+ ```
@@ -0,0 +1,85 @@
1
+ # Merge Plugins
2
+
3
+ The templatesync.json and templatesync.local.config files make use of a `"merge"` property where you can
4
+ customize the baseline behavior of just ignoring or overwriting from the template.
5
+
6
+ # Example Use Case
7
+
8
+ One example of this behavior is around an npm package.json. If you were making a template for a particular
9
+ set of boilerplate for an npm package, you would probably provide an example package.json like:
10
+
11
+ ```json
12
+ {
13
+ "name": "<fill in your package name",
14
+ "description": "<fill in your package description",
15
+ "license": "MIT",
16
+ "scripts": {
17
+ "build": "tsc",
18
+ "publish": "our-artifact-script"
19
+ },
20
+ "devDependencies": {
21
+ "typescript": "^5.0.0",
22
+ "our-artifact-package": "^1.0.0"
23
+ }
24
+ }
25
+ ```
26
+
27
+ In this scenario, we expect the template user to declare their own `name` and `description`, and add their own
28
+ `scripts` and `devDependencies`. However, we are hoping to make sure that the publish method and and its
29
+ our-artifact-package are kept up-to-date on syncs. Because of this, we would make use of the default json merge
30
+ plugin that is built-in with this library:
31
+
32
+ ```json
33
+ {
34
+ "merge": {
35
+ ".json": {
36
+ // This uses the default plugin for json merges
37
+ "rules": [
38
+ {
39
+ "glob": "package.json",
40
+ "options": {
41
+ "paths": [
42
+ ["$.scripts.publish", "merge-template"], // Any changes to publish are so critical that we want them to sync
43
+ ["$.devDependencies", "merge-template"] // Always ensure dev dependency versions for our scripts are updated
44
+ ]
45
+ }
46
+ }
47
+ ]
48
+ }
49
+ }
50
+ }
51
+ ```
52
+
53
+ As a repo maintainer, we can be sure that when people sync from our repo in its current state, the publish script
54
+ and devDependency should be synced from package.json, without anything else!
55
+
56
+ ## What if the repo extender is annoyed?
57
+
58
+ If the repo extender already made the decision to update the publish method for a good reason, they may find it
59
+ tedious to constantly get their publish script overwritten and then have to undo it. Due to the local
60
+ config file, they can specify their own merge configuration for the package.json.
61
+
62
+ ```json
63
+ {
64
+ "merge": {
65
+ ".json": {
66
+ // This uses the default plugin for json merges
67
+ "rules": [
68
+ {
69
+ "glob": "package.json",
70
+ "options": {
71
+ "paths": [
72
+ ["$.devDependencies", "merge-template"] // Always ensure dev dependency versions for our scripts are updated
73
+ ]
74
+ }
75
+ }
76
+ ]
77
+ }
78
+ }
79
+ }
80
+ ```
81
+
82
+ This configuration will now override the template repo's merge and only allow devDependencies to be updated. We report
83
+ this override as part of the output of the sync call, and for things like our
84
+ [github action](https://github.com/HanseltimeIndustries/template-repo-sync-action), we format that output into the PR
85
+ that is opened up when performing a sync.
@@ -0,0 +1,8 @@
1
+ export declare function gitCheckout(options: {
2
+ /** The directory where we cloned to */
3
+ tmpDir: string;
4
+ /** The name of the remote that git checks out against */
5
+ remoteName: string;
6
+ /** The branch to checkout against */
7
+ branch: string;
8
+ }): Promise<boolean>;
@@ -0,0 +1,17 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.gitCheckout = void 0;
4
+ const child_process_1 = require("child_process");
5
+ async function gitCheckout(options) {
6
+ const { branch, remoteName, tmpDir } = options;
7
+ (0, child_process_1.execSync)(`git fetch ${remoteName} ${branch}`, {
8
+ cwd: tmpDir,
9
+ env: process.env,
10
+ });
11
+ (0, child_process_1.execSync)(`git checkout -b ${branch} --track ${remoteName}/${branch}`, {
12
+ cwd: tmpDir,
13
+ env: process.env,
14
+ });
15
+ return true;
16
+ }
17
+ exports.gitCheckout = gitCheckout;
@@ -0,0 +1,2 @@
1
+ export * from "./git-checkout";
2
+ export * from "./types";
@@ -0,0 +1,18 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __exportStar = (this && this.__exportStar) || function(m, exports) {
14
+ for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
15
+ };
16
+ Object.defineProperty(exports, "__esModule", { value: true });
17
+ __exportStar(require("./git-checkout"), exports);
18
+ __exportStar(require("./types"), exports);
@@ -0,0 +1,14 @@
1
+ /**
2
+ * A function that will checkout a given "branch" after the repo has been
3
+ * "cloned" by a clone drvier.
4
+ *
5
+ * @returns true if the checkout succeeded
6
+ */
7
+ export type TemplateCheckoutDriverFn = (options: {
8
+ /** The directory where we cloned to */
9
+ tmpDir: string;
10
+ /** The name of the remote that git checks out against */
11
+ remoteName: string;
12
+ /** The branch to checkout against */
13
+ branch: string;
14
+ }) => Promise<boolean>;
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -1 +1,2 @@
1
- export declare function gitClone(tmpDir: string, repoUrl: string): Promise<string>;
1
+ import { CloneReturn } from "./types";
2
+ export declare function gitClone(tmpDir: string, repoUrl: string): Promise<CloneReturn>;
@@ -9,6 +9,9 @@ async function gitClone(tmpDir, repoUrl) {
9
9
  cwd: tmpDir,
10
10
  env: process.env,
11
11
  });
12
- return (0, path_1.resolve)(tmpDir, CLONE_DIR);
12
+ return {
13
+ dir: (0, path_1.resolve)(tmpDir, CLONE_DIR),
14
+ remoteName: "origin",
15
+ };
13
16
  }
14
17
  exports.gitClone = gitClone;
@@ -1,5 +1,16 @@
1
+ /**
2
+ * @deprecated - return the remote name in the CloneReturn
3
+ */
4
+ type CloneDir = string;
5
+ export interface CloneReturn {
6
+ /** The directory where the clone occurred - absolute path to avoid working dir issues */
7
+ dir: string;
8
+ /** The name of the remote for the particular technology that you used - passed to checkout drivers */
9
+ remoteName: string;
10
+ }
1
11
  /**
2
12
  * A function that clones the template repo into the provided tmpDir
3
13
  * and then returns the relative path within that directory to the template root
4
14
  */
5
- export type TemplateCloneDriverFn = (tmpDir: string, repoUrl: string) => Promise<string>;
15
+ export type TemplateCloneDriverFn = (tmpDir: string, repoUrl: string) => Promise<CloneReturn | CloneDir>;
16
+ export {};
@@ -1,13 +1,36 @@
1
1
  "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || function (mod) {
19
+ if (mod && mod.__esModule) return mod;
20
+ var result = {};
21
+ if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
22
+ __setModuleDefault(result, mod);
23
+ return result;
24
+ };
2
25
  var __importDefault = (this && this.__importDefault) || function (mod) {
3
26
  return (mod && mod.__esModule) ? mod : { "default": mod };
4
27
  };
5
28
  Object.defineProperty(exports, "__esModule", { value: true });
6
29
  exports.merge = exports.validate = void 0;
7
30
  const lodash_merge_1 = __importDefault(require("lodash.merge"));
8
- const lodash_clonedeep_1 = __importDefault(require("lodash.clonedeep"));
9
31
  const jsonpath_1 = __importDefault(require("jsonpath"));
10
32
  const infer_json_indent_1 = require("../formatting/infer-json-indent");
33
+ const commentJSON = __importStar(require("comment-json"));
11
34
  function stringOptionError(value) {
12
35
  if (value === "overwrite" ||
13
36
  value === "merge-template" ||
@@ -78,18 +101,18 @@ async function merge(current, fromTemplateRepo, context) {
78
101
  if (context.mergeArguments === "overwrite") {
79
102
  return fromTemplateRepo;
80
103
  }
81
- const currentJson = JSON.parse(current);
82
- const fromTemplateJson = JSON.parse(fromTemplateRepo);
104
+ const currentJson = commentJSON.parse(current);
105
+ const fromTemplateJson = commentJSON.parse(fromTemplateRepo);
83
106
  if (context.mergeArguments === "merge-current") {
84
107
  // Performs Lodash Merge with current as the override
85
- return JSON.stringify((0, lodash_merge_1.default)(fromTemplateJson, currentJson), null, (0, infer_json_indent_1.inferJSONIndent)(current));
108
+ return commentJSON.stringify((0, lodash_merge_1.default)(fromTemplateJson, currentJson), null, (0, infer_json_indent_1.inferJSONIndent)(current));
86
109
  }
87
110
  if (context.mergeArguments === "merge-template") {
88
111
  // Performs Lodash Merge with current as the override
89
- return JSON.stringify((0, lodash_merge_1.default)(currentJson, fromTemplateJson), null, (0, infer_json_indent_1.inferJSONIndent)(current));
112
+ return commentJSON.stringify((0, lodash_merge_1.default)(currentJson, fromTemplateJson), null, (0, infer_json_indent_1.inferJSONIndent)(current));
90
113
  }
91
114
  const { missingIsDelete, ignoreNewProperties, paths } = context.mergeArguments;
92
- const returnJson = (0, lodash_clonedeep_1.default)(currentJson);
115
+ const returnJson = commentJSON.parse(current);
93
116
  paths.forEach((p) => {
94
117
  const [jPath, overrideType] = p;
95
118
  const fromTemplatePaths = new Map();
@@ -143,7 +166,7 @@ async function merge(current, fromTemplateRepo, context) {
143
166
  }
144
167
  });
145
168
  }
146
- return JSON.stringify(returnJson, null, (0, infer_json_indent_1.inferJSONIndent)(current));
169
+ return commentJSON.stringify(returnJson, null, (0, infer_json_indent_1.inferJSONIndent)(current));
147
170
  }
148
171
  exports.merge = merge;
149
172
  /**
@@ -2,8 +2,17 @@ import { Change } from "diff";
2
2
  import { TemplateCloneDriverFn } from "./clone-drivers";
3
3
  import { TemplateDiffDriverFn } from "./diff-drivers";
4
4
  import { TemplateRefDriverFn } from "./ref-drivers/types";
5
+ import { TemplateCheckoutDriverFn } from "./checkout-drivers";
5
6
  export interface TemplateSyncOptions {
7
+ /**
8
+ * This is the url of the template repo
9
+ */
6
10
  repoUrl: string;
11
+ /**
12
+ * Optional Branch to check out - if not specified, this checks out the
13
+ * default branch of the template repo
14
+ */
15
+ branch?: string;
7
16
  /**
8
17
  * The directory for cloning our template repo into via the cloneDriver
9
18
  */
@@ -29,6 +38,10 @@ export interface TemplateSyncOptions {
29
38
  * Defaults to using git current ref
30
39
  */
31
40
  currentRefDriver?: TemplateRefDriverFn;
41
+ /**
42
+ * Defaults to using git checkout driver
43
+ */
44
+ checkoutDriver?: TemplateCheckoutDriverFn;
32
45
  }
33
46
  export interface TemplateSyncReturn {
34
47
  /**