syncwrap 2.6.2 → 2.7.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.
Files changed (67) hide show
  1. checksums.yaml +4 -4
  2. data/History.rdoc +44 -0
  3. data/Manifest.txt +2 -0
  4. data/README.rdoc +3 -3
  5. data/bin/syncwrap +1 -1
  6. data/lib/syncwrap/amazon_ec2.rb +1 -1
  7. data/lib/syncwrap/amazon_ws.rb +51 -17
  8. data/lib/syncwrap/base.rb +2 -2
  9. data/lib/syncwrap/cli.rb +1 -1
  10. data/lib/syncwrap/component.rb +6 -1
  11. data/lib/syncwrap/components/amazon_linux.rb +1 -1
  12. data/lib/syncwrap/components/arch.rb +48 -5
  13. data/lib/syncwrap/components/bundle.rb +1 -1
  14. data/lib/syncwrap/components/bundled_iyyov_daemon.rb +1 -1
  15. data/lib/syncwrap/components/bundler_gem.rb +1 -1
  16. data/lib/syncwrap/components/centos.rb +1 -1
  17. data/lib/syncwrap/components/commercial_jdk.rb +2 -1
  18. data/lib/syncwrap/components/cruby_vm.rb +15 -11
  19. data/lib/syncwrap/components/debian.rb +46 -10
  20. data/lib/syncwrap/components/etc_hosts.rb +1 -1
  21. data/lib/syncwrap/components/geminabox.rb +1 -1
  22. data/lib/syncwrap/components/hashdot.rb +2 -2
  23. data/lib/syncwrap/components/iyyov.rb +1 -1
  24. data/lib/syncwrap/components/iyyov_daemon.rb +1 -1
  25. data/lib/syncwrap/components/jruby_vm.rb +13 -7
  26. data/lib/syncwrap/components/lvm_cache.rb +1 -1
  27. data/lib/syncwrap/components/mdraid.rb +1 -1
  28. data/lib/syncwrap/components/network.rb +1 -1
  29. data/lib/syncwrap/components/open_jdk.rb +1 -1
  30. data/lib/syncwrap/components/postgresql.rb +24 -4
  31. data/lib/syncwrap/components/puma.rb +1 -1
  32. data/lib/syncwrap/components/qpid.rb +1 -1
  33. data/lib/syncwrap/components/rake_gem.rb +1 -1
  34. data/lib/syncwrap/components/rhel.rb +38 -17
  35. data/lib/syncwrap/components/run_user.rb +1 -1
  36. data/lib/syncwrap/components/source_tree.rb +1 -1
  37. data/lib/syncwrap/components/tarpit_gem.rb +1 -1
  38. data/lib/syncwrap/components/ubuntu.rb +1 -1
  39. data/lib/syncwrap/components/users.rb +10 -1
  40. data/lib/syncwrap/context.rb +11 -1
  41. data/lib/syncwrap/distro.rb +10 -5
  42. data/lib/syncwrap/formatter.rb +1 -1
  43. data/lib/syncwrap/git_help.rb +1 -1
  44. data/lib/syncwrap/hash_support.rb +1 -1
  45. data/lib/syncwrap/host.rb +1 -1
  46. data/lib/syncwrap/main.rb +1 -1
  47. data/lib/syncwrap/path_util.rb +1 -1
  48. data/lib/syncwrap/rsync.rb +8 -17
  49. data/lib/syncwrap/ruby_support.rb +1 -1
  50. data/lib/syncwrap/shell.rb +1 -1
  51. data/lib/syncwrap/systemd.rb +1 -1
  52. data/lib/syncwrap/user_data.rb +1 -1
  53. data/lib/syncwrap/version_support.rb +1 -1
  54. data/lib/syncwrap/zone_balancer.rb +65 -0
  55. data/lib/syncwrap.rb +19 -6
  56. data/sync/postgresql/postgresql.conf.erb +27 -5
  57. data/test/setup.rb +1 -1
  58. data/test/test_components.rb +3 -1
  59. data/test/test_context.rb +1 -1
  60. data/test/test_context_rput.rb +1 -1
  61. data/test/test_rsync.rb +1 -1
  62. data/test/test_shell.rb +1 -1
  63. data/test/test_space.rb +1 -1
  64. data/test/test_space_main.rb +9 -2
  65. data/test/test_version_support.rb +1 -1
  66. data/test/test_zone_balancer.rb +48 -0
  67. metadata +4 -2
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: e77f5ce5aa53289eeb185d2eae6cc57f1409c80b
4
- data.tar.gz: 1b4f72235707a1e8c57cacf696c50011f2482b2f
3
+ metadata.gz: d848cc57d0687947e9b350e86f3b581088572c42
4
+ data.tar.gz: fbbf0ae54fe44d9e14162f7e2ebef65c070fd065
5
5
  SHA512:
6
- metadata.gz: 97bde28072609b93f183ea46f154fc92e8a0affa9ba9c373acd341eb48e70d02d11f3c288105c6efd9034708f0388053c22918c10b3a1f8f57d55ea91fd6c40e
7
- data.tar.gz: 490597d2d2564ed30fb028d67e39650d7d13cc6d6f325443ddf8143a8ec08b998af2d446b205c6e4534a700f61fb2fde6873a986f898fa1ca015fe436c58948c
6
+ metadata.gz: d5647f57c02531435bced8dcb1373976fadaa162859bb7cf1c3e2bcc683dcb9b672b0ce6a6d4380712b93e68bf2be07257bd5fe5ac519e4beccec9de6593325a
7
+ data.tar.gz: 2914e8ec77e1c763c6c164a1b7df19bfc27a7c8ac536b1c207f4703dda71e40013bf3f5265e35fc25939920cfc98c4b6209654343cb01b807f68ac0677a09184
data/History.rdoc CHANGED
@@ -1,3 +1,47 @@
1
+ === 2.7.0 (2016-1-21)
2
+ * Add SyncWrap::ZoneBalancer utility for balancing new hosts across
3
+ multiple (AWS) availability zones for fault tolerance.
4
+ * Update SyncWrap::PostgreSQL for support of version 9.5. Changes,
5
+ including postgresql.conf updates, remain backward compatible with
6
+ 9.1+ and SyncWrap 2.3.0+
7
+ * Add a check_install option to Distro#dist_install for all
8
+ distros. This adds bash conditionals to check for the presence of
9
+ system packages before invoking the package manager install/update
10
+ commands. If already installed, this can greatly improve
11
+ provisioning speed and will not perform updates which might be
12
+ better left to when provisioning new hosts. The option is off by
13
+ default for now, but is used for some more complete component
14
+ dependencies (see below). To enable it globally,
15
+ add `options( check_install: true )` to your sync.rb file.
16
+ * Make SyncWrap::RHEL#dist_uninstall :succeed (don't fail even if no
17
+ packages are present) the default. This option is now deprecated on
18
+ dist_uninstall.
19
+ * Use `apt-get remove`, instead of aptitude on Debian and Ubuntu.
20
+ * Since Debian's `apt-get remove` and Arch's `pacman -R` fail if any
21
+ specified package is not found, test if each package is installed
22
+ before removing it. The leniency of dist_uninstall is now consistent
23
+ across all distros.
24
+ * Some minimal distros like Debian 8 might not include rsync in a base
25
+ image. Add a conditional dist_install of rsync to the
26
+ SyncWrap::Users component before attempting to rput user home
27
+ dirs. A distro component needs to be included before Users for
28
+ this to occur. Backward compatibility is maintained when this is not
29
+ the case.
30
+ * Some minimal distro base images might not include curl. Add
31
+ dist_install of curl to components that use it, either as part of
32
+ build dependencies, or separately using the new check_install
33
+ feature (see above) to minimize performance impact.
34
+ * Add preliminary support for non-default or multiple VPCs, or mixed
35
+ EC2-VPC and EC2-Classic deployments via the vpc and subnet_id
36
+ profile properties with the SyncWrap::AmazonEC2 provider.
37
+ * Add workaround for crash on jruby 9.0.0-4 with (wrapped) sync file
38
+ load (See jruby#3180 and #3609). Tests show wrapped load working
39
+ correctly on jruby 1.7.24 and 9.0.5 snapshots.
40
+ * Upgrade SyncWrap::JRubyVM default version to 1.7.23 (+ hash for 1.7.24)
41
+ * Upgrade SyncWrap::CRubyVM default version to 2.1.8
42
+ * Fix tmpdir access issue with rput with templates to localhost and
43
+ alt non-root :user option.
44
+
1
45
  === 2.6.2 (2015-12-3)
2
46
  * By way of comparability to RHEL 7, SyncWrap::AmazonLinux with a
3
47
  specified amazon_version property >= '2014.03' would incorrectly
data/Manifest.txt CHANGED
@@ -34,6 +34,7 @@ lib/syncwrap/shell.rb
34
34
  lib/syncwrap/systemd.rb
35
35
  lib/syncwrap/user_data.rb
36
36
  lib/syncwrap/version_support.rb
37
+ lib/syncwrap/zone_balancer.rb
37
38
  lib/syncwrap/components/amazon_linux.rb
38
39
  lib/syncwrap/components/arch.rb
39
40
  lib/syncwrap/components/bundle.rb
@@ -101,6 +102,7 @@ test/test_shell.rb
101
102
  test/test_space.rb
102
103
  test/test_space_main.rb
103
104
  test/test_version_support.rb
105
+ test/test_zone_balancer.rb
104
106
  test/zfile
105
107
  test/sync/d1/bar
106
108
  test/sync/d1/foo.erb
data/README.rdoc CHANGED
@@ -36,8 +36,8 @@ command queue, and a few powerful methods like rput (augmented rsync).
36
36
  * Independent of (but easily integrated into) rake
37
37
 
38
38
  * Depends only on ruby 1.9+ stdlib Open3 for interaction with bash,
39
- ssh and rsync. Actually, really works on jruby 1.6.8 (--1.9 mode)
40
- and 1.7+
39
+ ssh and rsync. Also works on jruby 1.7.x, 9.x and recent rubinuous
40
+ (see Travis CI variants).
41
41
 
42
42
  == Synopsis
43
43
 
@@ -139,7 +139,7 @@ yourself.
139
139
 
140
140
  == License
141
141
 
142
- Copyright (c) 2011-2015 David Kellum
142
+ Copyright (c) 2011-2016 David Kellum
143
143
 
144
144
  Licensed under the Apache License, Version 2.0 (the "License"); you
145
145
  may not use this file except in compliance with the License. You
data/bin/syncwrap CHANGED
@@ -2,7 +2,7 @@
2
2
  # -*- ruby -*-
3
3
 
4
4
  #--
5
- # Copyright (c) 2011-2015 David Kellum
5
+ # Copyright (c) 2011-2016 David Kellum
6
6
  #
7
7
  # Licensed under the Apache License, Version 2.0 (the "License"); you
8
8
  # may not use this file except in compliance with the License. You
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -59,43 +59,75 @@ module SyncWrap
59
59
  symbolize_names: true ) )
60
60
  end
61
61
 
62
- # Create a security_group given name and options. :region is the
63
- # only required option, :description is good to have. Currently
64
- # this is a no-op if the security group already exists.
62
+ # Create a security_group given name and options. Currently this
63
+ # is a no-op if the security group of the given name already
64
+ # exists (in the given or default VPC or without,
65
+ # e.g. EC2-Classic). In either case the associated SecurityGroup
66
+ # object is returned.
67
+ #
68
+ # === Options
69
+ #
70
+ # See
71
+ # {AWS::EC2::SecurityGroupCollection.create}[http://docs.aws.amazon.com/AWSRubySDK/latest/AWS/EC2/SecurityGroupCollection.html#create-instance_method]
72
+ # with the following additions/differences:
73
+ #
74
+ # :region:: Required
75
+ #
76
+ # :vpc:: The VPC ID in which to create the group. Required if host
77
+ # is to be launched in a subnet of a non-default VPC.
78
+ #
79
+ # :description:: Optional text description. Set to name if unspecified.
65
80
  def aws_create_security_group( name, opts = {} )
66
81
  opts = opts.dup
67
82
  region = opts.delete( :region )
83
+ vpc = opts[ :vpc ]
68
84
  ec2 = AWS::EC2.new.regions[ region ]
69
- unless ec2.security_groups.find { |sg| sg.name == name }
70
- sg = ec2.security_groups.create( name, opts )
71
85
 
72
- # FIXME: Allow ssh on the "default" region named group
86
+ sg = ec2.security_groups.find do |sg|
87
+ sg.name == name && ( vpc.nil? || sg.vpc_id == vpc )
88
+ end
89
+ unless sg
90
+ sg = ec2.security_groups.create( name, opts )
91
+ # Allow ssh on the special "default" region named group
73
92
  if name == region
74
93
  sg.authorize_ingress(:tcp, 22)
75
94
  end
76
95
  end
96
+ sg
77
97
  end
78
98
 
79
99
  # Create an instance, using name as the Name tag and assumed
80
- # host name. For options see
100
+ # host name.
101
+ #
102
+ # === Options
103
+ #
104
+ # See
81
105
  # {AWS::EC2::InstanceCollection.create}[http://docs.aws.amazon.com/AWSRubySDK/latest/AWS/EC2/InstanceCollection.html#create-instance_method]
82
106
  # with the following additions/differences:
83
107
  #
84
108
  # :count:: must be 1 or unspecified.
109
+ #
85
110
  # :region:: Default 'us-east-1'
86
- # :security_groups:: As per aws-sdk, but the special :default value
87
- # is replaced with a single security group with
88
- # same name as the :region.
89
- # :ebs_volumes:: The number of EBS volumes to create and attach to this instance.
111
+ #
112
+ # :security_groups:: Array of Security Group names. The special
113
+ # :default value is replaced with a single
114
+ # security group with same name as the :region.
115
+ #
116
+ # :ebs_volumes:: The number of EBS volumes to create and attach to
117
+ # this instance.
118
+ #
90
119
  # :ebs_volume_options:: A nested Hash of options, as per
91
120
  # {AWS::EC2::VolumeCollection.create}[http://docs.aws.amazon.com/AWSRubySDK/latest/AWS/EC2/VolumeCollection.html#create-instance_method]
92
121
  # with custom default :size 16 GB, and the same
93
122
  # :availibility_zone as the instance.
123
+ #
94
124
  # :ebs_mounts:: Device mounting scheme. The value :sdf_p indicates
95
125
  # "/dev/sd[f-p]", and should be used for HVM instances.
96
126
  # The default scheme is currently :sdh1_6 "/dev/sdh[1-6]".
97
127
  # See {EC2: Block Device Mapping}[http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/block-device-mapping-concepts.html]
128
+ #
98
129
  # :lvm_volumes:: Ignored here.
130
+ #
99
131
  # :roles:: Array of role Strings or Symbols (applied as Roles tag)
100
132
  def aws_create_instance( name, opts = {} )
101
133
  opts = deep_merge_hashes( @default_instance_options, opts )
@@ -111,18 +143,20 @@ module SyncWrap
111
143
  iopts.delete( :roles ) #-> tags
112
144
  iopts.delete( :description ) #-> tags
113
145
  iopts.delete( :tag ) #-> tags
146
+ iopts.delete( :vpc )
114
147
 
115
148
  if iopts[ :count ] && iopts[ :count ] != 1
116
149
  raise ":count #{iopts[ :count ]} != 1 is not supported"
117
150
  end
118
151
 
119
- iopts[ :security_groups ].map! do |sg|
120
- sg == :default ? region : sg
152
+ iopts[ :security_groups ].map! do |gname|
153
+ gname = region if gname == :default
154
+ aws_create_security_group( gname,
155
+ region: region, vpc: opts[ :vpc ] )
121
156
  end
122
157
 
123
- iopts[ :security_groups ].each do |sg|
124
- aws_create_security_group( sg, region: region )
125
- end
158
+ az = iopts[ :availability_zone ]
159
+ iopts[ :availability_zone ] = az.call if az.is_a?( Proc )
126
160
 
127
161
  inst = ec2.instances.create( iopts )
128
162
 
data/lib/syncwrap/base.rb CHANGED
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -15,7 +15,7 @@
15
15
  #++
16
16
 
17
17
  module SyncWrap
18
- VERSION='2.6.2'
18
+ VERSION='2.7.0'
19
19
 
20
20
  GEM_ROOT = File.dirname(File.dirname(File.dirname(__FILE__))) # :nodoc:
21
21
  end
data/lib/syncwrap/cli.rb CHANGED
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You
@@ -233,6 +233,11 @@ module SyncWrap
233
233
  ctx.verbose?
234
234
  end
235
235
 
236
+ # Return any value of :check_install set in default options.
237
+ def check_install?
238
+ ctx.check_install?
239
+ end
240
+
236
241
  # Return the path to the the specified src, as first found in the
237
242
  # :sync_paths option as per #rput, Source Resolution. Return nil
238
243
  # if not found. This allows optional, local behavior based on the
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -29,17 +29,60 @@ module SyncWrap
29
29
  true
30
30
  end
31
31
 
32
+ # Install the specified package names. A trailing hash is
33
+ # interpreted as options, see below.
34
+ #
35
+ # ==== Options
36
+ #
37
+ # :check_install:: Short-circuit if all packages already
38
+ # installed. Thus no upgrades will be performed.
39
+ #
40
+ # Additional options are passed to the sudo calls.
32
41
  def dist_install( *pkgs )
33
- opts = pkgs.last.is_a?( Hash ) && pkgs.pop || {}
34
- sudo "pacman -S --noconfirm #{pkgs.join ' '}"
42
+ opts = pkgs.last.is_a?( Hash ) && pkgs.pop.dup || {}
43
+ opts.delete( :minimal )
44
+ pkgs.flatten!
45
+ chk = opts.delete( :check_install ) || opts.delete( :succeed )
46
+ chk = check_install? if chk.nil?
47
+ dist_if_not_installed?( pkgs, chk, opts ) do
48
+ sudo( "pacman -S --noconfirm #{pkgs.join ' '}", opts )
49
+ end
35
50
  end
36
51
 
52
+ # Uninstall the specified package names. A trailing hash is
53
+ # interpreted as options, passed to the sudo calls.
37
54
  def dist_uninstall( *pkgs )
38
- opts = pkgs.last.is_a?( Hash ) && pkgs.pop || {}
39
- sudo "pacman -R --noconfirm #{pkgs.join ' '}"
55
+ opts = pkgs.last.is_a?( Hash ) && pkgs.pop.dup || {}
56
+ opts.delete( :succeed )
57
+ pkgs.flatten!
58
+ pkgs.each do |pkg|
59
+ dist_if_installed?( pkg, opts ) do
60
+ sudo( "pacman -R --noconfirm #{pkg}", opts )
61
+ end
62
+ end
63
+ end
64
+
65
+ # If chk is true, then wrap block in a sudo bash conditional
66
+ # testing if any specified pkgs are not installed. Otherwise just
67
+ # yield to block.
68
+ def dist_if_not_installed?( pkgs, chk, opts, &block )
69
+ if chk
70
+ c = "if ! pacman -Q #{pkgs.join ' '} >/dev/null 2>&1; then"
71
+ sudo( c, opts.merge( close: 'fi' ), &block )
72
+ else
73
+ block.call
74
+ end
75
+ end
76
+
77
+ # Wrap block in a sudo bash conditional testing if the single
78
+ # specified pkg is installed. Otherwise just yield to block.
79
+ def dist_if_installed?( pkg, opts, &block )
80
+ c = "if pacman -Q #{pkg} >/dev/null 2>&1; then"
81
+ sudo( c, opts.merge( close: 'fi' ), &block )
40
82
  end
41
83
 
42
84
  alias_method :dist_service, :dist_service_via_systemctl
85
+
43
86
  end
44
87
 
45
88
  end
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -71,6 +71,7 @@ module SyncWrap
71
71
  join( ' ' )
72
72
 
73
73
  sudo( "if [ ! -d #{jdk_dir} ]; then", close: "fi" ) do
74
+ dist_install( 'curl', minimal: true, check_install: true )
74
75
  sudo <<-SH
75
76
  curl -sSL -o #{distro} #{jdk_url}
76
77
  SH
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -46,19 +46,23 @@ module SyncWrap
46
46
  include RubySupport
47
47
  include HashSupport
48
48
 
49
- # Default version of #ruby_version to install
50
- DEFAULT_VERSION = '2.1.7'
49
+ # Default #ruby_version to install
50
+ DEFAULT_VERSION = '2.1.8'
51
51
 
52
- # SHA256 #hash for DEFAULT_VERSION
53
- DEFAULT_VERSION_HASH =
54
- 'f59c1596ac39cc7e60126e7d3698c19f482f04060674fdfe0124e1752ba6dd81'
52
+ # A set of known (sha256) cryptographic hashes, keyed by version
53
+ # string.
54
+ KNOWN_HASHES = {
55
+ '2.1.7' =>
56
+ 'f59c1596ac39cc7e60126e7d3698c19f482f04060674fdfe0124e1752ba6dd81',
57
+ '2.1.8' =>
58
+ 'afd832b8d5ecb2e3e1477ec6a9408fdf9898ee73e4c5df17a2b2cb36bd1c355d' }
55
59
 
56
60
  # The ruby version to install, as it appears in source packages
57
61
  # from ruby-lang.org. Note that starting with 2.1.0, the patch
58
62
  # release (p#) no longer appears in package names.
59
63
  # (Default: DEFAULT_VERSION)
60
64
  #
61
- # Example values: '2.0.0-p481', '2.1.7'
65
+ # Example values: '2.0.0-p481', '2.1.8'
62
66
  attr_accessor :ruby_version
63
67
 
64
68
  # If true, attempt to uninstall any pre-existing distro packaged
@@ -68,6 +72,7 @@ module SyncWrap
68
72
 
69
73
  # A cryptographic hash value (hexadecimal, some standard length)
70
74
  # to use for verifying the 'source.tar.gz' package.
75
+ # (Default: KNOWN_HASHES[ ruby_version ])
71
76
  attr_writer :hash
72
77
 
73
78
  def initialize( opts = {} )
@@ -78,7 +83,7 @@ module SyncWrap
78
83
  end
79
84
 
80
85
  def hash
81
- @hash || ( ruby_version == DEFAULT_VERSION && DEFAULT_VERSION_HASH )
86
+ @hash || KNOWN_HASHES[ ruby_version ]
82
87
  end
83
88
 
84
89
  def install
@@ -110,11 +115,10 @@ module SyncWrap
110
115
 
111
116
  def uninstall_distro_ruby
112
117
  if distro.is_a?( RHEL )
113
- dist_uninstall( %w[ ruby ruby18 ruby19 ruby20 ruby21 ruby22 ],
114
- succeed: true )
118
+ dist_uninstall( %w[ ruby ruby18 ruby19 ruby20 ruby21 ruby22 ruby23 ] )
115
119
  else
116
120
  dist_uninstall( %w[ ruby ruby1.8 ruby1.9 ruby1.9.1
117
- ruby1.9.3 ruby2.0 ruby2.1 ruby2.2 ] )
121
+ ruby1.9.3 ruby2.0 ruby2.1 ruby2.2 ruby2.3 ] )
118
122
  end
119
123
  end
120
124
 
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -54,22 +54,58 @@ module SyncWrap
54
54
  # well. A trailing hash is interpreted as options, see below.
55
55
  #
56
56
  # ==== Options
57
+ #
58
+ # :check_install:: Short-circuit if all packages already
59
+ # installed. Thus no upgrades will be performed.
60
+ #
57
61
  # :minimal:: Eqv to --no-install-recommends
58
62
  #
59
- # Other options will be ignored.
63
+ # Additional options are passed to the sudo calls.
60
64
  def dist_install( *args )
61
- opts = args.last.is_a?( Hash ) && args.pop || {}
62
- args.unshift "--no-install-recommends" if opts[ :minimal ]
63
-
64
- sudo( "apt-get -yqq update" ) if first_apt?
65
- sudo( "apt-get -yq install #{args.join ' '}" )
65
+ opts = args.last.is_a?( Hash ) && args.pop.dup || {}
66
+ args.flatten!
67
+ flags = []
68
+ flags << '--no-install-recommends' if opts.delete( :minimal )
69
+ chk = opts.delete( :check_install ) || opts.delete( :succeed )
70
+ chk = check_install? if chk.nil?
71
+ dist_if_not_installed?( args, chk, opts ) do
72
+ sudo( "apt-get -yqq update", opts ) if first_apt?
73
+ sudo( "apt-get -yq install #{(flags + args).join ' '}", opts )
74
+ end
66
75
  end
67
76
 
68
77
  # Uninstall the specified package names. A trailing hash is
69
- # interpreted as options.
78
+ # interpreted as options, passed to the sudo calls.
70
79
  def dist_uninstall( *pkgs )
71
- opts = pkgs.last.is_a?( Hash ) && pkgs.pop || {}
72
- sudo "aptitude -yq purge #{pkgs.join ' '}"
80
+ opts = pkgs.last.is_a?( Hash ) && pkgs.pop.dup || {}
81
+ opts.delete( :succeed )
82
+ pkgs.flatten!
83
+ pkgs.each do |pkg|
84
+ dist_if_installed?( pkg, opts ) do
85
+ sudo( "apt-get -yq --purge remove #{pkg}", opts )
86
+ end
87
+ end
88
+ end
89
+
90
+ # If chk is true, then wrap block in a sudo bash conditional
91
+ # testing if any specified pkgs are not installed. Otherwise just
92
+ # yield to block.
93
+ def dist_if_not_installed?( pkgs, chk, opts, &block )
94
+ if chk
95
+ qry = "dpkg-query -W -f '${db:Status-Status}\\n' #{pkgs.join ' '}"
96
+ cnt = qry + " | grep -c -E '^installed$'"
97
+ cond = %Q{if [ "$(#{cnt})" != "#{pkgs.count}" ]; then}
98
+ sudo( cond, opts.merge( close: 'fi' ), &block )
99
+ else
100
+ block.call
101
+ end
102
+ end
103
+
104
+ def dist_if_installed?( pkg, opts, &block )
105
+ qry = "dpkg-query -W -f '${db:Status-Status}\\n' #{pkg}"
106
+ tst = qry + " | grep -q 'installed'"
107
+ cond = "if #{tst}; then"
108
+ sudo( cond, opts.merge( close: 'fi' ), &block )
73
109
  end
74
110
 
75
111
  # Install a System V style init.d service script
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -30,7 +30,7 @@ module SyncWrap
30
30
  class Hashdot < Component
31
31
  include HashSupport
32
32
 
33
- # Default version of #hashdot_version to install
33
+ # Default #hashdot_version to install
34
34
  DEFAULT_VERSION = '1.4.0'
35
35
 
36
36
  # SHA256 #hash for DEFAULT_VERSION
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -1,5 +1,5 @@
1
1
  #--
2
- # Copyright (c) 2011-2015 David Kellum
2
+ # Copyright (c) 2011-2016 David Kellum
3
3
  #
4
4
  # Licensed under the Apache License, Version 2.0 (the "License"); you
5
5
  # may not use this file except in compliance with the License. You may
@@ -31,18 +31,22 @@ module SyncWrap
31
31
  include RubySupport
32
32
  include HashSupport
33
33
 
34
- # Default version of #jruby_version to install
35
- DEFAULT_VERSION = '1.7.22'
34
+ # Default #jruby_version to install
35
+ DEFAULT_VERSION = '1.7.23'
36
36
 
37
- # The #hash for DEFAULT_VERSION. Prefer sha256 but sha1 is what is
38
- # currently published.
39
- DEFAULT_VERSION_HASH = '6b9e310a04ad8173d0d6dbe299da04c0ef85fc15'
37
+ # A set of known cryptographic hashes, keyed by version
38
+ # string. Note, we prefer sha256 but sha1 is what is currently
39
+ # published.
40
+ KNOWN_HASHES = { '1.7.22' => '6b9e310a04ad8173d0d6dbe299da04c0ef85fc15',
41
+ '1.7.23' => '2b5e796feeed2bcfab02f8bf2ff3d77ca318e310',
42
+ '1.7.24' => '0c321d2192768dfec419bee6b44c7190f4db32e1' }
40
43
 
41
44
  # JRuby version to install (default: DEFAULT_VERSION)
42
45
  attr_accessor :jruby_version
43
46
 
44
47
  # A cryptographic hash value (hexadecimal, some standard length)
45
48
  # to use for verifying the 'jruby-bin-*.tar.gz' package.
49
+ # (Default: KNOWN_HASHES[ jruby_version ])
46
50
  attr_writer :hash
47
51
 
48
52
  def initialize( opts = {} )
@@ -53,7 +57,7 @@ module SyncWrap
53
57
  end
54
58
 
55
59
  def hash
56
- @hash || ( jruby_version == DEFAULT_VERSION && DEFAULT_VERSION_HASH )
60
+ @hash || KNOWN_HASHES[ jruby_version ]
57
61
  end
58
62
 
59
63
  def jruby_dist_path
@@ -86,6 +90,8 @@ module SyncWrap
86
90
  root = "#{local_root}/lib/jruby"
87
91
  distro = "/tmp/jruby-bin-#{jruby_version}.tar.gz"
88
92
 
93
+ dist_install( 'curl', minimal: true, check_install: true )
94
+
89
95
  sudo <<-SH
90
96
  if [ ! -d #{jruby_dist_path} ]; then
91
97
  mkdir -p #{root}