Implement remote plugin manager backed by vagrant go

This commit is contained in:
Chris Roberts 2021-12-17 14:56:27 -08:00 committed by Paul Hinze
parent acb32d33f7
commit fb2319f1e2
No known key found for this signature in database
GPG Key ID: B69DEDF2D55501C0

View File

@ -6,52 +6,207 @@ module Vagrant
# This class maintains a list of all the registered plugins as well
# as provides methods that allow querying all registered components of
# those plugins as a single unit.
class Manager < Vagrant::Plugin::V2::Manager
attr_reader :registered
class Manager
WRAPPER_CLASS = proc do |klass|
class << klass
attr_accessor :plugin_name, :type
def name
"Vagrant::Plugin::Remote::#{type.to_s.split(/-_/).map(&:capitalize).join}"
end
def initialize
@logger = Log4r::Logger.new("vagrant::plugin::remote::manager")
@logger.debug("initializing remote manager")
# Copy in local Ruby registered plugins
@registered = Vagrant.plugin("2").v2_manager.registered
def to_s
"<#{name} plugin_name=#{plugin_name}>"
end
def inspect
"<#{name} plugin_name=#{plugin_name} type=#{type}>"
end
def inherited(klass)
klass.plugin_name = plugin_name
klass.type = type
end
end
def initialize(*args, **kwargs, &block)
info = Thread.current.thread_variable_get(:service_info)
if info&.plugin_manager
client = info.plugin_manager.get_plugin(
name: self.class.plugin_name,
type: self.class.type
)
kwargs[:client] = client
end
super(*args, **kwargs, &block)
end
def name
self.class.plugin_name
end
def inspect
"<#{self.class.name}:#{object_id} plugin_name=#{name} type=#{self.class.type}>"
end
def to_s
"<#{self.class.name}:#{object_id}>"
end
end
attr_reader :real_manager
def initialize(manager)
@logger = Log4r::Logger.new(self.class.name.downcase)
@real_manager = manager
end
def method_missing(m, *args, **kwargs, &block)
@logger.debug("method not defined, sending to real manager `#{m}'")
@real_manager.send(m, *args, **kwargs, &block)
end
def plugin_manager
info = Thread.current.thread_variable_get(:service_info)
info.plugin_manager if info
end
# This returns all synced folder implementations.
#
# @return [Registry]
def synced_folders
return real_manager.synced_folders if plugin_manager.nil?
Registry.new.tap do |result|
@registered.each do |plugin|
plugin.components.synced_folders.each do |k, v|
sf_class = Class.new(v[0])
sf_class.class_eval do
def initialize(*_, **_)
super(@@client)
end
def self.client=(val)
@@client=val
end
def self.client
@@client
end
end
# TODO: set the actual client
sf_class.client = "todo"
v = [sf_class] + v[1..]
result.register(k) do
v
end
plugin_manager.list_plugins(:synced_folder).each do |plg|
sf_class = Class.new(V2::SyncedFolder, &WRAPPER_CLASS)
sf_class.plugin_name = plg[:name]
sf_class.type = plg[:type]
result.register(plg[:name].to_sym) do
sf_class
end
end
end
end
# Registers remote plugins provided from the client
#
# @param [VagrantPlugin::Command::Serve::Client::Basis]
def register_remote_plugins(client)
# TODO
def commands
return real_manager.synced_folders if plugin_manager.nil?
Registry.new.tap do |result|
plugin_manager.list_plugins(:command).each do |plg|
sf_class = Class.new(V2::Command, &WRAPPER_CLASS)
sf_class.plugin_name = plg[:name]
sf_class.type = plg[:type]
result.register(plg[:name].to_sym) do
[proc{sf_class}, {}] # TODO(spox): Options hash should be what?
end
end
end
end
# def communicators
# return real_manager.synced_folders if plugin_manager.nil?
# Registry.new.tap do |result|
# plugin_manager.list_plugins(:communicator).each do |plg|
# sf_class = Class.new(V2::Communicator, &WRAPPER_CLASS)
# sf_class.plugin_name = plg[:name]
# sf_class.type = plg[:type]
# result.register(plg[:name].to_sym) do
# proc{sf_class}
# end
# end
# end
# end
# def config
# return real_manager.synced_folders if plugin_manager.nil?
# Registry.new.tap do |result|
# plugin_manager.list_plugins(:config).each do |plg|
# sf_class = Class.new(V2::Config, &WRAPPER_CLASS)
# sf_class.plugin_name = plg[:name]
# sf_class.type = plg[:type]
# result.register(plg[:name].to_sym) do
# proc{sf_class}
# end
# end
# end
# end
def guests
return real_manager.synced_folders if plugin_manager.nil?
Registry.new.tap do |result|
plugin_manager.list_plugins(:guest).each do |plg|
sf_class = Class.new(V2::Guest, &WRAPPER_CLASS)
sf_class.plugin_name = plg[:name]
sf_class.type = plg[:type]
result.register(plg[:name].to_sym) do
proc{sf_class}
end
end
end
end
def hosts
return real_manager.synced_folders if plugin_manager.nil?
Registry.new.tap do |result|
plugin_manager.list_plugins(:host).each do |plg|
sf_class = Class.new(V2::Host, &WRAPPER_CLASS)
sf_class.plugin_name = plg[:name]
sf_class.type = plg[:type]
result.register(plg[:name].to_sym) do
proc{sf_class}
end
end
end
end
# def providers
# return real_manager.synced_folders if plugin_manager.nil?
# Registry.new.tap do |result|
# plugin_manager.list_plugins(:provider).each do |plg|
# sf_class = Class.new(V2::Provider, &WRAPPER_CLASS)
# sf_class.plugin_name = plg[:name]
# sf_class.type = plg[:type]
# result.register(plg[:name].to_sym) do
# proc{sf_class}
# end
# end
# end
# end
# def provisioners
# return real_manager.synced_folders if plugin_manager.nil?
# Registry.new.tap do |result|
# plugin_manager.list_plugins(:provisioner).each do |plg|
# sf_class = Class.new(V2::Provisioner, &WRAPPER_CLASS)
# sf_class.plugin_name = plg[:name]
# sf_class.type = plg[:type]
# result.register(plg[:name].to_sym) do
# proc{sf_class}
# end
# end
# end
# end
# def pushes
# return real_manager.synced_folders if plugin_manager.nil?
# Registry.new.tap do |result|
# plugin_manager.list_plugins(:push).each do |plg|
# sf_class = Class.new(V2::Push, &WRAPPER_CLASS)
# sf_class.plugin_name = plg[:name]
# sf_class.type = plg[:type]
# result.register(plg[:name].to_sym) do
# proc{sf_class}
# end
# end
# end
# end
end
end
end