1 | # copy-files-from-to
|
2 | Copy files from one path to another, based on the instructions provided in a configuration file.
|
3 |
|
4 | # Use cases
|
5 |
|
6 | * This tool is useful when a few files need to be copied / updated frequently
|
7 | * This tool works as a basic alternative for `npm` / `bower` when you wish to copy the scripts out of `node_modules` / `bower_components` folder
|
8 | * You may like to use this tool if you prefer to keep some third-party dependencies (eg: from `node_modules`) updated and/or committed to your project's repository
|
9 |
|
10 |
|
11 | # Installation
|
12 | ```sh
|
13 | $ npm install -g copy-files-from-to
|
14 | ```
|
15 |
|
16 | # How to use
|
17 | In your `package.json` file, add the `"copyFiles"` and `"copyFilesSettings"` (optional) instructions as described in this section.
|
18 |
|
19 | Alternatively, you may create a file, say, `copy-files-from-to.json` or `copy-files-from-to.cjson` [(JSON with comments)](https://github.com/kof/node-cjson) in your project and refer to the following usage examples.
|
20 |
|
21 | ## Basic usage
|
22 | Sample file: [package.json](test/test-copy-instructions-from-package-json/package.json)
|
23 | ```json
|
24 | {
|
25 | "name": "my-application",
|
26 | "version": "1.0.0",
|
27 | "dependencies": {
|
28 | "jquery": "3.4.0"
|
29 | },
|
30 | "copyFiles": [
|
31 | {
|
32 | "from": "node_modules/jquery/dist/jquery.js",
|
33 | "to": "scripts/jquery/jquery.js"
|
34 | },
|
35 | {
|
36 | "from": "https://raw.githubusercontent.com/webextensions/console-panel/master/src/console-panel.js",
|
37 | "to": "scripts/console-panel/console-panel.js"
|
38 | },
|
39 | {
|
40 | "from": "https://raw.githubusercontent.com/webextensions/console-panel/master/src/console-panel.css",
|
41 | "to": "scripts/console-panel/console-panel.css"
|
42 | }
|
43 | ]
|
44 | }
|
45 | ```
|
46 |
|
47 | Sample file: [copy-file-from-to.json](test/basic-usage/copy-files-from-to.json)
|
48 | ```json
|
49 | {
|
50 | "copyFiles": [
|
51 | {
|
52 | "from": "node_modules/jquery/dist/jquery.js",
|
53 | "to": "scripts/jquery/jquery.js"
|
54 | },
|
55 | {
|
56 | "from": "https://raw.githubusercontent.com/webextensions/console-panel/master/src/console-panel.js",
|
57 | "to": "scripts/console-panel/console-panel.js"
|
58 | },
|
59 | {
|
60 | "from": "https://raw.githubusercontent.com/webextensions/console-panel/master/src/console-panel.css",
|
61 | "to": "scripts/console-panel/console-panel.css"
|
62 | }
|
63 | ]
|
64 | }
|
65 | ```
|
66 |
|
67 | ### Command and output
|
68 | ```
|
69 | $ copy-files-from-to
|
70 | ```
|
71 |
|
72 | ```
|
73 | Reading copy instructions from file copy-files-from-to.json
|
74 |
|
75 | Starting copy operation in "default" mode:
|
76 | ✓ Copied [ utf8 ] node_modules/jquery/dist/jquery.js to scripts/jquery/jquery.js
|
77 | ✓ Copied [binary] assets/logo.png to build/logo.png
|
78 | ✓ Copied [remote] https://raw.githubusercontent.com/webextensions/console-panel/master/src/console-panel.css to scripts/console-panel/console-panel.css
|
79 | ✓ Copied [remote] https://raw.githubusercontent.com/webextensions/console-panel/master/src/console-panel.js to scripts/console-panel/console-panel.js
|
80 | ```
|
81 |
|
82 |
|
83 | ## Advanced usage
|
84 | Sample file: [copy-files-from-to.cjson](test/advanced-usage/copy-files-from-to.cjson)
|
85 | ```js
|
86 | // This is a CJSON file (JSON with comments)
|
87 | {
|
88 | "copyFiles": [
|
89 | // In "development" mode, copy from the full version of the library, in all other modes, use the minified version
|
90 | {
|
91 | "from": {
|
92 | "default": "https://raw.githubusercontent.com/jashkenas/underscore/master/underscore-min.js",
|
93 | "development": "https://raw.githubusercontent.com/jashkenas/underscore/master/underscore.js"
|
94 | },
|
95 | "to": "scripts/underscore.js"
|
96 | },
|
97 |
|
98 | // Copy this file only in "pre-production" mode
|
99 | {
|
100 | "from": "https://raw.githubusercontent.com/jashkenas/underscore/master/underscore-min.js.map",
|
101 | "to": {
|
102 | "default": {
|
103 | "skip": true
|
104 | },
|
105 | "pre-production": "scripts/underscore.js.map"
|
106 | }
|
107 | },
|
108 |
|
109 | // Copy this file in "pre-production" and "production" mode only
|
110 | {
|
111 | "from": {
|
112 | "default": {
|
113 | "skip": true
|
114 | },
|
115 | "pre-production": "node_modules/native-promise-only/npo.js",
|
116 | "production": "node_modules/native-promise-only/npo.js"
|
117 | },
|
118 | "to": "scripts/native-promise-only.js"
|
119 | },
|
120 |
|
121 | // Copy this file in all modes except "production" mode
|
122 | {
|
123 | "from": "https://raw.githubusercontent.com/webextensions/console-panel/master/src/console-panel.js",
|
124 | "to": {
|
125 | "default": "scripts/console-panel/console-panel.js",
|
126 | "production": {
|
127 | "skip": true
|
128 | }
|
129 | }
|
130 | },
|
131 |
|
132 | // Copy the files matching the "glob" pattern (matching files, along with the their folder structure go into the "to" directory)
|
133 | {
|
134 | "from": "assets/**/*.jpg",
|
135 | "to": "public/images/"
|
136 | },
|
137 |
|
138 | // Copy the files matching the "glob" pattern (all of the matching files directly go into the "to" directory) since "toFlat" is set to "true"
|
139 | {
|
140 | "from": "assets/**/*.jpg",
|
141 | "to": "public/copy-all-jpg-files-to-this-directory/",
|
142 | "toFlat": true
|
143 | }
|
144 | ],
|
145 | "copyFilesSettings": {
|
146 | "whenFileExists": "notify-about-available-change",
|
147 | "removeSourceMappingURL": false,
|
148 | "uglifyJs": false,
|
149 | "addReferenceToSourceOfOrigin": false,
|
150 | "ignoreDotFilesAndFolders": true
|
151 | }
|
152 | }
|
153 | ```
|
154 |
|
155 | ### Command and output
|
156 |
|
157 | <details>
|
158 | <summary>$ copy-files-from-to</summary>
|
159 | <p>
|
160 |
|
161 | ```
|
162 | Reading copy instructions from file copy-files-from-to.cjson
|
163 |
|
164 | Starting copy operation in "default" mode:
|
165 | ✓ Copied [remote] https://raw.githubusercontent.com/jashkenas/underscore/master/underscore-min.js to scripts/underscore.js
|
166 | ✓ Copied [remote] https://raw.githubusercontent.com/webextensions/console-panel/master/src/console-panel.js to scripts/console-panel/console-panel.js
|
167 | ```
|
168 | </p>
|
169 | </details>
|
170 |
|
171 | <details>
|
172 | <summary>$ copy-files-from-to --mode development</summary>
|
173 | <p>
|
174 |
|
175 | ```
|
176 | Reading copy instructions from file copy-files-from-to.cjson
|
177 |
|
178 | Starting copy operation in "development" mode:
|
179 | ✓ Copied [remote] https://raw.githubusercontent.com/jashkenas/underscore/master/underscore.js to scripts/underscore.js
|
180 | ✓ Copied [remote] https://raw.githubusercontent.com/webextensions/console-panel/master/src/console-panel.js to scripts/console-panel/console-panel.js
|
181 | ```
|
182 | </p>
|
183 | </details>
|
184 |
|
185 | <details>
|
186 | <summary>$ copy-files-from-to --mode production</summary>
|
187 | <p>
|
188 |
|
189 | ```
|
190 | Reading copy instructions from file copy-files-from-to.cjson
|
191 |
|
192 | Starting copy operation in "production" mode:
|
193 | ✓ Copied [ utf8 ] node_modules/native-promise-only/npo.js to scripts/native-promise-only.js
|
194 | ✓ Copied [remote] https://raw.githubusercontent.com/jashkenas/underscore/master/underscore-min.js to scripts/underscore.js
|
195 | ```
|
196 | </p>
|
197 | </details>
|
198 |
|
199 | <details>
|
200 | <summary>$ copy-files-from-to --mode pre-production --config copy-files-from-to.cjson</summary>
|
201 | <p>
|
202 |
|
203 | ```
|
204 | Reading copy instructions from file copy-files-from-to.cjson
|
205 |
|
206 | Starting copy operation in "pre-production" mode:
|
207 | ✓ Copied [ utf8 ] node_modules/native-promise-only/npo.js to scripts/native-promise-only.js
|
208 | ✓ Copied [remote] https://raw.githubusercontent.com/jashkenas/underscore/master/underscore-min.js to scripts/underscore.js
|
209 | ✓ Copied [remote] https://raw.githubusercontent.com/jashkenas/underscore/master/underscore-min.js.map to scripts/underscore.js.map
|
210 | ✓ Copied [remote] https://raw.githubusercontent.com/webextensions/console-panel/master/src/console-panel.js to scripts/console-panel/console-panel.js
|
211 | ```
|
212 | </p>
|
213 | </details>
|
214 |
|
215 | # Configuration
|
216 |
|
217 | ## Structure of "copyFiles" instruction file
|
218 | * You can provide the "copyFiles" instructions in a JSON or [CJSON](https://github.com/kof/node-cjson) file
|
219 | * The file can be structured like:
|
220 | ```js
|
221 | {
|
222 | // copyFiles (required parameter)
|
223 | // Summary: This is the instruction set for the files to be copied
|
224 | // Data type: array (of objects)
|
225 | "copyFiles": [
|
226 | // Using "from" and "to", both, as simple strings
|
227 | {
|
228 | // from (required parameter)
|
229 | // Summary: This contains the path of a file which is either on disk or accessible via "http"/"https" URL
|
230 | // Data type: string, array, or object
|
231 | // Note: When it is set as a string, it would be used for all modes. When it is set as an object, it can be
|
232 | // configured differently for different modes (refer to the next example)
|
233 | // When it is set as an array, it describes an array of glob patterns and settings
|
234 | "from": "http://example.com/index.html",
|
235 |
|
236 | // to (required parameter)
|
237 | // Data type: string or object
|
238 | // Summary: This instruction set would write a file to this path on the disk
|
239 | // Note: When it is set as a string, it would be used for all modes. When it is set as an object, it can be
|
240 | // configured differently for different modes
|
241 | "to": "example-index.html"
|
242 | },
|
243 |
|
244 | // Using "from" as an array of glob expressions
|
245 | {
|
246 | // from (required parameter)
|
247 | // Data type: array
|
248 | // Note: When it is set as an array, it describes an array of glob patterns and settings
|
249 | // Any strings in the array are used as glob patterns.
|
250 | // Any objects are used as fast-glob options: (See https://www.npmjs.com/package/fast-glob)
|
251 | "from": [
|
252 | // The first entry here is also used to figure out the "non-magic parent path" from a glob string
|
253 | // Copy all files from the public folder
|
254 | "public/**/*",
|
255 | // A "!" at the beginning of the pattern will ignore any files matching that pattern
|
256 | // This ignores all files in the public/tmp folder
|
257 | "!public/tmp/**/*",
|
258 | // Any objects in the array will be collected together to pass to fast-glob as options
|
259 | // This will copy any files starting with a .*
|
260 | // This will not copy symlinked folders
|
261 | { dot: true, followSymlinkedDirectories: false }
|
262 | ],
|
263 | // to (required parameter)
|
264 | // Data type: string
|
265 | // Summary: This instruction set would write all the files found with the glob patterns and settings
|
266 | // to this folder.
|
267 | // Note: When using glob patterns for the "from" value the target "to" path needs to be a folder
|
268 | "to": "build/"
|
269 | },
|
270 |
|
271 | // Using "from" and "to", both, as objects (and use string based mode entries)
|
272 | {
|
273 | "from": {
|
274 | // The "from" section should contain details about at least one mode
|
275 |
|
276 | // "default" mode (optional parameter, recommended to have)
|
277 | // Summary: "default" mode would be used when the command is executed without any mode or when the command
|
278 | // is executed in a mode which is not described for the given entry
|
279 | // Data type: string or object
|
280 | "default": "node_modules/example/index.js",
|
281 |
|
282 | // <custom> mode (optional parameter if any other mode exists)
|
283 | "development": "node_modules/example/dev.js",
|
284 |
|
285 | // <custom> mode (optional parameter if any other mode exists)
|
286 | "production": "node_modules/example/production.js"
|
287 |
|
288 | // More <custom> mode entries
|
289 | },
|
290 | "to": {
|
291 | "default": "example.js"
|
292 | }
|
293 | },
|
294 |
|
295 | // Using "from" and "to", both, as objects (and use object based mode entries)
|
296 | {
|
297 | "from": {
|
298 | "default": {
|
299 | // src (required parameter)
|
300 | // Summary: This contains the path of a file which is either on disk or accessible via "http"/"https" URL
|
301 | // Data type: string
|
302 | "src": "http://example.com/index-1.0.0.js.map",
|
303 |
|
304 | // latest (optional parameter)
|
305 | // Summary: This contains the path of a file which is either on disk or accessible via "http"/"https" URL
|
306 | // Data type: string
|
307 | // Note: When this tools is executed with "--outdated" parameter, then the file from "latest" would be
|
308 | // compared with the file from "src", and if there are any differences, it would be notified that
|
309 | // an update is available
|
310 | "latest": "http://example.com/index.js.map"
|
311 | }
|
312 | },
|
313 | "to": {
|
314 | "default": {
|
315 | // dest (required parameter, when not using "skip" parameter set as true)
|
316 | // Summary: This instruction set would write a file to this path on the disk
|
317 | // Data type: string
|
318 | "dest": "scripts/index.js.map",
|
319 |
|
320 | // removeSourceMappingURL (optional parameter)
|
321 | // Summary: When set to true, any contents after "//# sourceMappingURL=" would be removed before
|
322 | // the copy operation
|
323 | // Data type: boolean
|
324 | // Default value: false
|
325 | "removeSourceMappingURL": false,
|
326 |
|
327 | // uglifyJs (optional parameter)
|
328 | // Summary: When set to true, this JavaScript file would be uglified before the copy operation
|
329 | // (via https://www.npmjs.com/package/uglify-js)
|
330 | // Data type: boolean
|
331 | // Default value: undefined
|
332 | "uglifyJs": false
|
333 | },
|
334 | "production": {
|
335 | // skip (required parameter, when not using "dest" parameter)
|
336 | // Summary: If you wish to skip a file in some particular mode, add "skip" as true, otherwise a warning
|
337 | // would be raised when you run this tool for that particular mode
|
338 | // Data type: boolean
|
339 | // Default value: false
|
340 | "skip": true
|
341 | }
|
342 | }
|
343 | }
|
344 |
|
345 | // Add more object entries with "from" and "to" details, and you can use any of the supported data types to
|
346 | // represent the values of "from", "to" and their "default" or <custom> modes
|
347 | ],
|
348 |
|
349 | // copyFilesSettings (optional parameter)
|
350 | // Summary: Settings for the copy files operation
|
351 | // Data type: object
|
352 | "copyFilesSettings": {
|
353 | // whenFileExists (optional parameter)
|
354 | // Summary: When the file at "to" path already exists, what action should be taken
|
355 | // Data type: string
|
356 | // Supported values: "do-nothing" / "overwrite" / "notify-about-available-change"
|
357 | // Default value: "do-nothing"
|
358 | "whenFileExists": "notify-about-available-change",
|
359 |
|
360 | // removeSourceMappingURL (optional parameter)
|
361 | // Summary: When set to true, any contents after "//# sourceMappingURL=" would be removed before
|
362 | // the copy operation
|
363 | // Data type: boolean
|
364 | // Default value: false
|
365 | "removeSourceMappingURL": false,
|
366 |
|
367 | // uglifyJs (optional parameter)
|
368 | // Summary: When set to true, the JavaScript files would be uglified before the copy operation
|
369 | // (via https://www.npmjs.com/package/uglify-js)
|
370 | // Data type: boolean
|
371 | // Default value: false
|
372 | "uglifyJs": false,
|
373 |
|
374 | // addReferenceToSourceOfOrigin (optional parameter)
|
375 | // Summary: When set to true, the copy operation would create a file "<to-file-path>.source.txt"
|
376 | // which would contain a link to the "from" path
|
377 | // Data type: boolean
|
378 | // Default value: false
|
379 | "addReferenceToSourceOfOrigin": false
|
380 |
|
381 | // ignoreDotFilesAndFolders (optional parameter)
|
382 | // Summary: When set to true, globbing will ignore files and folders starting with a "." dot.
|
383 | // Data type: boolean
|
384 | // Default value: false
|
385 | "ignoreDotFilesAndFolders": true
|
386 | }
|
387 | }
|
388 | ```
|
389 |
|
390 | ## Command line options
|
391 |
|
392 | ```sh
|
393 | $ copy-files-from-to --help
|
394 | ```
|
395 |
|
396 | ```
|
397 | Usage:
|
398 | copy-files-from-to [--config <config-file>] [--mode <mode-name>] [...]
|
399 |
|
400 | Examples:
|
401 | copy-files-from-to
|
402 | copy-files-from-to --config copy-files-from-to.json
|
403 | copy-files-from-to --mode production
|
404 | copy-files-from-to -h
|
405 | copy-files-from-to --version
|
406 |
|
407 | Options:
|
408 | --config <config-file-path> Path to configuration file
|
409 | When unspecified, it looks for:
|
410 | 1) copy-files-from-to.cjson
|
411 | 2) copy-files-from-to.json
|
412 | 3) package.json
|
413 | --mode <mode-name> Mode to use for copying the files
|
414 | When unspecified, it uses "default" mode
|
415 | --when-file-exists <operation> Override "whenFileExists" setting specified in configuration file
|
416 | <operation> can be "notify-about-available-change" or "overwrite" or "do-nothing"
|
417 | --outdated Notify about outdated parts of the configuration file
|
418 | (takes cue from "latest" property, wherever specified)
|
419 | --verbose Verbose logging
|
420 | -v --version Output the version number
|
421 | -h --help Show help
|
422 | ```
|
423 |
|
424 | # TODO
|
425 |
|
426 | See [TODO.md](TODO.md)
|
427 |
|
428 |
|
429 | # About this project
|
430 |
|
431 | ## Author
|
432 |
|
433 | * Priyank Parashar - [GitHub](https://github.com/paras20xx) | [Twitter](https://twitter.com/paras20xx) | [LinkedIn](https://linkedin.com/in/ParasharPriyank/)
|
434 |
|
435 | ## Connect to us
|
436 |
|
437 | * https://webextensions.org/
|
438 | * [GitHub](https://github.com/webextensions/live-css-editor)
|
439 | * [Twitter](https://twitter.com/webextensions)
|
440 |
|
441 | ## License
|
442 |
|
443 | * [MIT](LICENSE)
|