From 1b0148bc783298c7aa16a519e133bb26bcc1cc9f Mon Sep 17 00:00:00 2001 From: Brian Cain Date: Tue, 11 Jun 2019 10:38:56 -0700 Subject: [PATCH] Fixes #10895: Use relative paths to machines folder path for Listener Prior to this commit, the rsync helper expanded all exclude paths that should be ignored to be full qualified and regexp escaped. However the Listen gem expects these ignore paths to be relative to the path passed into the listener, not a full path. This commit fixes that by using the path given by the user for the `rsync__exclude` option --- .../synced_folders/rsync/command/rsync_auto.rb | 6 +++++- plugins/synced_folders/rsync/helper.rb | 15 ++++++++------- .../rsync/command/rsync_auto_test.rb | 8 +++++--- .../plugins/synced_folders/rsync/helper_test.rb | 16 ++++++++-------- 4 files changed, 26 insertions(+), 19 deletions(-) diff --git a/plugins/synced_folders/rsync/command/rsync_auto.rb b/plugins/synced_folders/rsync/command/rsync_auto.rb index 7ecb6999e50..c7bd9e09749 100644 --- a/plugins/synced_folders/rsync/command/rsync_auto.rb +++ b/plugins/synced_folders/rsync/command/rsync_auto.rb @@ -121,9 +121,13 @@ def execute if folder_opts[:exclude] Array(folder_opts[:exclude]).each do |pattern| - ignores << RsyncHelper.exclude_to_regexp(hostpath, pattern.to_s) + ignores << RsyncHelper.exclude_to_regexp(pattern.to_s) end end + + # Always ignore Vagrant + ignores << /.vagrant\// + ignores.uniq! end end diff --git a/plugins/synced_folders/rsync/helper.rb b/plugins/synced_folders/rsync/helper.rb index c23cd1d5354..a3c9decdc9d 100644 --- a/plugins/synced_folders/rsync/helper.rb +++ b/plugins/synced_folders/rsync/helper.rb @@ -16,7 +16,13 @@ class RsyncHelper # This converts an rsync exclude pattern to a regular expression # we can send to Listen. - def self.exclude_to_regexp(path, exclude) + # + # Note: Listen expects a path relative to the parameter passed into the + # Listener, not a fully qualified path + # + # @param [String] - exclude path + # @return [Regexp] - A regex of the path, modified, to exclude + def self.exclude_to_regexp(exclude) start_anchor = false if exclude.start_with?("/") @@ -24,19 +30,14 @@ def self.exclude_to_regexp(path, exclude) exclude = exclude[1..-1] end - path = "#{path}/" if !path.end_with?("/") - regexp = "^#{Regexp.escape(path)}" - regexp += ".*" if !start_anchor - # This is not an ideal solution, but it's a start. We can improve and # keep unit tests passing in the future. exclude = exclude.gsub("**", "|||GLOBAL|||") exclude = exclude.gsub("*", "|||PATH|||") exclude = exclude.gsub("|||PATH|||", "[^/]*") exclude = exclude.gsub("|||GLOBAL|||", ".*") - regexp += exclude - Regexp.new(regexp) + Regexp.new(exclude) end def self.rsync_single(machine, ssh_info, opts) diff --git a/test/unit/plugins/synced_folders/rsync/command/rsync_auto_test.rb b/test/unit/plugins/synced_folders/rsync/command/rsync_auto_test.rb index 953c55ed0a5..5a9c691ffdf 100644 --- a/test/unit/plugins/synced_folders/rsync/command/rsync_auto_test.rb +++ b/test/unit/plugins/synced_folders/rsync/command/rsync_auto_test.rb @@ -66,15 +66,12 @@ def machine_stub(name) # https://github.com/hashicorp/vagrant/blob/9c1b014536e61b332cfaa00774a87a240cce8ed9/lib/vagrant/action/builtin/synced_folders.rb#L45-L46 let(:config_synced_folders) { {"/vagrant": {type: "rsync", - exclude: false, hostpath: "/Users/brian/code/vagrant-sandbox"}, "/vagrant/other-dir": {type: "rsync", - exclude: false, hostpath: "/Users/brian/code/vagrant-sandbox/other-dir"}, "/vagrant/relative-dir": {type: "rsync", - exclude: false, hostpath: "/Users/brian/code/relative-dir"}}} before do @@ -103,6 +100,11 @@ def machine_stub(name) with("Watching: /Users/brian/code/relative-dir") expect(helper_class).to receive(:rsync_single) + expect(Listen).to receive(:to). + with("/Users/brian/code/vagrant-sandbox", + "/Users/brian/code/relative-dir", + {:ignore=>[/.vagrant\//], + :force_polling=>false}) subject.execute end diff --git a/test/unit/plugins/synced_folders/rsync/helper_test.rb b/test/unit/plugins/synced_folders/rsync/helper_test.rb index e50ae872cf7..aea2f198bf3 100644 --- a/test/unit/plugins/synced_folders/rsync/helper_test.rb +++ b/test/unit/plugins/synced_folders/rsync/helper_test.rb @@ -32,23 +32,23 @@ let(:path) { "/foo/bar" } it "converts a directory match" do - expect(described_class.exclude_to_regexp(path, "foo/")). - to eq(/^#{Regexp.escape(path)}\/.*foo\//) + expect(described_class.exclude_to_regexp("foo/")). + to eq(/foo\//) end it "converts the start anchor" do - expect(described_class.exclude_to_regexp(path, "/foo")). - to eq(/^\/foo\/bar\/foo/) + expect(described_class.exclude_to_regexp("/foo")). + to eq(/foo/) end it "converts the **" do - expect(described_class.exclude_to_regexp(path, "fo**o")). - to eq(/^#{Regexp.escape(path)}\/.*fo.*o/) + expect(described_class.exclude_to_regexp("fo**o")). + to eq(/fo.*o/) end it "converts the *" do - expect(described_class.exclude_to_regexp(path, "fo*o")). - to eq(/^#{Regexp.escape(path)}\/.*fo[^\/]*o/) + expect(described_class.exclude_to_regexp("fo*o")). + to eq(/fo[^\/]*o/) end end