将单个文件从主机复制到 Vagrant 来宾的最简单方法?

Posted

技术标签:

【中文标题】将单个文件从主机复制到 Vagrant 来宾的最简单方法?【英文标题】:Easiest way to copy a single file from host to Vagrant guest? 【发布时间】:2013-05-18 05:31:49 【问题描述】:

我有一个用例,我偶尔想将单个文件从我的主机复制到 Vagrant 来宾。

我不想通过传统的供应商(Puppet / Chef)这样做,因为这通常是一次性的——我只想快速添加一些东西到我的 Vagrantfile 中。

我不想共享整个目录,可能是因为我想覆盖现有文件而不破坏来宾上的整个目录。

当我只想复制一个文件时,编写一个 shell 配置脚本并处理潜在的转义似乎也有点矫枉过正。

那么,将单个文件从主机复制到客户机最简单的方法是什么?

【问题讨论】:

请注意,接受的答案是基于 Vagrant 1.x--using a file provisioner is the standard Vagrant 2 approach,尽管更改 /vagrant 的挂载点 as mentioned here 也是一个不错的选择 @jouell 的回答确实值得为单个文件的一次性副本的简单用例获得更多投票:vagrant upload /path/to/my/file... vagrant scp file.txt :~/. ***.com/a/53908426/547569 by ***.com/users/3462494/jouell 应该是公认的答案。这是 Vagrant CLI 的内置命令,用于将文件或目录复制到主机 vagrant upload SOURCE [DESTINATION] [NAME|ID]。我最初错过了它,因为它被埋得太深了。 【参考方案1】:

由于您要求最简单的方法,我建议使用vagrant-scp。它向 vagrant 添加了一个 scp 命令,因此您可以像通常使用 scp 一样将文件复制到您的 VM。

通过以下方式安装:

vagrant plugin install vagrant-scp

像这样使用它:

vagrant scp <some_local_file_or_dir> [vm_name]:<somewhere_on_the_vm>

【讨论】:

这对我不起作用。我安装了插件,但一直收到错误提示“找不到插件“vagrant-scp”。请确保它已通过vagrant plugin正确安装。” 嗨 Rod,vagrant-scp 适用于 Vagrant 1.7+。从您打开的错误中,您正在运行 1.4.3。如果您需要此插件,恐怕您必须升级(快速且轻松)。 我尝试了这个命令来复制文件,但没有工作并给出错误vagrant scp /vagrant/www/koushik.php ubuntu/trusty64:/usr/share/nginx/html 我正在尝试将文件复制到 nginx 根目录中。它说,The machine with the name 'C' was not found configured for this Vagrant environment. 目录和一切都很好。 补充一点:您必须使用第一列中的 vagrant global-status 可以获得的机器 ID。尽管如此,这是最好的解决方案。 @KoushikDas 在 Windows 上无法开箱即用。您必须在 Windows 10 上启用 Ubuntu 子系统,然后不要将 C:/.. 放置为文件的路径,而是放置 /mnt/c/... 并且工作万岁!另请注意另一条评论,使用 vagrant global-status 获取 vagrant 机器的 id。【参考方案2】:

实际上有一个更简单的解决方案。见https://gist.github.com/colindean/5213685/#comment-882885:

"请注意,除非您出于某种原因特别需要 scp,否则将文件从主机传输到 VM 的最简单方法是将它们放在与 Vagrantfile 相同的目录中 - 该目录会自动挂载在 /vagrant 下VM,以便您可以直接从 VM 复制或使用它们。”

【讨论】:

这正是我的答案......它运行一个 shell 配置程序从 /vagrant/ 复制文件。 最好使用 LeexGreen 所使用的 vagrant Provisioning。 确保config.vm.synced_folder ".", "/vagrant", disabled: false 然后vagrant reload 如果尝试执行反向操作(本地机器的 vagrant 框),这 notcentos/7 vagrant 框起作用。 在将文件从我的 Ubuntu 14 vagrant VM 复制到我的主机时,这非常适合我。谢谢!!【参考方案3】:

您也可以使用 Vagrant file provisioner,而不是使用 shell 配置器来复制文件。

供应商名称: "file"

文件配置器允许您将文件从主机上传到客户机。

Vagrant.configure("2") do |config|
  # ... other configuration

  config.vm.provision "file", source: "~/.gitconfig", destination: ".gitconfig"
end

【讨论】:

这绝对是在 Vagrant 2 中做到这一点的最佳方式!但是,在我需要执行此操作时,Vagrant 2 不可用... :) 这个解决方案听起来不错,但由于权限错误,我无法复制任何文件。 @orbatschow 我有同样的问题,但如果我将它复制到/tmp 这不是 OP 所要求的。问题是如何偶尔传输文件;必须运行配置是多余的。【参考方案4】:

默认情况下,第一个 vagrant 实例使用 ssh 端口为 2222,其 ip 地址为 127.0.0.1(如果您创建了多个虚拟主机,可能需要调整端口)

==> default: Forwarding ports...
    default: 22 (guest) => 2222 (host) (adapter 1)

因此,您可以运行以下命令将本地文件复制到 vagrant 实例中,而不仅仅是 /vagrant。密码与用户名相同,即vagrant

scp -P 2222 your_file vagrant@127.0.0.1:.

您也可以将文件复制回本地主机。

scp -P 2222 vagrant@127.0.0.1:/PATH/filename .

【讨论】:

我必须这样做并禁用严格的密钥检查:scp -P 2222 -o UserKnownHostsFile=/dev/null -o StrictHostKeyChecking=no my-file.txt matt@127.0.0.1:/tmp 我建议将这些 ssh 选项默认添加到 ~/.ssh/config 中,我在我的环境中这样做了:StrictHostKeyChecking no +1 + 如果一个有多个虚拟机,则端口值应从 Oracle VM VirtualBox Manager 的 UI 中获取 - 选择左侧的 vm、设置、网络、端口转发 这比接受的答案要好。 /vagrant 目录并不总是存在。 令人惊讶的是,与 scp 相比,在这种情况下让 rsync 工作要困难得多,因为 rsync 将其描述为“更快、更灵活的 rcp 替代品”。【参考方案5】:

这是我解决问题的方法:

第 1 步 - 找到私钥、ssh 端口和 IP:

root@vivi:/opt/boxes/jessie# vagrant ssh-config
Host default
  HostName 127.0.0.1
  User vagrant
  Port 2222
  UserKnownHostsFile /dev/null
  StrictHostKeyChecking no
  PasswordAuthentication no
  IdentityFile /root/.vagrant.d/insecure_private_key
  IdentitiesOnly yes
  LogLevel FATAL

第 2 步 - 使用端口和私钥作为 scp 的参数传输文件:

  scp -P 2222 -i /root/.vagrant.d/insecure_private_key \
  someFileName.txt vagrant@127.0.0.1:~

希望对你有帮助

【讨论】:

这是最简单的方法。谢谢。 使用密钥允许我传输文件。没有此信息的更高答案不起作用,所以谢谢! 简单而完整的解决方案。【参考方案6】:
vagrant upload localfile

这会将 localfile 放在 vagrant 用户的主目录中

https://www.vagrantup.com/docs/cli/upload.html

【讨论】:

这似乎完全符合 OP 的要求,方便一次性使用。 不错,简单且符合标准!【参考方案7】:

我最终做的是将文件保存在我的 vagrant 目录中(自动挂载为 /vagrant/)并使用 shell 配置器将其复制:

command = "cp #File.join('/vagrant/', path_within_repo) #remote_file"
config.vm.provision :shell, :inline => command

【讨论】:

我建议使用 coreutils install 例如install -D -m644 -C ...src 目标。而不是 cp,因为您可以执行诸如指定权限、所有权、自动创建前导目录、仅在需要更新文件时才进行复制等操作……而不是 cp,如果您仅此而已需要做的。 @LeeXGreen。我正在尝试做与您尝试做的相同的事情,但我不太明白您的答案。您是否在终端中输入了那行代码?你到底把它放在哪里了? 我的回答中的代码 sn-p 与您的其他供应商一起出现在您的 Vagrantfile 中。您需要将path_within_reporemote_file 替换为对您的应用程序有意义的东西,当然:) 工作,但我得到“默认:标准输入:不是 tty”错误【参考方案8】:

如果您不能将文件放在目录中,则可以在主机的脚本文件中运行此代码。

#!/bin/sh
OPTIONS=`vagrant ssh-config | awk -v ORS=' ' 'print "-o " $1 "=" $2'`

scp $OPTIONS /File/To/Copy vagrant@YourServer:/Where/To/Put/File

在此设置中,您只需将/File/To/Copy 更改为您要复制的文件,然后/Where/To/Put/File 是您希望将文件复制到的VM 上的位置。

如果您创建此文件并将其命名为copyToServer.sh,则可以运行sh 命令来推送这些文件。

sh ./copyToServer.sh

最后一点,您不能将此代码作为 provisioner 运行,因为它在访客服务器上运行,而此代码从主机运行。

【讨论】:

这可能是安装 vagrant-scp 插件之外的最佳解决方案。它使用 Vagrant 使用的 SSH 配置,因此它可以处理不同提供商提供的不同网络设置。 不错!我建议您还请注意,人们可以简单地将 vagrant ssh-config 的输出粘贴到他们的 ~/.ssh/config 文件中,以便将来更容易。 IE。将此与 chf 的答案结合起来 我发现有必要跳过 ssh-config 输出的第一行以避免错误“主机指令不支持作为命令行选项”——由 ssh- 的标头引起配置部分:“主机默认值”。所以,我的脚本有 OPTIONS=`vagrant ssh-config | tail -n +2 | awk -v ORS=' ' 'print "-o " $1 "=" $2'` 使用 ssh-config 输出的第一行来省略。 或者,要删除“不支持主机指令”错误,您可以使用OPTIONS=`vagrant ssh-config | grep -v '^Host ' | awk -v ORS=' ' 'NFprint "-o " $1 "=" $2'`,如下所述:gist.github.com/geedew/11289350【参考方案9】:

Vagrant 提供了一种通过 ssh 执行命令而不是登录的方法,因此对于 Linux 主机和客户机,您可以使用:

从主人到客人:

cat ~/file_on_host.txt | vagrant ssh -c 'cat - &gt; ~/file_on_guest.txt'

从客人到主人:

vagrant ssh -c 'cat ~/file_on_guest.txt' &gt; ~/file_on_host.txt

无需插件或访客重新加载。如果您与 Vagrantfile 不在同一个目录中,请确保将 vagrant box ID 提供给“vagrant ssh”。在 Vagrant v1.8.1 上测试。

【讨论】:

从客户到主机的方法不会在文件中保留特殊符号【参考方案10】:

以上所有答案都可能有效。但下面是对我有用的。我有多个流浪主机:host1,host2。 我想将文件从 ~/Desktop/file.sh 复制到主机:host1 我做到了:

    $vagrant upload ~/Desktop/file.sh host1

这将复制 ~/Desktop/file.sh 到 /home/xxxx 下,其中 xxx 是你在 host1 下的 vagrant 用户

【讨论】:

【参考方案11】:

您可以在~/.ssh/config中添加条目:

Host vagrant
    User vagrant
    HostName localhost
    Port 2222
    IdentityFile /home/user_name/.vagrant.d/insecure_private_key

还有简单的scp file vagrant:/path/。您可以使用vagrant ssh-config 命令找到身份文件的路径。

【讨论】:

非常有帮助,有助于澄清正在发生的事情。这使您可以复制两个方向,进行递归复制等,并很好地利用 scp / ssh 的现有知识 我刚刚重新阅读了上面的答案,并通过玩 geedew 的答案发现vagrant ssh-config 为您提供了一个更加完整和方便的配置,您可以将其放入您的 ~/.ssh/config 中。但再次感谢!【参考方案12】:

转到您拥有Vagrantfile的目录 然后,编辑您的 Vagrantfile 并添加以下内容:

config.vm.synced_folder ".", "/vagrant", :mount_options => ['dmode=774','fmode=775']

"." 表示您当前在主机上的目录"/vagrant" 表示“/home /vagrant”在访客机器(Vagrant机器)上。

将您需要发送到访客计算机的文件复制到您拥有Vagrantfile 的文件夹中 然后打开 Git Bashcd 到您拥有 Vagrantfile 的目录并输入:

vagrant scp config.json XXXXXXX:/home/vagrant/

其中 XXXXXXX 是您的 虚拟机名称。您可以通过运行

来获取您的虚拟机名称
vagrant global-status

【讨论】:

【参考方案13】:

如果由于某些原因您没有使用权限

vagrant plugin install vagrant-scp

还有另一种方法:

先 vagrant up yourVagrantProject,然后在终端里写:

vagrant ssh-config

您将获得有关虚拟机“主机名”和“端口”的信息。

在某些情况下,您的项目中可能会有一些虚拟机。所以只要找到你的master机器(一般来说,这个VM的端口是2222),不要关注其他机器的信息。

编写复制命令:

scp -P xxPortxx  /Users/where/is/your/file.txt  vagrant@xxHostNamexx:/home/vagrant

在这个陡峭的地方,你将不得不输入一个流浪密码: 默认情况下它是“流浪汉”

之后,如果您查看虚拟机中的文件:

vagrant ssh xxVirtualMachineNamexx
pwd
ls

你的虚拟机目录中会有“file.txt”

【讨论】:

输入 vagrant 密码后,我得到“权限被拒绝” 但这是由于对目标目录的权限。我复制到 /home/vagrant 并且确实有效。【参考方案14】:

如果你知道你的 vagrant box 名字,vagrant scp 插件就可以工作。 检查 vagrant global-status 它将提供您的盒子名称,然后您可以运行:

vagrant global-status
id       name    provider   state   directory
------------------------------------------------------------------------
13e680d  **default** virtualbox running /home/user

vagrant scp ~/foobar "name in my case default":/home/"user"/

【讨论】:

这对我有用。编辑也很有帮助,我还将包括安装 vagrant scp 插件的命令。【参考方案15】:

试试这个.. vagrant ubuntu 14.04 这对我有用。

scp -r -P 2222 vagrant@localhost:/home .

【讨论】:

【参考方案16】:

另一种无需安装任何东西的方法(vagrant-scp 等)请注意,名称 default 需要按原样使用,因为 vagrant ssh-config 会发出该名称。

vg_scp() 
  tmpfile=$(mktemp /tmp/vagrant-ssh-config.XXXX)
  vagrant ssh-config > $tmpfile
  scp -F $tmpfile "$@"
  rm $tmpfile


# Copy from local to remote
vg_scp somefile default:/tmp

# Copy from remote to local
vg_scp default:/tmp/somefile ./

# Copy a directory from remote to local
vg_scp -r default:/tmp ./tmp

如果 scp -F =(vagrant ssh-config) ... 可以跨 shell 工作,则不需要该函数。但由于 Bash 不支持这一点,我们不得不求助于这种解决方法。

【讨论】:

【参考方案17】:

如果有人想将文件从 Windows 主机传输到 vagrant,那么这个解决方案对我有用。

1. Make sure to install **winscp** on your windows system
2. run **vagrant up** command
3. run **vagrant ssh-config** command and note down below details
4. Enter Hostname, Port, Username: vagrant, Password: vagrant in winscp and select **SCP**, file protocol 
5. In most cases, hostname: 127.0.0.1, port: 2222, username: vagrant, password: vagrant.

你应该能够在你的 vagrant 机器上看到目录。

【讨论】:

【参考方案18】:

对我来说最好的答案是将文件/目录(要复制)写入 vagrant 文件目录,现在任何文件都可以在路径 /vagrant 中使用。

就是这样,不需要scp或任何其他方法,

同样,您可以通过粘贴 /vagrant 目录将任何文件从 VM 复制到主机。

【讨论】:

【参考方案19】:

将文件从本地复制到 vagrant 的最佳方式,无需编写任何代码或任何东西或任何配置更改。 1- 首先是流浪者(vagrant up) 2-打开cygwin 3- cygwin :转到 vagrantfile 所在的文件夹或启动 vagrant 的位置 4- ssh vagrant 5-现在它将像正常系统一样工作。

【讨论】:

我用这种方法发现了一个问题:如果 vagrant 需要配置您的 Guest Additions,则 /vagrant 目录可能不会在文件配置器运行时实际挂载。

以上是关于将单个文件从主机复制到 Vagrant 来宾的最简单方法?的主要内容,如果未能解决你的问题,请参考以下文章

加快 Vagrant 上主机和来宾之间的同步延迟(NFS 同步文件夹)

如何将文件从 Vagrant 机器复制到 localhost

VMWare主机和来宾的同步文件夹

端口使用Vagrant转发时连接重置

Vagrant Homestead'存储'文件夹权限被拒绝[已结束]

将文本从VirtualBox Debian guest虚拟机复制到Windows 7主机会添加行