autoproj 1.4.4 → 1.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/History.txt +15 -0
- data/Manifest.txt +5 -1
- data/README.txt +1 -41
- data/Rakefile +1 -1
- data/bin/autoproj +62 -747
- data/doc/guide/src/autoproj_bootstrap +54 -9
- data/doc/guide/src/customization.page +5 -4
- data/doc/guide/src/index.page +1 -41
- data/doc/guide/src/overview.png +0 -0
- data/doc/guide/src/overview.svg +537 -0
- data/doc/guide/src/package_sets/autobuild.page +37 -13
- data/doc/guide/src/package_sets/importers.page +1 -1
- data/doc/guide/src/package_sets/manifest-xml.page +2 -2
- data/doc/guide/src/package_sets/osdeps.page +14 -9
- data/doc/guide/src/quick_start.page +110 -0
- data/doc/guide/src/{structure.page → writing_manifest.page} +47 -57
- data/lib/autoproj.rb +1 -0
- data/lib/autoproj/autobuild.rb +74 -32
- data/lib/autoproj/cmdline.rb +912 -0
- data/lib/autoproj/default.osdeps +12 -2
- data/lib/autoproj/manifest.rb +141 -88
- data/lib/autoproj/osdeps.rb +42 -7
- data/lib/autoproj/version.rb +1 -1
- metadata +90 -53
data/lib/autoproj/default.osdeps
CHANGED
@@ -12,7 +12,17 @@ ruby18:
|
|
12
12
|
- dev-lang/ruby:1.8
|
13
13
|
|
14
14
|
ruby19:
|
15
|
-
debian
|
15
|
+
debian:
|
16
|
+
squeeze,sid:
|
17
|
+
- ruby1.9.1
|
18
|
+
- ruby1.9.1-dev
|
19
|
+
- rubygems1.9.1
|
20
|
+
stable:
|
21
|
+
- ruby1.9.1
|
22
|
+
- ruby1.9.1-dev
|
23
|
+
- rubygems1.9.1
|
24
|
+
|
25
|
+
ubuntu:
|
16
26
|
- ruby1.9.1
|
17
27
|
- ruby1.9.1-dev
|
18
28
|
- rubygems1.9.1
|
@@ -46,7 +56,7 @@ autoproj: gem
|
|
46
56
|
# The following definitions are for the VCS and build systems
|
47
57
|
git:
|
48
58
|
debian,ubuntu: git-core
|
49
|
-
gentoo: dev-
|
59
|
+
gentoo: dev-vcs/git
|
50
60
|
arch: git
|
51
61
|
svn:
|
52
62
|
debian,ubuntu: subversion
|
data/lib/autoproj/manifest.rb
CHANGED
@@ -3,18 +3,6 @@ require 'utilrb/kernel/options'
|
|
3
3
|
require 'nokogiri'
|
4
4
|
require 'set'
|
5
5
|
|
6
|
-
module Autobuild
|
7
|
-
class Package
|
8
|
-
def os_packages
|
9
|
-
@os_packages || Array.new
|
10
|
-
end
|
11
|
-
def depends_on_os_package(name)
|
12
|
-
@os_packages ||= Array.new
|
13
|
-
@os_packages << name
|
14
|
-
end
|
15
|
-
end
|
16
|
-
end
|
17
|
-
|
18
6
|
module Autoproj
|
19
7
|
@build_system_dependencies = Set.new
|
20
8
|
|
@@ -106,13 +94,22 @@ module Autoproj
|
|
106
94
|
@type == 'local'
|
107
95
|
end
|
108
96
|
|
97
|
+
def self.to_absolute_url(url, root_dir = nil)
|
98
|
+
# NOTE: we MUST use nil as default argument of root_dir as we don't
|
99
|
+
# want to call Autoproj.root_dir unless completely necessary
|
100
|
+
# (to_absolute_url might be called on installations that are being
|
101
|
+
# bootstrapped, and as such don't have a root dir yet).
|
102
|
+
url = Autoproj.single_expansion(url, 'HOME' => ENV['HOME'])
|
103
|
+
if url && url !~ /^(\w+:\/)?\/|^\w+\@|^(\w+\@)?[\w\.-]+:/
|
104
|
+
url = File.expand_path(url, root_dir || Autoproj.root_dir)
|
105
|
+
end
|
106
|
+
url
|
107
|
+
end
|
108
|
+
|
109
109
|
def create_autobuild_importer
|
110
110
|
return if type == "none"
|
111
111
|
|
112
|
-
url =
|
113
|
-
if url && url !~ /^(\w+:\/)?\/|^\w+\@|^(\w+\@)?[\w\.-]+:/
|
114
|
-
url = File.expand_path(url, Autoproj.root_dir)
|
115
|
-
end
|
112
|
+
url = VCSDefinition.to_absolute_url(self.url)
|
116
113
|
Autobuild.send(type, url, options)
|
117
114
|
end
|
118
115
|
|
@@ -196,26 +193,44 @@ module Autoproj
|
|
196
193
|
|
197
194
|
# True if this source has already been checked out on the local autoproj
|
198
195
|
# installation
|
199
|
-
def present?; File.directory?(
|
196
|
+
def present?; File.directory?(raw_local_dir) end
|
200
197
|
# True if this source is local, i.e. is not under a version control
|
201
198
|
def local?; vcs.local? end
|
202
199
|
# True if this source defines nothing
|
203
200
|
def empty?
|
204
201
|
!source_definition['version_control'] &&
|
205
202
|
!each_package.find { true } &&
|
206
|
-
!File.exists?(File.join(
|
207
|
-
!File.exists?(File.join(
|
203
|
+
!File.exists?(File.join(raw_local_dir, "overrides.rb")) &&
|
204
|
+
!File.exists?(File.join(raw_local_dir, "init.rb"))
|
208
205
|
end
|
209
206
|
|
210
|
-
|
211
|
-
def local_dir
|
207
|
+
def raw_local_dir
|
212
208
|
if local?
|
213
|
-
vcs.url
|
209
|
+
return vcs.url
|
214
210
|
else
|
215
211
|
File.join(Autoproj.remotes_dir, automatic_name)
|
216
212
|
end
|
217
213
|
end
|
218
214
|
|
215
|
+
def user_local_dir
|
216
|
+
if local?
|
217
|
+
return vcs.url
|
218
|
+
else
|
219
|
+
File.join(Autoproj.config_dir, 'remotes', name)
|
220
|
+
end
|
221
|
+
end
|
222
|
+
|
223
|
+
# The directory in which data for this source will be checked out
|
224
|
+
def local_dir
|
225
|
+
ugly_dir = raw_local_dir
|
226
|
+
pretty_dir = user_local_dir
|
227
|
+
if File.symlink?(pretty_dir) && File.readlink(pretty_dir) == ugly_dir
|
228
|
+
pretty_dir
|
229
|
+
else
|
230
|
+
ugly_dir
|
231
|
+
end
|
232
|
+
end
|
233
|
+
|
219
234
|
# A name generated from the VCS url
|
220
235
|
def automatic_name
|
221
236
|
vcs.to_s.gsub(/[^\w]/, '_')
|
@@ -237,7 +252,7 @@ module Autoproj
|
|
237
252
|
raise InternalError, "source #{vcs} has not been fetched yet, cannot load description for it"
|
238
253
|
end
|
239
254
|
|
240
|
-
source_file = File.join(
|
255
|
+
source_file = File.join(raw_local_dir, "source.yml")
|
241
256
|
if !File.exists?(source_file)
|
242
257
|
raise ConfigError, "source #{vcs.type}:#{vcs.url} should have a source.yml file, but does not"
|
243
258
|
end
|
@@ -255,21 +270,30 @@ module Autoproj
|
|
255
270
|
source_definition
|
256
271
|
end
|
257
272
|
|
273
|
+
# Load and validate the name from the YAML hash
|
258
274
|
def load_name
|
259
|
-
definition = raw_description_file
|
275
|
+
definition = @source_definition || raw_description_file
|
260
276
|
@name = definition['name']
|
261
|
-
|
277
|
+
|
278
|
+
if @name !~ /^[\w_\.-]+$/
|
279
|
+
raise ConfigError, "invalid source name '#{@name}': source names can only contain alphanumeric characters, and .-_"
|
280
|
+
elsif @name == "local"
|
262
281
|
raise ConfigError, "source #{self} is named 'local', but this is a reserved name"
|
263
282
|
end
|
264
283
|
|
265
284
|
rescue InternalError
|
266
285
|
end
|
267
286
|
|
287
|
+
def source_file
|
288
|
+
File.join(local_dir, 'source.yml')
|
289
|
+
end
|
290
|
+
|
268
291
|
# Load the source.yml file that describes this source, and resolve the
|
269
292
|
# $BLABLA values that are in there. Use #raw_description_file to avoid
|
270
293
|
# resolving those values
|
271
294
|
def load_description_file
|
272
295
|
@source_definition = raw_description_file
|
296
|
+
load_name
|
273
297
|
|
274
298
|
# Compute the definition of constants
|
275
299
|
begin
|
@@ -342,8 +366,12 @@ module Autoproj
|
|
342
366
|
urls['HOME'] = ENV['HOME']
|
343
367
|
|
344
368
|
all_vcs = source_definition['version_control']
|
345
|
-
if all_vcs
|
346
|
-
|
369
|
+
if all_vcs
|
370
|
+
if all_vcs.kind_of?(Hash)
|
371
|
+
raise ConfigError, "wrong format for the version_control field, you forgot the '-' in front of the package names"
|
372
|
+
elsif !all_vcs.kind_of?(Array)
|
373
|
+
raise ConfigError, "wrong format for the version_control field"
|
374
|
+
end
|
347
375
|
end
|
348
376
|
|
349
377
|
vcs_spec = Hash.new
|
@@ -412,7 +440,7 @@ module Autoproj
|
|
412
440
|
Autoproj.normalize_vcs_definition(vcs_spec)
|
413
441
|
end
|
414
442
|
rescue ConfigError => e
|
415
|
-
raise ConfigError, "#{e.message} in
|
443
|
+
raise ConfigError, "#{e.message} in #{source_file}", e.backtrace
|
416
444
|
end
|
417
445
|
|
418
446
|
def each_package
|
@@ -439,8 +467,12 @@ module Autoproj
|
|
439
467
|
def load_name
|
440
468
|
end
|
441
469
|
|
470
|
+
def source_file
|
471
|
+
File.join(Autoproj.config_dir, "overrides.yml")
|
472
|
+
end
|
473
|
+
|
442
474
|
def raw_description_file
|
443
|
-
path =
|
475
|
+
path = source_file
|
444
476
|
if File.file?(path)
|
445
477
|
begin
|
446
478
|
data = YAML.load(File.read(path)) || Hash.new
|
@@ -458,7 +490,7 @@ module Autoproj
|
|
458
490
|
PackageDefinition = Struct.new :autobuild, :user_block, :package_set, :file
|
459
491
|
|
460
492
|
class Manifest
|
461
|
-
FakePackage = Struct.new :text_name, :name, :srcdir, :importer
|
493
|
+
FakePackage = Struct.new :text_name, :name, :srcdir, :importer, :updated
|
462
494
|
class FakePackage
|
463
495
|
def autoproj_name; name end
|
464
496
|
def import
|
@@ -503,6 +535,10 @@ module Autoproj
|
|
503
535
|
|
504
536
|
attr_reader :file
|
505
537
|
|
538
|
+
def auto_update?
|
539
|
+
!!data['auto_update']
|
540
|
+
end
|
541
|
+
|
506
542
|
def initialize(file, data)
|
507
543
|
@file = file
|
508
544
|
@data = data
|
@@ -633,36 +669,26 @@ module Autoproj
|
|
633
669
|
return @sources.each(&block)
|
634
670
|
end
|
635
671
|
|
636
|
-
|
672
|
+
all_sources = []
|
673
|
+
|
674
|
+
(data['package_sets'] || []).each do |spec|
|
675
|
+
all_sources << source_from_spec(spec, load_description)
|
676
|
+
end
|
677
|
+
|
678
|
+
# Now load the local source
|
637
679
|
local = LocalSource.new
|
638
680
|
if load_description
|
639
681
|
local.load_description_file
|
640
682
|
else
|
641
683
|
local.load_name
|
642
684
|
end
|
643
|
-
if load_description
|
644
|
-
|
645
|
-
@sources = [local]
|
646
|
-
else
|
647
|
-
@sources = []
|
648
|
-
end
|
649
|
-
else
|
650
|
-
yield(local)
|
651
|
-
end
|
652
|
-
|
653
|
-
return if !data['package_sets']
|
654
|
-
|
655
|
-
data['package_sets'].each do |spec|
|
656
|
-
source = source_from_spec(spec, load_description)
|
657
|
-
if load_description
|
658
|
-
@sources << source
|
659
|
-
else
|
660
|
-
yield(source)
|
661
|
-
end
|
685
|
+
if !load_description || !local.empty?
|
686
|
+
all_sources << local
|
662
687
|
end
|
663
688
|
|
689
|
+
all_sources.each(&block)
|
664
690
|
if load_description
|
665
|
-
@sources
|
691
|
+
@sources = all_sources
|
666
692
|
end
|
667
693
|
end
|
668
694
|
|
@@ -704,6 +730,13 @@ module Autoproj
|
|
704
730
|
self
|
705
731
|
end
|
706
732
|
|
733
|
+
# Creates an autobuild package whose job is to allow the import of a
|
734
|
+
# specific repository into a given directory.
|
735
|
+
#
|
736
|
+
# +vcs+ is the VCSDefinition file describing the repository, +text_name+
|
737
|
+
# the name used when displaying the import progress, +pkg_name+ the
|
738
|
+
# internal name used to represent the package and +into+ the directory
|
739
|
+
# in which the package should be checked out.
|
707
740
|
def self.create_autobuild_package(vcs, text_name, pkg_name, into)
|
708
741
|
importer = vcs.create_autobuild_importer
|
709
742
|
return if !importer # updates have been disabled by using the 'none' type
|
@@ -716,6 +749,9 @@ module Autoproj
|
|
716
749
|
raise ConfigError, "cannot import #{name}: #{e.message}", e.backtrace
|
717
750
|
end
|
718
751
|
|
752
|
+
# Imports or updates a source (remote or otherwise).
|
753
|
+
#
|
754
|
+
# See create_autobuild_package for informations about the arguments.
|
719
755
|
def self.update_source(vcs, text_name, pkg_name, into)
|
720
756
|
fake_package = create_autobuild_package(vcs, text_name, pkg_name, into)
|
721
757
|
fake_package.import
|
@@ -724,15 +760,38 @@ module Autoproj
|
|
724
760
|
raise ConfigError, "cannot import #{name}: #{e.message}", e.backtrace
|
725
761
|
end
|
726
762
|
|
763
|
+
# Updates the main autoproj configuration
|
727
764
|
def update_yourself
|
728
765
|
Manifest.update_source(vcs, "autoproj main configuration", "autoproj_conf", Autoproj.config_dir)
|
729
766
|
end
|
730
767
|
|
768
|
+
# Updates all the remote sources in ROOT_DIR/.remotes, as well as the
|
769
|
+
# symbolic links in ROOT_DIR/autoproj/remotes
|
731
770
|
def update_remote_sources
|
732
771
|
# Iterate on the remote sources, without loading the source.yml
|
733
772
|
# file (we're not ready for that yet)
|
773
|
+
sources = []
|
734
774
|
each_remote_source(false) do |source|
|
735
|
-
Manifest.update_source(source.vcs, source.name || source.vcs.url, source.automatic_name, source.
|
775
|
+
Manifest.update_source(source.vcs, source.name || source.vcs.url, source.automatic_name, source.raw_local_dir)
|
776
|
+
sources << source
|
777
|
+
end
|
778
|
+
|
779
|
+
# Check for directories in ROOT_DIR/.remotes that do not map to a
|
780
|
+
# source repository, and remove them
|
781
|
+
Dir.glob(File.join(Autoproj.remotes_dir, '*')).each do |dir|
|
782
|
+
dir = File.expand_path(dir)
|
783
|
+
if File.directory?(dir) && !sources.any? { |s| s.raw_local_dir == dir }
|
784
|
+
FileUtils.rm_rf dir
|
785
|
+
end
|
786
|
+
end
|
787
|
+
|
788
|
+
remotes_symlinks_dir = File.join(Autoproj.config_dir, 'remotes')
|
789
|
+
FileUtils.rm_rf remotes_symlinks_dir
|
790
|
+
FileUtils.mkdir remotes_symlinks_dir
|
791
|
+
# Create symbolic links from .remotes/weird_url to
|
792
|
+
# autoproj/remotes/name
|
793
|
+
each_remote_source(false) do |source|
|
794
|
+
FileUtils.ln_sf source.raw_local_dir, File.join(remotes_symlinks_dir, source.name)
|
736
795
|
end
|
737
796
|
end
|
738
797
|
|
@@ -772,7 +831,8 @@ module Autoproj
|
|
772
831
|
# by S1
|
773
832
|
def load_importers
|
774
833
|
packages.each_value do |pkg|
|
775
|
-
vcs = importer_definition_for(pkg.autobuild.name, pkg.package_set)
|
834
|
+
vcs = importer_definition_for(pkg.autobuild.name, pkg.package_set) ||
|
835
|
+
importer_definition_for("default", pkg.package_set)
|
776
836
|
|
777
837
|
if vcs
|
778
838
|
Autoproj.add_build_system_dependency vcs.type
|
@@ -876,21 +936,6 @@ module Autoproj
|
|
876
936
|
yield
|
877
937
|
end
|
878
938
|
|
879
|
-
def handle_enabled_packages(selected_packages)
|
880
|
-
handled_packages = Set.new
|
881
|
-
each_package_set(selected_packages) do |name, packages, enabled_packages|
|
882
|
-
packages -= handled_packages
|
883
|
-
enabled_packages -= handled_packages
|
884
|
-
|
885
|
-
in_sublayout(name, packages) do
|
886
|
-
if !packages.empty?
|
887
|
-
yield(name, packages, enabled_packages)
|
888
|
-
end
|
889
|
-
end
|
890
|
-
handled_packages |= packages
|
891
|
-
end
|
892
|
-
end
|
893
|
-
|
894
939
|
def default_packages
|
895
940
|
names = if layout = data['layout']
|
896
941
|
layout_packages(layout, true)
|
@@ -925,10 +970,7 @@ module Autoproj
|
|
925
970
|
manifest = PackageManifest.load(package, manifest_path)
|
926
971
|
package_manifests[package.name] = manifest
|
927
972
|
|
928
|
-
manifest.
|
929
|
-
if Autoproj.verbose
|
930
|
-
STDERR.puts " #{package.name} depends on #{name}"
|
931
|
-
end
|
973
|
+
manifest.each_dependency do |name|
|
932
974
|
begin
|
933
975
|
package.depends_on name
|
934
976
|
rescue Autobuild::ConfigException => e
|
@@ -959,18 +1001,14 @@ module Autoproj
|
|
959
1001
|
required_os_packages = Set.new
|
960
1002
|
package_os_deps = Hash.new { |h, k| h[k] = Array.new }
|
961
1003
|
packages.each do |pkg_name|
|
962
|
-
|
963
|
-
|
964
|
-
|
965
|
-
required_os_packages << osdep_name
|
966
|
-
end
|
1004
|
+
pkg = Autobuild::Package[pkg_name]
|
1005
|
+
if !pkg
|
1006
|
+
raise InternalError, "internal error: #{pkg_name} is not a package"
|
967
1007
|
end
|
968
1008
|
|
969
|
-
|
970
|
-
|
971
|
-
|
972
|
-
required_os_packages << osdep_name
|
973
|
-
end
|
1009
|
+
pkg.os_packages.each do |osdep_name|
|
1010
|
+
package_os_deps[osdep_name] << pkg_name
|
1011
|
+
required_os_packages << osdep_name
|
974
1012
|
end
|
975
1013
|
end
|
976
1014
|
|
@@ -1020,11 +1058,12 @@ module Autoproj
|
|
1020
1058
|
if layout_name[0..-1] =~ Regexp.new("#{sel}\/?$")
|
1021
1059
|
expanded_packages.concat(packages.to_a)
|
1022
1060
|
else
|
1023
|
-
|
1024
|
-
|
1061
|
+
match = Regexp.new("^#{Regexp.quote(sel)}")
|
1062
|
+
Autobuild::Package.each(true) do |name, pkg|
|
1063
|
+
if pkg.srcdir =~ match
|
1064
|
+
expanded_packages << name
|
1065
|
+
end
|
1025
1066
|
end
|
1026
|
-
expanded_packages.concat(packages)
|
1027
|
-
!packages.empty?
|
1028
1067
|
end
|
1029
1068
|
end
|
1030
1069
|
end
|
@@ -1032,14 +1071,19 @@ module Autoproj
|
|
1032
1071
|
end
|
1033
1072
|
end
|
1034
1073
|
|
1035
|
-
# The singleton manifest object on which the current run works
|
1036
1074
|
class << self
|
1075
|
+
# The singleton manifest object on which the current run works
|
1037
1076
|
attr_accessor :manifest
|
1077
|
+
|
1078
|
+
# The operating system package definitions
|
1079
|
+
attr_accessor :osdeps
|
1038
1080
|
end
|
1039
1081
|
|
1040
1082
|
class PackageManifest
|
1041
1083
|
def self.load(package, file)
|
1042
|
-
doc = Nokogiri::XML(File.read(file))
|
1084
|
+
doc = Nokogiri::XML(File.read(file)) do |c|
|
1085
|
+
c.noblanks
|
1086
|
+
end
|
1043
1087
|
PackageManifest.new(package, doc)
|
1044
1088
|
end
|
1045
1089
|
|
@@ -1053,6 +1097,15 @@ module Autoproj
|
|
1053
1097
|
@xml = doc
|
1054
1098
|
end
|
1055
1099
|
|
1100
|
+
def each_dependency(&block)
|
1101
|
+
if block_given?
|
1102
|
+
each_os_dependency(&block)
|
1103
|
+
each_package_dependency(&block)
|
1104
|
+
else
|
1105
|
+
enum_for(:each_dependency, &block)
|
1106
|
+
end
|
1107
|
+
end
|
1108
|
+
|
1056
1109
|
def each_os_dependency
|
1057
1110
|
if block_given?
|
1058
1111
|
xml.xpath('//rosdep').each do |node|
|
data/lib/autoproj/osdeps.rb
CHANGED
@@ -2,12 +2,12 @@ require 'tempfile'
|
|
2
2
|
module Autoproj
|
3
3
|
class OSDependencies
|
4
4
|
def self.load(file)
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
5
|
+
begin
|
6
|
+
data = YAML.load(File.read(file))
|
7
|
+
verify_definitions(data)
|
8
|
+
rescue ArgumentError => e
|
9
|
+
raise ConfigError, "error in #{file}: #{e.message}"
|
10
|
+
end
|
11
11
|
|
12
12
|
OSDependencies.new(data)
|
13
13
|
end
|
@@ -47,6 +47,23 @@ module Autoproj
|
|
47
47
|
@definitions = definitions.merge(info.definitions)
|
48
48
|
end
|
49
49
|
|
50
|
+
def self.verify_definitions(hash = nil)
|
51
|
+
hash ||= definitions
|
52
|
+
hash.each do |key, value|
|
53
|
+
if !key.kind_of?(String)
|
54
|
+
raise ArgumentError, "invalid osdeps definition: found an #{key.class}. Don't forget to put quotes around numbers"
|
55
|
+
end
|
56
|
+
next if !value
|
57
|
+
if value.kind_of?(Array) || value.kind_of?(Hash)
|
58
|
+
verify_definitions(value)
|
59
|
+
else
|
60
|
+
if !value.kind_of?(String)
|
61
|
+
raise ArgumentError, "invalid osdeps definition: found an #{value.class}. Don't forget to put quotes around numbers"
|
62
|
+
end
|
63
|
+
end
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
50
67
|
def operating_system
|
51
68
|
if @operating_system
|
52
69
|
return @operating_system
|
@@ -144,7 +161,9 @@ module Autoproj
|
|
144
161
|
version_entry = data.find do |version_list, data|
|
145
162
|
version_list.to_s.split(',').
|
146
163
|
map(&:downcase).
|
147
|
-
any?
|
164
|
+
any? do |v|
|
165
|
+
os_version.any? { |osv| Regexp.new(v) =~ osv }
|
166
|
+
end
|
148
167
|
end
|
149
168
|
|
150
169
|
if !version_entry
|
@@ -168,8 +187,24 @@ module Autoproj
|
|
168
187
|
"\n" + shell_snippets
|
169
188
|
end
|
170
189
|
|
190
|
+
# Returns true if there is an operating-system package with that name,
|
191
|
+
# and false otherwise
|
192
|
+
def has?(name)
|
193
|
+
partition_packages([name].to_set)
|
194
|
+
true
|
195
|
+
rescue ConfigError
|
196
|
+
false
|
197
|
+
end
|
198
|
+
|
171
199
|
# call-seq:
|
172
200
|
# partition_packages(package_names) => os_packages, gem_packages
|
201
|
+
#
|
202
|
+
# Resolves the package names listed in +package_set+, and returns a set
|
203
|
+
# of packages that have to be installed using the platform's native
|
204
|
+
# package manager, and the set of packages that have to be installed
|
205
|
+
# using Ruby's package manager, RubyGems.
|
206
|
+
#
|
207
|
+
# Raises ConfigError if no package can be found
|
173
208
|
def partition_packages(package_set, package_osdeps = Hash.new)
|
174
209
|
package_set = package_set.
|
175
210
|
map { |name| OSDependencies.aliases[name] || name }.
|