99 lines
3.4 KiB
Markdown
99 lines
3.4 KiB
Markdown
|
---
|
||
|
sidebar_current: "plugins-guests"
|
||
|
---
|
||
|
|
||
|
# Plugin Development: Guests
|
||
|
|
||
|
This page documents how to add new guest OS detection to Vagrant, allowing
|
||
|
Vagrant to properly configure new operating systems.
|
||
|
Prior to reading this, you should be familiar
|
||
|
with the [plugin development basics](/v2/plugins/development-basics.html).
|
||
|
|
||
|
<div class="alert alert-warn">
|
||
|
<p>
|
||
|
<strong>Warning: Advanced Topic!</strong> Developing plugins is an
|
||
|
advanced topic that only experienced Vagrant users who are reasonably
|
||
|
comfortable with Ruby should approach.
|
||
|
</p>
|
||
|
</div>
|
||
|
|
||
|
Vagrant has many features that requires doing guest OS-specific
|
||
|
actions, such as mounting folders, configuring networks, etc. These
|
||
|
tasks vary from operating system to operating system. If you find that
|
||
|
one of these doesn't work for your operating system, then maybe the
|
||
|
guest implementation is incomplete or incorrect.
|
||
|
|
||
|
## Definition Component
|
||
|
|
||
|
Within the context of a plugin definition, new guests can be defined
|
||
|
like so:
|
||
|
|
||
|
```ruby
|
||
|
guest "ubuntu" do
|
||
|
require_relative "guest"
|
||
|
Guest
|
||
|
end
|
||
|
```
|
||
|
|
||
|
Guests are defined with the `guest` method. The first argument is the
|
||
|
name of the guest. This name isn't actually used anywhere, but may in the
|
||
|
future, so choose something helpful. Then, the block argument returns a
|
||
|
class that implements the `Vagrant.plugin(2, :guest)` interface.
|
||
|
|
||
|
## Implementation
|
||
|
|
||
|
Implementations of guests subclass `Vagrant.plugin("2", "guest")`. Within
|
||
|
this implementation, only the `detect?` method needs to be implemented.
|
||
|
|
||
|
The `detect?` method is called by Vagrant at some point after the machine
|
||
|
is booted in order to determine what operating system the guest is running.
|
||
|
If you detect that it is your operating system, return `true` from `detect?`.
|
||
|
Otherwise, return `false`.
|
||
|
|
||
|
Communication channels to the machine are guranteed to be running at this
|
||
|
point, so the most common way to detect the operating system is to do
|
||
|
some basic testing:
|
||
|
|
||
|
```
|
||
|
class MyGuest < Vagrant.plugin("2", "guest")
|
||
|
def detect?(machine)
|
||
|
machine.communicate.test("cat /etc/myos-release")
|
||
|
end
|
||
|
end
|
||
|
```
|
||
|
|
||
|
After detecting an OS, that OS is used for various
|
||
|
[guest capabilities](/v2/plugins/guest_capabilities.html) that may be
|
||
|
required.
|
||
|
|
||
|
## Guest Inheritance
|
||
|
|
||
|
Vagrant also supports a form of inheritance for guests, since sometimes
|
||
|
operating systems stem from a common root. A good example of this is Linux
|
||
|
is the root of Debian, which further is the root of Ubuntu in many cases.
|
||
|
Inheritance allows guests to share a lot of common behavior while allowing
|
||
|
distro-specific overrides.
|
||
|
|
||
|
Inheritance is not done via standard Ruby class inheritance because Vagrant
|
||
|
uses a custom [capability-based](/v2/plugins/guest_capabilities.html) system.
|
||
|
Vagrant handles inheritance dispatch for you.
|
||
|
|
||
|
To subclass another guest, specify that guest's name as a second parameter
|
||
|
in the guest definition:
|
||
|
|
||
|
```ruby
|
||
|
guest "ubuntu", "debian" do
|
||
|
require_relative "guest"
|
||
|
Guest
|
||
|
end
|
||
|
```
|
||
|
|
||
|
With the above component, the "ubuntu" guest inherits from "debian." When
|
||
|
a capability is looked up for "ubuntu", all capabilities from "debian" are
|
||
|
also available, and any capabilities in "ubuntu" override parent capabilities.
|
||
|
|
||
|
When detecting operating systems with `detect?`, Vagrant always does a
|
||
|
depth-first search by searching the children operating systems before
|
||
|
checking their parents. Therefore, it is guaranteed in the above example
|
||
|
that the `detect?` method on "ubuntu" will be called before "debian."
|