84

I am trying out npm as a build tool.

One stumbling block I have encountered is that I need to copy javascript files from one folder to another. The source folder contains typescript files, javascript files and map files, but in the target folder I am only interested in javascript files.

I do not want to make a copy-statement for each file, but would like to copy all .js files. Also, my source folder contains subfolders that also contains javascript files. These need to be copied as well, and maintain the subfolder structure.

What I have tried is using NCP with a filter, but I cannot get the filter to work. I have tested the regex used in the filter and it appears to work fine. The test was done at Regex Tester with regular expression .*\.js$ and test-strings like main.ts, main.js main.js.map etc, and only the .js strings were matched.

My package json contains the following (abbreviated):

{
    "scripts": {
        "copy": "ncp scripts wwwroot/scripts --filter=\".*(\\\\.js$)\"" 
    }, 
    "devDependencies": { 
        "ncp": "2.0.0.0" 
    }
}

Since my regex is in a string in a string I have double-escaped it. I have also tried other variations, for example:

--filter=/.*\.js$/g       - compilation error
--filter=/.*\\.js$/g      - no files copied
--filter=\".*\\.js$\"     - no files copied
--filter=\"/.*\\.js$/g\"  - no files copied
(no filter)               - all files copied

I am in no way married to NCP. If something else works better then I will use that.

So: How do I, inside package.json's scripts section copy only files with a speific extension to another folder? I am pretty sure I have overlooked something blindingly obvious...

Thomas Jørgensen
  • 1,092
  • 2
  • 12
  • 19

9 Answers9

101

Warning! The cpx package appears to be abandoned. cpy-cli, copyfiles, and other solutions are listed in comments here or answers, below.

cpx might be a good substitution.

It has a CLI, allows you to use globs instead of regex, can preserve the directory tree, and is relatively up-to-date as I write this....

Matthew Bakaitis
  • 11,600
  • 7
  • 43
  • 53
  • 10
    Perfect. Now my script is "copy": "cpx \"scripts/**/*.js\" wwwroot/scripts", with the devDependency "cpx": "1.3.1". It is exactly what I was looking for. – Thomas Jørgensen Jun 25 '16 at 21:14
  • Yeah, cpx is a really great tool. Good recommendation. – deepelement Dec 29 '18 at 16:35
  • 9
    At now cpx seems to be abondened and has open vulnerabilities in the dependencies. I would suggest to use [cpy-cli](https://github.com/sindresorhus/cpy-cli) based on [cpy](https://github.com/sindresorhus/cpy). – RiZKiT Aug 27 '19 at 10:54
  • I think [ncp](https://www.npmjs.com/package/ncp) might be a good substitute since cpx now seems to be abandoned. It's async and does recursive file and directory copying. – Mattias Oct 30 '19 at 13:50
  • The last release was 3 years ago. Looks like it is abandoned. It has vulnerabitlies – Wildhammer Jan 21 '20 at 17:08
46

There's also npm module called copyfiles https://github.com/calvinmetcalf/copyfiles

E.g. to copy all *.css files from the ./src folder to the ./styles folder:

copyfiles --flat src/*.css styles
catamphetamine
  • 4,489
  • 30
  • 25
  • 6
    Why not just `cp -R`? I'm using `cp -R ./email/templates ./build/email` and just curious about your solution. – Woppi Jul 04 '18 at 04:36
  • 41
    @Woppi my reasoning would be, because it uses OS commands, which might not work on other OS's. – Coo Aug 21 '18 at 02:10
13

Quick compatibility build script (also works on Windows):

"build": "react-scripts build && mv build docs || move build docs",
Sagar Ghimire
  • 231
  • 4
  • 10
5
@powershell copy \"D:/Path/untitled.txt\"  destionation-file.txt"
Sorin Veștemean
  • 1,772
  • 19
  • 17
  • 3
    @JasonAller Powershell is available cross platform https://learn.microsoft.com/en-us/powershell/scripting/whats-new/what-s-new-in-powershell-70?view=powershell-7#where-can-i-install-powershell – Switters Aug 13 '20 at 11:50
  • 3
    It would be useful to edit the answer to include that information and also to note how systems that don't have PowerShell installed will react to this line of code and if there is a way to mitigate that. – Jason Aller Aug 13 '20 at 14:53
3

Windows users:

// Copy file
xcopy c:\workfile d:\test

// Copy folders incl. sub folders
xcopy <source> <destination> /e

// If folder name has space in name use double quotes
xcopy c:\workfile “d:\test new”

More info here

KostovV
  • 51
  • 1
  • 5
1

You can use gulp.js for this. Write a gulp task to isolate only the js files (/path/to/files/*.js) and move it to destination of your choice. It will require only a few lines of code. Include that in the script section of package.json if necessary.

The link to gulp.js : https://gulpjs.com/

var gulp = require('gulp');
gulp.task('jscopy', function(){
  return gulp.src('client/templates/*.js')
    .pipe(gulp.dest('build/js'))
});
Zer0
  • 448
  • 1
  • 5
  • 16
  • 4
    Adding Gulp as a dependency just for copying files is a bit overdone. If you already/still use gulp, it could be an option. – RiZKiT Aug 27 '19 at 10:58
  • 2
    Yeah if someone is using something like webpack they wouldn't want to add gulp to just use copy. – Craig Jan 18 '20 at 17:27
1

ncp copies recursively, therefore before copying files it will check whether directory matches filter or not, e.g.:

d:\path\to\app\src\server
d:\path\to\app\src\server\middleware
d:\path\to\app\src\server\middleware\cool-middleware.js
d:\path\to\app\src\server\middleware\cool-middleware.js.map

So your regex must matches all these paths and your file also

1

I am able to just use cp in my script command:

"build": "npx babel src --out-dir dist && cp ./src/*.css ./dist",

This will work if you have your distribution package already inside the /dist folder. You can also add another command to copy that over, then even run the publish command.

I use this in Git bash in windows which has the cp command available. The comments are correct that you will need this in your underlying shell/command prompt. It should be able to be modeled and updated for your OS.

rhigdon
  • 1,483
  • 1
  • 15
  • 20
0

@KostovV answer but adapted for json string and relative path

"build": "nest build && xcopy \".\\myFolder0\" \".\\myFolde1\\sub\"",

63RMAN
  • 519
  • 4
  • 6