Forwarded ports
This commit is contained in:
parent
c59defa7e8
commit
a39df9f150
|
@ -7,17 +7,9 @@ module Vagrant
|
||||||
end
|
end
|
||||||
|
|
||||||
def call(env)
|
def call(env)
|
||||||
proc = lambda do |vm|
|
env[:ui].info I18n.t("vagrant.actions.vm.clear_forward_ports.deleting")
|
||||||
env[:ui].info I18n.t("vagrant.actions.vm.clear_forward_ports.deleting")
|
env[:vm].driver.clear_forwarded_ports
|
||||||
|
|
||||||
vm.network_adapters.each do |na|
|
|
||||||
na.nat_driver.forwarded_ports.dup.each do |fp|
|
|
||||||
fp.destroy
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
env["vm.modify"].call(proc)
|
|
||||||
@app.call(env)
|
@app.call(env)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,11 +1,7 @@
|
||||||
require File.join(File.dirname(__FILE__), 'forward_ports_helpers')
|
|
||||||
|
|
||||||
module Vagrant
|
module Vagrant
|
||||||
module Action
|
module Action
|
||||||
module VM
|
module VM
|
||||||
class ForwardPorts
|
class ForwardPorts
|
||||||
include ForwardPortsHelpers
|
|
||||||
|
|
||||||
def initialize(app,env)
|
def initialize(app,env)
|
||||||
@app = app
|
@app = app
|
||||||
@env = env
|
@env = env
|
||||||
|
@ -35,7 +31,7 @@ module Vagrant
|
||||||
# report the collisions detected or will attempt to fix them
|
# report the collisions detected or will attempt to fix them
|
||||||
# automatically if the port is configured to do so.
|
# automatically if the port is configured to do so.
|
||||||
def external_collision_check
|
def external_collision_check
|
||||||
existing = used_ports
|
existing = @env[:vm].driver.read_used_ports
|
||||||
@env[:vm].config.vm.forwarded_ports.each do |name, options|
|
@env[:vm].config.vm.forwarded_ports.each do |name, options|
|
||||||
if existing.include?(options[:hostport].to_i)
|
if existing.include?(options[:hostport].to_i)
|
||||||
handle_collision(name, options, existing)
|
handle_collision(name, options, existing)
|
||||||
|
@ -86,35 +82,41 @@ module Vagrant
|
||||||
def call(env)
|
def call(env)
|
||||||
@env = env
|
@env = env
|
||||||
|
|
||||||
proc = lambda do |vm|
|
env[:ui].info I18n.t("vagrant.actions.vm.forward_ports.forwarding")
|
||||||
env[:ui].info I18n.t("vagrant.actions.vm.forward_ports.forwarding")
|
forward_ports(env[:vm])
|
||||||
forward_ports(vm)
|
|
||||||
end
|
|
||||||
|
|
||||||
env["vm.modify"].call(proc)
|
|
||||||
@app.call(env)
|
@app.call(env)
|
||||||
end
|
end
|
||||||
|
|
||||||
def forward_ports(vm)
|
def forward_ports(vm)
|
||||||
|
ports = []
|
||||||
|
|
||||||
@env[:vm].config.vm.forwarded_ports.each do |name, options|
|
@env[:vm].config.vm.forwarded_ports.each do |name, options|
|
||||||
adapter = options[:adapter]
|
adapter = options[:adapter] + 1
|
||||||
message_attributes = {
|
message_attributes = {
|
||||||
:name => name,
|
:name => name,
|
||||||
:guest_port => options[:guestport],
|
:guest_port => options[:guestport],
|
||||||
:host_port => options[:hostport],
|
:host_port => options[:hostport],
|
||||||
:adapter => adapter + 1
|
:adapter => adapter
|
||||||
}
|
}
|
||||||
|
|
||||||
# Assuming the only reason to establish port forwarding is because the VM is using Virtualbox NAT networking.
|
# Assuming the only reason to establish port forwarding is
|
||||||
# Host-only or Bridged networking don't require port-forwarding and establishing forwarded ports on these
|
# because the VM is using Virtualbox NAT networking. Host-only
|
||||||
# attachment types has uncertain behaviour.
|
# bridged networking don't require port-forwarding and establishing
|
||||||
if vm.network_adapters[adapter].attachment_type == :nat
|
# forwarded ports on these attachment types has uncertain behaviour.
|
||||||
@env[:ui].info(I18n.t("vagrant.actions.vm.forward_ports.forwarding_entry", message_attributes))
|
@env[:ui].info(I18n.t("vagrant.actions.vm.forward_ports.forwarding_entry",
|
||||||
forward_port(vm, name, options)
|
message_attributes))
|
||||||
else
|
|
||||||
@env[:ui].info(I18n.t("vagrant.actions.vm.forward_ports.non_nat", message_attributes))
|
# Add the options to the ports array to send to the driver later
|
||||||
end
|
ports << options.merge(:name => name, :adapter => adapter)
|
||||||
|
|
||||||
|
# TODO: Check for non-nat again... This was removed during the VBoxManage
|
||||||
|
# transition but should be brought back.
|
||||||
|
# @env[:ui].info(I18n.t("vagrant.actions.vm.forward_ports.non_nat",
|
||||||
|
# message_attributes))
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@env[:vm].driver.forward_ports(ports)
|
||||||
end
|
end
|
||||||
|
|
||||||
#--------------------------------------------------------------
|
#--------------------------------------------------------------
|
||||||
|
|
|
@ -1,28 +0,0 @@
|
||||||
module Vagrant
|
|
||||||
module Action
|
|
||||||
module VM
|
|
||||||
# Helper methods for forwarding ports. Requires that the environment
|
|
||||||
# is set to the `@env` instance variable.
|
|
||||||
module ForwardPortsHelpers
|
|
||||||
# Returns an array of used ports. This method is implemented
|
|
||||||
# differently depending on the VirtualBox version, but the
|
|
||||||
# behavior is the same.
|
|
||||||
#
|
|
||||||
# @return [Array<String>]
|
|
||||||
def used_ports
|
|
||||||
result = VirtualBox::VM.all.collect do |vm|
|
|
||||||
if vm.accessible? && vm.running? && vm.uuid != @env["vm"].uuid
|
|
||||||
vm.network_adapters.collect do |na|
|
|
||||||
na.nat_driver.forwarded_ports.collect do |fp|
|
|
||||||
fp.hostport.to_i
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
result.flatten.uniq
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
|
@ -24,6 +24,59 @@ module Vagrant
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
# This clears the forwarded ports that have been set on the
|
||||||
|
# virtual machine.
|
||||||
|
def clear_forwarded_ports
|
||||||
|
args = []
|
||||||
|
read_forwarded_ports(@uuid).each do |nic, name, _, _|
|
||||||
|
args.concat(["--natpf#{nic}", "delete", name])
|
||||||
|
end
|
||||||
|
|
||||||
|
execute("modifyvm", @uuid, *args) if !args.empty?
|
||||||
|
end
|
||||||
|
|
||||||
|
# This deletes the VM with the given name.
|
||||||
|
def delete
|
||||||
|
execute("unregistervm", @uuid, "--delete")
|
||||||
|
end
|
||||||
|
|
||||||
|
# Forwards a set of ports for a VM.
|
||||||
|
#
|
||||||
|
# This will not affect any previously set forwarded ports,
|
||||||
|
# so be sure to delete those if you need to.
|
||||||
|
#
|
||||||
|
# The format of each port hash should be the following:
|
||||||
|
#
|
||||||
|
# {
|
||||||
|
# :name => "foo",
|
||||||
|
# :host_port => 8500,
|
||||||
|
# :guest_port => 80,
|
||||||
|
# :adapter => 1,
|
||||||
|
# :protocol => "tcp"
|
||||||
|
# }
|
||||||
|
#
|
||||||
|
# Note that "adapter" and "protocol" are optional and will default
|
||||||
|
# to 1 and "tcp" respectively.
|
||||||
|
#
|
||||||
|
# @param [Array<Hash>] ports An array of ports to set. See documentation
|
||||||
|
# for more information on the format.
|
||||||
|
def forward_ports(ports)
|
||||||
|
args = []
|
||||||
|
ports.each do |options|
|
||||||
|
pf_builder = [options[:name],
|
||||||
|
options[:protocol] || "tcp",
|
||||||
|
"",
|
||||||
|
options[:host_port],
|
||||||
|
"",
|
||||||
|
options[:guest_port]]
|
||||||
|
|
||||||
|
args.concat(["--natpf#{options[:adapter] || 1}",
|
||||||
|
pf_builder.join(",")])
|
||||||
|
end
|
||||||
|
|
||||||
|
execute("modifyvm", @uuid, *args)
|
||||||
|
end
|
||||||
|
|
||||||
# Imports the VM with the given path to the OVF file. It returns
|
# Imports the VM with the given path to the OVF file. It returns
|
||||||
# the UUID as a string.
|
# the UUID as a string.
|
||||||
def import(ovf, name)
|
def import(ovf, name)
|
||||||
|
@ -36,11 +89,6 @@ module Vagrant
|
||||||
nil
|
nil
|
||||||
end
|
end
|
||||||
|
|
||||||
# This deletes the VM with the given name.
|
|
||||||
def delete
|
|
||||||
execute("unregistervm", @uuid, "--delete")
|
|
||||||
end
|
|
||||||
|
|
||||||
# This reads the guest additions version for a VM.
|
# This reads the guest additions version for a VM.
|
||||||
def read_guest_additions_version
|
def read_guest_additions_version
|
||||||
output = execute("guestproperty", "get", @uuid, "/VirtualBox/GuestAdd/Version")
|
output = execute("guestproperty", "get", @uuid, "/VirtualBox/GuestAdd/Version")
|
||||||
|
@ -61,6 +109,21 @@ module Vagrant
|
||||||
nil
|
nil
|
||||||
end
|
end
|
||||||
|
|
||||||
|
# This will read all the used ports for port forwarding by
|
||||||
|
# all virtual machines.
|
||||||
|
def read_used_ports
|
||||||
|
ports = []
|
||||||
|
execute("list", "vms").split("\n").each do |line|
|
||||||
|
if line =~ /^".+?" \{(.+?)\}$/
|
||||||
|
read_forwarded_ports($1.to_s, true).each do |_, _, hostport, _|
|
||||||
|
ports << hostport
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
ports
|
||||||
|
end
|
||||||
|
|
||||||
# This sets the MAC address for a network adapter.
|
# This sets the MAC address for a network adapter.
|
||||||
def set_mac_address(mac)
|
def set_mac_address(mac)
|
||||||
execute("modifyvm", @uuid, "--macaddress1", mac)
|
execute("modifyvm", @uuid, "--macaddress1", mac)
|
||||||
|
@ -68,6 +131,33 @@ module Vagrant
|
||||||
|
|
||||||
protected
|
protected
|
||||||
|
|
||||||
|
# This returns a list of the forwarded ports in the form
|
||||||
|
# of `[nic, name, hostport, guestport]`.
|
||||||
|
#
|
||||||
|
# @return [Array<Array>]
|
||||||
|
def read_forwarded_ports(uuid, active_only=false)
|
||||||
|
results = []
|
||||||
|
current_nic = nil
|
||||||
|
execute("showvminfo", uuid, "--machinereadable").split("\n").each do |line|
|
||||||
|
# This is how we find the nic that a FP is attached to,
|
||||||
|
# since this comes first.
|
||||||
|
current_nic = $1.to_i if line =~ /^nic(\d+)=".+?"$/
|
||||||
|
|
||||||
|
# If we care about active VMs only, then we check the state
|
||||||
|
# to verify the VM is running.
|
||||||
|
if active_only && line =~ /^VMState="(.+?)"$/ && $1.to_s != "running"
|
||||||
|
return []
|
||||||
|
end
|
||||||
|
|
||||||
|
# Parse out the forwarded port information
|
||||||
|
if line =~ /^Forwarding.+?="(.+?),.+?,.*?,(.+?),.*?,(.+?)"$/
|
||||||
|
results << [current_nic, $1.to_s, $2.to_i, $3.to_i]
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
results
|
||||||
|
end
|
||||||
|
|
||||||
# This returns the version of VirtualBox that is running.
|
# This returns the version of VirtualBox that is running.
|
||||||
#
|
#
|
||||||
# @return [String]
|
# @return [String]
|
||||||
|
|
Loading…
Reference in New Issue