From 2e37d2c25342924d7d0792807235a1c83f539481 Mon Sep 17 00:00:00 2001 From: Martin Bektchiev Date: Fri, 26 Aug 2016 18:21:23 +0300 Subject: [PATCH] CB-11771 Deep symlink directories to target project instead of linking the directory itself When installing a plugin with custom library using the --link option the whole directory is symlinked and temporary files leak into the original plugin directory on build. This leads to broken builds if the same plugin is linked in 2 projects targeting different Cordova versions. This closes #326 --- bin/templates/cordova/lib/pluginHandlers.js | 28 +++++++++++++-------- 1 file changed, 18 insertions(+), 10 deletions(-) diff --git a/bin/templates/cordova/lib/pluginHandlers.js b/bin/templates/cordova/lib/pluginHandlers.js index d209de1b..5e745fd5 100644 --- a/bin/templates/cordova/lib/pluginHandlers.js +++ b/bin/templates/cordova/lib/pluginHandlers.js @@ -231,17 +231,9 @@ function copyFile (plugin_dir, src, project_dir, dest, link) { throw new CordovaError('Destination "' + dest + '" for source file "' + src + '" is located outside the project'); shell.mkdir('-p', path.dirname(dest)); - var srcStat = fs.statSync(src); if (link) { - //CB-11683 We need to handle linking to directories on our own because Windows doesn't. - var type; - if (srcStat.isDirectory()) { - type = 'dir'; - } else { - type = 'file'; - } - fs.symlinkSync(path.relative(path.dirname(dest), src), dest, type); - } else if (srcStat.isDirectory()) { + symlinkFileOrDirTree(src, dest); + } else if (fs.statSync(src).isDirectory()) { // XXX shelljs decides to create a directory when -R|-r is used which sucks. http://goo.gl/nbsjq shell.cp('-Rf', src+'/*', dest); } else { @@ -258,6 +250,22 @@ function copyNewFile (plugin_dir, src, project_dir, dest, link) { copyFile(plugin_dir, src, project_dir, dest, !!link); } +function symlinkFileOrDirTree(src, dest) { + if (fs.existsSync(dest)) { + shell.rm('-Rf', dest); + } + + if (fs.statSync(src).isDirectory()) { + shell.mkdir('-p', dest); + fs.readdirSync(src).forEach(function(entry) { + symlinkFileOrDirTree(path.join(src, entry), path.join(dest, entry)); + }); + } + else { + fs.symlinkSync(path.relative(fs.realpathSync(path.dirname(dest)), src), dest); + } +} + // checks if file exists and then deletes. Error if doesn't exist function removeFile (project_dir, src) { var file = path.resolve(project_dir, src);