lib/basalt/packages.rb
require 'basalt/version'
require 'basalt/config'
require 'basalt/basaltfile'
require 'basalt/packages/context'
require 'colorize'
require 'docopt'
require 'fileutils'
require 'ostruct'
require 'yaml'
module Basalt
class Packages
DOC = %Q(Usage:
%<binname>s package new [options] NAME
%<binname>s package install [options] NAME...
%<binname>s package uninstall [options] NAME...
%<binname>s package sync [options] NAME...
%<binname>s package update [options] NAME...
%<binname>s package list [options]
%<binname>s package list-available [options]
%<binname>s package list-installed [options]
Options:
-f, --basaltfile=BASALTFILE
-i, --install-method=METHOD
-v, --verbose
)
attr_writer :basaltfile
def initialize(basaltfile = nil)
@basaltfile = basaltfile || Basaltfile.new
end
def basaltfile
@basaltfile
end
def basaltfile_package_map
@basaltfile.packages.each_with_object({}) { |pkg, hash| hash[pkg.name] = pkg }
end
def config
@config ||= Basalt::Config::Sys.new
end
def repoconfig
@repoconfig ||= OpenStruct.new(pkgdir: basaltfile.pkgdir,
install_method: basaltfile.install_method || config[:install_method])
end
def context
@context ||= Context.new(config.get, repoconfig)
end
def generate_packages_list(options = {})
pkgs = context.repo.installed
m = basaltfile_package_map
# only install packages that are listed in the basaltfile spec
# TODO move this elsewhere, dunno where yet.
pkgs.select! { |pkg| m.key?(pkg.pkgname) }
DependecySolver.solve(pkgs, options)
end
def generate_packages_require(options = {})
m = basaltfile_package_map
contents = ''
contents << "# AutoGenerated by Basalt\n"
contents << "$LOAD_PATH << '#{basaltfile.pkgdir}'\n\n"
generate_packages_list(options).each do |pkg|
next unless m[pkg.pkgname].options[:autoload]
contents << pkg.entry_point_contents
contents << "\n" unless contents.end_with?("\n")
end
filename = File.join(basaltfile.pkgdir, 'load.rb')
File.write(filename, contents)
STDERR.puts "\tGENERATED".light_green + "\t#{filename}"
end
private def each_basaltfile_package(options = {})
basaltfile.packages.each do |bpkg|
yield bpkg, bpkg.options.merge(options)
end
end
def install(options = {})
each_basaltfile_package(options) do |bpkg, opts|
context.install(bpkg.name, opts)
end
generate_packages_require
end
def update(options = {})
each_basaltfile_package(options) do |bpkg, opts|
context.update(bpkg.name, opts)
end
generate_packages_require
end
def sync(options = {})
each_basaltfile_package(options) do |bpkg, opts|
context.sync(bpkg.name, opts)
end
generate_packages_require
end
private def multi_exec(list)
if list.is_a?(Array)
list.each do |v|
begin
yield v
rescue
end
end
else
begin
yield list
rescue
end
end
end
def run(rootfilename, argv, rctx)
rctx.verbose.puts 'Running package subcommand'
doc = DOC % ({ binname: rootfilename })
data = Docopt.docopt(doc, argv: argv, version: VERSION, help: true)
names = data['NAME']
options = {}
options[:basaltfile] = data['--basaltfile'] || rctx[:basaltfile]
options[:install_method] = data['--install-method'] || rctx[:install_method]
options[:verbose] = data['--verbose'] || rctx[:verbose]
rctx.verbose.puts "(#{self.class.name}).options: #{options}"
if bsf = options[:basaltfile]
self.basaltfile = Basaltfile.new(bsf)
end
if data['new']
multi_exec(names) { |name| context.new(name, options) }
elsif data['install']
multi_exec(names) { |name| context.install(name, options) }
elsif data['uninstall']
multi_exec(names) { |name| context.uninstall(name, options) }
elsif data['sync']
multi_exec(names) { |name| context.sync(name, options) }
elsif data['update']
multi_exec(names) { |name| context.update(name, options) }
elsif data['list']
context.list(options)
elsif data['list-available']
context.list_available(options)
elsif data['list-installed']
context.list_installed(options)
end
end
end
end