npm的流氓文件系统问题

时间:2017-01-11 21:55:49

标签: node.js npm vagrant virtualbox webpack-dev-server

我经常遇到Vagrant计算机和npm的错误,文件系统突然变为只读。在所有情况下,都涉及包含git repo的同步目录。

这是我能够遇到问题的配置设置。这两个文件都位于面向节点的git存储库的根目录中,如this one

Vagrantfile

# Vagrantfile API/syntax version. Don't touch unless you know what you're doing!
VAGRANTFILE_API_VERSION = "2"

Vagrant.configure(VAGRANTFILE_API_VERSION) do |config|
  # Use host's SSH keys
  config.ssh.forward_agent = true

  # Get current directory name (presumably, repo dirname)
  repo_dirname = File.basename(Dir.getwd)

  # Set US locale
  ENV['LC_ALL']="en_US.UTF-8"

  # Ensures virtualbox can create symlinks in shared folders
  config.vm.provider "virtualbox" do |vb|
    vb.customize ["setextradata", :id,
                  "VBoxInternal2/SharedFoldersEnableSymlinksCreate/vagrant", "1"]
  end

  # Forward usual dev port through to host machine
  config.vm.network :forwarded_port, guest: 3000, host: 3000
  # Also forward production port just in case
  config.vm.network :forwarded_port, guest: 80, host: 8080
  # Forward a folder for the repo so that code can be worked on from outside the
  # VM as usual
  config.vm.synced_folder ".", "/home/ubuntu/#{repo_dirname}", create: true

  config.vm.define "#{repo_dirname}-vm" do |repo_vm|
    repo_vm.vm.box = "ubuntu/xenial64"
    repo_vm.vm.host_name = "#{repo_dirname}-vm"
    repo_vm.vm.provision :shell do |sh|
      sh.path = "vagrant_provision.sh"
      sh.privileged = false
      sh.env = {
        REPO_DIR: repo_dirname
      }
    end
  end

end

vagrant_provision.sh

#!/usr/bin/env bash

function set_locale() {
    sudo locale-gen en.US
}

function get_builds() {
    sudo apt-get update &&
        sudo apt-get upgrade -y &&
        sudo apt-get install -y curl build-essential
}

function get_n_installer() {
    if [ -f n-install ]
    then
        echo "n installer already exists. Not downloading."
        return 0
    else
        echo "n installer not found. Downloading..."
        wget -L https://git.io/n-install
    fi
}

function install_n() {
    if [ -d "n" ]
    then
        echo "n install directory already exists. Not installing."
        return 0
    else
        echo "n install directory not found. Installing..."
        yes | bash n-install
    fi
}

function add_github_keys() {
    # Adds the github server key to known hosts
    ssh-keyscan github.com >> ~/.ssh/known_hosts &&
        return 0 || return 1
}

function add_n_to_path() {
    # Added by n-install, but ignored by vagrant
    export N_PREFIX="$HOME/n";
    [[ :$PATH: == *":$N_PREFIX/bin:"* ]] || PATH+=":$N_PREFIX/bin"
}

function get_repo() {
    if [ -d "$2" ]
    then
        echo "Destination directory $2 already exists. Deleting contents..."
        rm -rfv ./$2
    fi
    echo "Cloning $1 into $2..."
    git clone $1 $2
}

function install_npm_deps() {
    echo "Installing npm dependencies..."
    npm install
}

function rebuild_node_sass() {
    # Needed because of https://github.com/sass/node-sass/issues/1579
    npm rebuild node-sass
}

# . ~/.bashrc &&
set_locale &&
    add_github_keys &&
    get_builds &&
    get_n_installer &&
    install_n &&
    add_n_to_path &&
    cd $REPO_DIR &&
    install_npm_deps &&
    rebuild_node_sass &&
    echo "Provisioned user is: $USER" &&
    echo "Frontend provisioned. To run, type 'vagrant ssh'."

似乎导致问题的主要步骤是由非特权提供者执行npm install。有时an archive unpacking error会发生,但有时候,npm会因ENOENT错误而失败。

使用vagrant ssh登录以完成作业后,将显示只读文件系统错误。尽管如此,系统上仍有足够的空间(例如,剩余8GB中有7个)。

当webpack服务器在相同的情况下运行时,也会出现只读文件系统错误。

有些问题和票据浮出水面引用了类似的错误,但我还没有看到对潜在机制的探索。这笔交易是什么?

2 个答案:

答案 0 :(得分:1)

我遇到过与Vagrant 1.8.7和Virtualbox 5.1.10类似的问题。通过将cpu核心数量减少到1:

,我能够修复文件系统只读问题
config.vm.provider "virtualbox" do |v|
  v.cpus = 1
end

我仍然会遇到构建问题(npm模块未找到,ENOENT,ELIFECYCLE,......)但速度较慢。不幸的是,我无法找到这些错误的根本原因。

在我的设置中,npm没有写入共享目录。如果写入位置是共享文件夹,您可以尝试a different syncing mechanism来解决虚拟机共享文件夹实现的某些限制。

答案 1 :(得分:1)

我设法通过symlinking / vagrant共享文件夹外的node_modules来解决这个问题,即/ home / vagrant / node_modules:

mkdir /home/vagrant/node_modules
ln -sf /home/vagrant/node_modules /vagrant/

这样做的缺点是你不能再在外面设置npm安装,只能在内部安装(除非你的主机上有mkdir / vagrant)。