diff options
author | Scott Paeth <scott.paeth@freshgrade.com> | 2017-07-20 13:39:50 -0700 |
---|---|---|
committer | Scott Paeth <scott.paeth@freshgrade.com> | 2017-07-20 13:55:03 -0700 |
commit | c1777563f04fd04be16a2ab22ac0af541a5b1f87 (patch) | |
tree | 6f5bdeea53498bf34bb3add0fb54034d10a3ccf9 | |
parent | bd4d31a66bba368cade1c9769996a9bd3a22f155 (diff) | |
download | net-ssh-c1777563f04fd04be16a2ab22ac0af541a5b1f87.tar.gz |
Fixed side-effects caused by passing by reference
The Net::SSH::Config::default_files method is supposed to "return an array of locations" to parse by default.
However, it currently returns a **reference** to the actual `@@default_files` instance variable, meaning that any API consumers who `Enumerable#shift`, `pop`, or otherwise modify the returned Array are actually **__modifying the state of the `Net::SSH` library as a whole__**, meaning that subsequent uses cannot use the same array.
I found this because I use `Net::SSH.start` by itself (eg, automagically getting configuration), but ran into problems when I added this block in front, where I'm simply loading the files to find whether the new option `IdentityAgent` is set. (Eg, I'm not otherwise using/`::translate`ing the loaded options)
```ruby
raw_opts = {}
opt_files = Net::SSH::Config.default_files
while (file = opt_files.shift)
raw_opts = Net::SSH::Config.load(file, some_hostname, raw_opts)
end
identity_agent = raw_opts.fetch("identityagent", nil)
Net::SSH.start(hostname, nil, verbose: :info) do |session|
# ... do my regular stuff
end
```
After I added that block, the attempted ssh session used the wrong username, etc, as if `#start` was no longer loading the config files.
At first I assumed that `Net::SSH::Config.load` had side effects (documented or otherwise) but I couldn't see any evidence of that in the code.
Imagine my surprise when I found the "pass by reference" problem in `::default_files`...
My fix boiled down to this:
`opt_files = Net::SSH::Config.default_files` -> `opt_files = Net::SSH::Config.default_files.clone`
Hence the PR. I don't think it makes sense for anyone to be able to modify the internal state of Net::SSH...
Feel free to reject this PR, in which case I'll make another one to adjust the docs instead, warning people of the side effects :-)
-rw-r--r-- | lib/net/ssh/config.rb | 2 |
1 files changed, 1 insertions, 1 deletions
diff --git a/lib/net/ssh/config.rb b/lib/net/ssh/config.rb index 46d8373..1e86d06 100644 --- a/lib/net/ssh/config.rb +++ b/lib/net/ssh/config.rb @@ -49,7 +49,7 @@ module Net; module SSH # Returns an array of locations of OpenSSH configuration files # to parse by default. def default_files - @@default_files + @@default_files.clone end def default_auth_methods |