packaging 0.99.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.
- checksums.yaml +7 -0
- data/LICENSE +17 -0
- data/README-Solaris.md +117 -0
- data/README.md +1031 -0
- data/lib/packaging.rb +32 -0
- data/lib/packaging/artifactory.rb +278 -0
- data/lib/packaging/config.rb +392 -0
- data/lib/packaging/config/params.rb +366 -0
- data/lib/packaging/deb.rb +28 -0
- data/lib/packaging/deb/repo.rb +263 -0
- data/lib/packaging/gem.rb +112 -0
- data/lib/packaging/ips.rb +57 -0
- data/lib/packaging/msi.rb +89 -0
- data/lib/packaging/nuget.rb +39 -0
- data/lib/packaging/osx.rb +36 -0
- data/lib/packaging/paths.rb +238 -0
- data/lib/packaging/platforms.rb +480 -0
- data/lib/packaging/repo.rb +55 -0
- data/lib/packaging/retrieve.rb +46 -0
- data/lib/packaging/rpm.rb +5 -0
- data/lib/packaging/rpm/repo.rb +257 -0
- data/lib/packaging/tar.rb +154 -0
- data/lib/packaging/util.rb +146 -0
- data/lib/packaging/util/date.rb +15 -0
- data/lib/packaging/util/execution.rb +85 -0
- data/lib/packaging/util/file.rb +125 -0
- data/lib/packaging/util/git.rb +174 -0
- data/lib/packaging/util/git_tags.rb +73 -0
- data/lib/packaging/util/gpg.rb +62 -0
- data/lib/packaging/util/jenkins.rb +95 -0
- data/lib/packaging/util/misc.rb +69 -0
- data/lib/packaging/util/net.rb +368 -0
- data/lib/packaging/util/os.rb +17 -0
- data/lib/packaging/util/platform.rb +40 -0
- data/lib/packaging/util/rake_utils.rb +111 -0
- data/lib/packaging/util/serialization.rb +19 -0
- data/lib/packaging/util/ship.rb +171 -0
- data/lib/packaging/util/tool.rb +41 -0
- data/lib/packaging/util/version.rb +326 -0
- data/spec/fixtures/config/ext/build_defaults.yaml +2 -0
- data/spec/fixtures/config/ext/project_data.yaml +2 -0
- data/spec/fixtures/config/params.yaml +2 -0
- data/spec/fixtures/configs/components/test_file.json +1 -0
- data/spec/fixtures/configs/components/test_file_2.json +0 -0
- data/spec/fixtures/configs/components/test_file_not_tagged.json +1 -0
- data/spec/fixtures/configs/components/test_file_wrong_ext.txt +0 -0
- data/spec/fixtures/configs/components/test_file_wrong_ext.wrong +0 -0
- data/spec/fixtures/util/pre_tasks.yaml +4 -0
- data/spec/lib/packaging/artifactory_spec.rb +171 -0
- data/spec/lib/packaging/config_spec.rb +556 -0
- data/spec/lib/packaging/deb/repo_spec.rb +148 -0
- data/spec/lib/packaging/deb_spec.rb +52 -0
- data/spec/lib/packaging/paths_spec.rb +153 -0
- data/spec/lib/packaging/platforms_spec.rb +153 -0
- data/spec/lib/packaging/repo_spec.rb +97 -0
- data/spec/lib/packaging/retrieve_spec.rb +61 -0
- data/spec/lib/packaging/rpm/repo_spec.rb +133 -0
- data/spec/lib/packaging/tar_spec.rb +122 -0
- data/spec/lib/packaging/util/execution_spec.rb +56 -0
- data/spec/lib/packaging/util/file_spec.rb +139 -0
- data/spec/lib/packaging/util/git_spec.rb +160 -0
- data/spec/lib/packaging/util/git_tag_spec.rb +36 -0
- data/spec/lib/packaging/util/gpg_spec.rb +64 -0
- data/spec/lib/packaging/util/jenkins_spec.rb +112 -0
- data/spec/lib/packaging/util/misc_spec.rb +31 -0
- data/spec/lib/packaging/util/net_spec.rb +239 -0
- data/spec/lib/packaging/util/os_spec.rb +31 -0
- data/spec/lib/packaging/util/rake_utils_spec.rb +70 -0
- data/spec/lib/packaging/util/ship_spec.rb +117 -0
- data/spec/lib/packaging/util/version_spec.rb +123 -0
- data/spec/lib/packaging_spec.rb +19 -0
- data/spec/spec_helper.rb +36 -0
- data/static_artifacts/PackageInfo.plist +3 -0
- data/tasks/00_utils.rake +216 -0
- data/tasks/30_metrics.rake +33 -0
- data/tasks/apple.rake +266 -0
- data/tasks/build.rake +12 -0
- data/tasks/clean.rake +5 -0
- data/tasks/config.rake +30 -0
- data/tasks/deb.rake +129 -0
- data/tasks/deb_repos.rake +28 -0
- data/tasks/deprecated.rake +130 -0
- data/tasks/doc.rake +20 -0
- data/tasks/education.rake +57 -0
- data/tasks/fetch.rake +57 -0
- data/tasks/gem.rake +146 -0
- data/tasks/jenkins.rake +494 -0
- data/tasks/jenkins_dynamic.rake +202 -0
- data/tasks/load_extras.rake +21 -0
- data/tasks/mock.rake +348 -0
- data/tasks/nightly_repos.rake +335 -0
- data/tasks/pe_deb.rake +12 -0
- data/tasks/pe_rpm.rake +13 -0
- data/tasks/pe_ship.rake +221 -0
- data/tasks/pe_sign.rake +13 -0
- data/tasks/pe_tar.rake +5 -0
- data/tasks/retrieve.rake +45 -0
- data/tasks/rpm.rake +66 -0
- data/tasks/rpm_repos.rake +29 -0
- data/tasks/ship.rake +752 -0
- data/tasks/sign.rake +226 -0
- data/tasks/tag.rake +8 -0
- data/tasks/tar.rake +34 -0
- data/tasks/update.rake +16 -0
- data/tasks/vanagon.rake +35 -0
- data/tasks/vendor_gems.rake +117 -0
- data/tasks/version.rake +33 -0
- data/tasks/z_data_dump.rake +65 -0
- data/templates/README +1 -0
- data/templates/downstream.xml.erb +47 -0
- data/templates/msi.xml.erb +197 -0
- data/templates/packaging.xml.erb +344 -0
- data/templates/repo.xml.erb +114 -0
- metadata +234 -0
data/tasks/gem.rake
ADDED
@@ -0,0 +1,146 @@
|
|
1
|
+
if Pkg::Config.build_gem
|
2
|
+
require 'rubygems/package_task'
|
3
|
+
|
4
|
+
def glob_gem_files
|
5
|
+
gem_files = []
|
6
|
+
gem_excludes_file_list = []
|
7
|
+
gem_excludes_raw = Pkg::Config.gem_excludes.nil? ? [] : Pkg::Config.gem_excludes.split(' ')
|
8
|
+
gem_excludes_raw << 'ext/packaging'
|
9
|
+
gem_excludes_raw << 'pkg'
|
10
|
+
gem_excludes_raw.each do |exclude|
|
11
|
+
if File.directory?(exclude)
|
12
|
+
gem_excludes_file_list += FileList["#{exclude}/**/*"]
|
13
|
+
else
|
14
|
+
gem_excludes_file_list << exclude
|
15
|
+
end
|
16
|
+
end
|
17
|
+
files = FileList[Pkg::Config.gem_files.split(' ')]
|
18
|
+
files.each do |file|
|
19
|
+
if File.directory?(file)
|
20
|
+
gem_files += FileList["#{file}/**/*"]
|
21
|
+
else
|
22
|
+
gem_files << file
|
23
|
+
end
|
24
|
+
end
|
25
|
+
gem_files -= gem_excludes_file_list
|
26
|
+
end
|
27
|
+
|
28
|
+
def add_gem_dependency(opts = {})
|
29
|
+
spec = opts[:spec]
|
30
|
+
version = opts[:version]
|
31
|
+
type = opts[:type].to_s
|
32
|
+
gem = opts[:gem].to_s
|
33
|
+
if opts[:version].nil? or opts[:version].empty?
|
34
|
+
spec.send("add_#{type}_dependency".to_sym, gem)
|
35
|
+
else
|
36
|
+
spec.send("add_#{type}_dependency".to_sym, gem, version)
|
37
|
+
end
|
38
|
+
spec
|
39
|
+
end
|
40
|
+
|
41
|
+
def create_default_gem_spec
|
42
|
+
spec = Gem::Specification.new do |s|
|
43
|
+
s.name = Pkg::Config.project unless Pkg::Config.project.nil?
|
44
|
+
s.name = Pkg::Config.gem_name unless Pkg::Config.gem_name.nil?
|
45
|
+
s.version = Pkg::Config.gemversion unless Pkg::Config.gemversion.nil?
|
46
|
+
s.author = Pkg::Config.author unless Pkg::Config.author.nil?
|
47
|
+
s.email = Pkg::Config.email unless Pkg::Config.email.nil?
|
48
|
+
s.homepage = Pkg::Config.homepage unless Pkg::Config.homepage.nil?
|
49
|
+
s.summary = Pkg::Config.summary unless Pkg::Config.summary.nil?
|
50
|
+
s.summary = Pkg::Config.gem_summary unless Pkg::Config.gem_summary.nil?
|
51
|
+
s.description = Pkg::Config.description unless Pkg::Config.description.nil?
|
52
|
+
s.description = Pkg::Config.gem_description unless Pkg::Config.gem_description.nil?
|
53
|
+
s.files = glob_gem_files unless glob_gem_files.nil?
|
54
|
+
s.executables = Pkg::Config.gem_executables unless Pkg::Config.gem_executables.nil?
|
55
|
+
s.require_path = Pkg::Config.gem_require_path unless Pkg::Config.gem_require_path.nil?
|
56
|
+
s.required_ruby_version = Pkg::Config.gem_required_ruby_version unless Pkg::Config.gem_required_ruby_version.nil?
|
57
|
+
s.required_rubygems_version = Pkg::Config.gem_required_rubygems_version unless Pkg::Config.gem_required_rubygems_version.nil?
|
58
|
+
s.test_files = FileList[Pkg::Config.gem_test_files.split(' ')] unless Pkg::Config.gem_test_files.nil?
|
59
|
+
s.rubyforge_project = Pkg::Config.gem_forge_project unless Pkg::Config.gem_forge_project.nil?
|
60
|
+
Pkg::Config.gem_rdoc_options.each do |option|
|
61
|
+
s.rdoc_options << option
|
62
|
+
end unless Pkg::Config.gem_rdoc_options.nil?
|
63
|
+
end
|
64
|
+
|
65
|
+
Pkg::Config.gem_runtime_dependencies.each do |gem, version|
|
66
|
+
spec = add_gem_dependency(:spec => spec, :gem => gem, :version => version, :type => :runtime)
|
67
|
+
end unless Pkg::Config.gem_runtime_dependencies.nil?
|
68
|
+
|
69
|
+
Pkg::Config.gem_development_dependencies.each do |gem, version|
|
70
|
+
spec = add_gem_dependency(:spec => spec, :gem => gem, :version => version, :type => :development)
|
71
|
+
end unless Pkg::Config.gem_development_dependencies.nil?
|
72
|
+
spec
|
73
|
+
end
|
74
|
+
|
75
|
+
def create_gem(spec, gembuilddir)
|
76
|
+
gem_files = glob_gem_files + FileList[(Pkg::Config.gem_test_files || '').split(' ')]
|
77
|
+
workdir = File.join(Pkg::Util::File.mktemp)
|
78
|
+
|
79
|
+
bench = Benchmark.realtime do
|
80
|
+
Pkg::Util::File.install_files_into_dir(gem_files, workdir)
|
81
|
+
|
82
|
+
cd workdir do
|
83
|
+
gem_task = Gem::PackageTask.new(spec)
|
84
|
+
gem_task.define
|
85
|
+
Rake::Task[:gem].reenable
|
86
|
+
Rake::Task[:gem].invoke
|
87
|
+
rm_rf File.join("pkg", gembuilddir)
|
88
|
+
mv Dir.glob("pkg/#{Pkg::Config.gem_name}-#{Pkg::Config.gemversion}*.gem"), File.join(Pkg::Config.project_root, "pkg")
|
89
|
+
end
|
90
|
+
end
|
91
|
+
|
92
|
+
rm_rf workdir
|
93
|
+
puts "Finished building in: #{bench}"
|
94
|
+
end
|
95
|
+
|
96
|
+
def create_default_gem
|
97
|
+
spec = create_default_gem_spec
|
98
|
+
create_gem(spec, "#{Pkg::Config.gem_name}-#{Pkg::Config.gemversion}")
|
99
|
+
end
|
100
|
+
|
101
|
+
def unknown_gems_platform?(platform)
|
102
|
+
return true if platform.os == "unknown"
|
103
|
+
false
|
104
|
+
end
|
105
|
+
|
106
|
+
def create_platform_specific_gems
|
107
|
+
Pkg::Config.gem_platform_dependencies.each do |platform, dependency_hash|
|
108
|
+
spec = create_default_gem_spec
|
109
|
+
pf = Gem::Platform.new(platform)
|
110
|
+
fail "
|
111
|
+
Platform: '#{platform}' is not recognized by rubygems.
|
112
|
+
This is probably an erroneous 'gem_platform_dependencies' entry!" if unknown_gems_platform?(pf)
|
113
|
+
spec.platform = pf
|
114
|
+
dependency_hash.each do |type, gems|
|
115
|
+
t = case type
|
116
|
+
when "gem_runtime_dependencies"
|
117
|
+
"runtime"
|
118
|
+
when "gem_development_dependencies"
|
119
|
+
"development"
|
120
|
+
else
|
121
|
+
fail "Platform specific gem dependency type must be 'gem_runtime_dependencies' or 'gem_development_dependencies', not '#{type}'"
|
122
|
+
end
|
123
|
+
gems.each do |gem, version|
|
124
|
+
spec = add_gem_dependency(:spec => spec, :gem => gem, :version => version, :type => t)
|
125
|
+
end
|
126
|
+
end
|
127
|
+
create_gem(spec, "#{Pkg::Config.gem_name}-#{Pkg::Config.gemversion}-#{platform}")
|
128
|
+
end
|
129
|
+
end
|
130
|
+
|
131
|
+
namespace :package do
|
132
|
+
desc "Build a gem - All gems if platform specific"
|
133
|
+
task :gem => ["clean"] do
|
134
|
+
mkdir_p File.join(Pkg::Config.project_root, "pkg")
|
135
|
+
create_default_gem
|
136
|
+
if Pkg::Config.gem_platform_dependencies
|
137
|
+
create_platform_specific_gems
|
138
|
+
end
|
139
|
+
end
|
140
|
+
end
|
141
|
+
|
142
|
+
# An alias task to simplify our remote logic in jenkins.rake
|
143
|
+
namespace :pl do
|
144
|
+
task :gem => "package:gem"
|
145
|
+
end
|
146
|
+
end
|
data/tasks/jenkins.rake
ADDED
@@ -0,0 +1,494 @@
|
|
1
|
+
##
|
2
|
+
# The jenkins tasks enable the packaging repo to kick off packaging builds on a
|
3
|
+
# remote jenkins slave. They work in a similar way to the :remote tasks, but
|
4
|
+
# with a few key differences. The jenkins tasks transmit information to a
|
5
|
+
# jenkins coordinator, which handles the rest. The data passed are the
|
6
|
+
# following:
|
7
|
+
#
|
8
|
+
# 1) $PROJECT_BUNDLE - a tar.gz of a git-bundle from HEAD of the current
|
9
|
+
# project, which is cloned on the builder to set up a duplicate of this
|
10
|
+
# environment
|
11
|
+
#
|
12
|
+
# 2) $BUILD_PROPERTIES - a build parameters file, containing all information about the build
|
13
|
+
#
|
14
|
+
# 3) $BUILD_TYPE - the "type" of build, e.g. rpm, deb, gem, etc The jenkins url and job name
|
15
|
+
# are obtained via the team build-data file at
|
16
|
+
# git@github.com/puppetlabs/build-data
|
17
|
+
#
|
18
|
+
# 4) $PROJECT - the project we're building, e.g. facter, puppet. This is used later in
|
19
|
+
# determining the target for the build artifacts on the distribution server
|
20
|
+
#
|
21
|
+
# On the Jenkins end, the job is a parameterized job that accepts four
|
22
|
+
# parameters. Jenkins has the Parameterized Trigger Plugin, Workspace Cleanup
|
23
|
+
# Plugin, and Node and Label Parameter Plugin in use for this job. The
|
24
|
+
# workspace cleanup plugin cleans the workspace before each build. Two are file
|
25
|
+
# parameters, a string parameter, and a Label parameter provided by the Node
|
26
|
+
# and Label Parameter Plugin, as described above. When th pl:jenkins:post task
|
27
|
+
# triggers a build, it passes values for all of these parameters. The Label
|
28
|
+
# parameter is associated with the build type. This way we can queue the job on
|
29
|
+
# a builder with the appropriate capabilities just by assigning a builder the
|
30
|
+
# label "deb" or "rpm," etc. The actual build itself is accomplished via a
|
31
|
+
# shell build task. The contents of the task are:
|
32
|
+
#
|
33
|
+
#################
|
34
|
+
#
|
35
|
+
# #!/bin/bash
|
36
|
+
#
|
37
|
+
# SHA=$(echo $BUILD_PROPERTIES | cut -d '.' -f1)
|
38
|
+
#
|
39
|
+
# echo "Build type: $BUILD_TYPE"
|
40
|
+
#
|
41
|
+
# ### Create a local clone of the git-bundle that was passed
|
42
|
+
# # The bundle is a tarball, and since this is a project-agnostic
|
43
|
+
# # job, we don't actually know what's in it, just that it's a
|
44
|
+
# # git bundle.
|
45
|
+
# #
|
46
|
+
#
|
47
|
+
# [ -f "PROJECT_BUNDLE" ] || exit 1
|
48
|
+
# mkdir project && tar -xzf PROJECT_BUNDLE -C project/
|
49
|
+
#
|
50
|
+
# pushd project
|
51
|
+
# git clone --recursive $(ls) git_repo
|
52
|
+
#
|
53
|
+
# pushd git_repo
|
54
|
+
#
|
55
|
+
# ### Clone the packaging repo
|
56
|
+
# rake package:bootstrap
|
57
|
+
#
|
58
|
+
# ### Perform the build
|
59
|
+
# rake pl:build_from_params PARAMS_FILE=$WORKSPACE/BUILD_PROPERTIES
|
60
|
+
#
|
61
|
+
# ### Send the results
|
62
|
+
# rake pl:jenkins:ship["artifacts"] PARAMS_FILE=$WORKSPACE/BUILD_PROPERTIES
|
63
|
+
#
|
64
|
+
# popd
|
65
|
+
# popd
|
66
|
+
#
|
67
|
+
# ### Create the repositories from our project by trigger a downstream job
|
68
|
+
# ### Because we can't trigger downstream with a File Parameter, we use curl
|
69
|
+
# if [ "$BUILD_TYPE" = "rpm" ] || [ "$BUILD_TYPE" = "deb" ] ; then
|
70
|
+
# curl -i -Fname=PROJECT_BUNDLE -Ffile0=@PROJECT_BUNDLE -FSubmit=Build -Fjson="{\"parameter\":[{\"name\":\"PROJECT_BUNDLE\",\"file\":\"file0\"}]}" \
|
71
|
+
# http://jenkins-release.delivery.puppetlabs.net/job/puppetlabs-packaging-repo-creation/build
|
72
|
+
# fi
|
73
|
+
#
|
74
|
+
# ### If a downstream job was passed, trigger it now
|
75
|
+
# if [ -n "$DOWNSTREAM_JOB" ] ; then
|
76
|
+
# pushd project
|
77
|
+
# pushd git_repo
|
78
|
+
# rake pl:jenkins:post["$DOWNSTREAM_JOB"] PARAMS_FILE=$WORKSPACE/BUILD_PROPERTIES
|
79
|
+
# popd
|
80
|
+
# popd
|
81
|
+
# fi
|
82
|
+
#
|
83
|
+
#################
|
84
|
+
|
85
|
+
namespace :pl do
|
86
|
+
namespace :jenkins do
|
87
|
+
##
|
88
|
+
# Do the heavy lifting. This task generates the URL for the jenkins job and posts it.
|
89
|
+
# It expects a the following arguments
|
90
|
+
# 1. :build_task => The lower-level pl: or pe: task we're executing, e.g. pl:deb_all
|
91
|
+
#
|
92
|
+
task :post_build, :build_task do |t, args|
|
93
|
+
# Check for a dirty tree before allowing a remote build that is doomed to unexpected results
|
94
|
+
Pkg::Util::Git.fail_on_dirty_source
|
95
|
+
|
96
|
+
# We use JSON for parsing the json part of the submission to JSON
|
97
|
+
Pkg::Util.require_library_or_fail 'json'
|
98
|
+
|
99
|
+
build_task = args.build_task
|
100
|
+
##
|
101
|
+
# We set @:task of Pkg::Config manually with our task data so the remote
|
102
|
+
# build knows what to do. Puppetdb needs early knowledge of if this is
|
103
|
+
# a PE build, so we always this along as an environment variable task
|
104
|
+
# argument if its the case.
|
105
|
+
#
|
106
|
+
Pkg::Config.task = { :task => "#{build_task}", :args => nil }
|
107
|
+
Pkg::Config.task[:args] = ["PE_BUILD=true"] if @build_pe
|
108
|
+
#
|
109
|
+
# Determine the type of build we're doing to inform jenkins
|
110
|
+
build_type = case build_task
|
111
|
+
when /deb/
|
112
|
+
if Pkg::Config.default_cow.split('-')[1] =~ /cumulus/
|
113
|
+
"cumulus"
|
114
|
+
else
|
115
|
+
"deb"
|
116
|
+
end
|
117
|
+
when /mock/ then "rpm"
|
118
|
+
when /dmg|apple/ then "dmg"
|
119
|
+
when /gem/ then "gem"
|
120
|
+
when /tar/ then "tar"
|
121
|
+
else raise "Could not determine build type for #{build_task}"
|
122
|
+
end
|
123
|
+
|
124
|
+
# Create a string of metrics to send to Jenkins for data analysis
|
125
|
+
dist = case build_type
|
126
|
+
when /deb/ then Pkg::Config.default_cow.split('-')[1]
|
127
|
+
when /rpm/
|
128
|
+
if Pkg::Config.pe_version
|
129
|
+
Pkg::Config.final_mocks.split(' ')[0].split('-')[2]
|
130
|
+
else
|
131
|
+
Pkg::Config.final_mocks.split(' ')[0].split('-')[1..2].join("")
|
132
|
+
end
|
133
|
+
when /dmg/ then "apple"
|
134
|
+
when /gem/ then "gem"
|
135
|
+
when /sles/ then "sles"
|
136
|
+
when /tar/ then "tar"
|
137
|
+
else raise "Could not determine build type for #{build_task}"
|
138
|
+
end
|
139
|
+
|
140
|
+
if Pkg::Config.pe_version
|
141
|
+
metrics = "#{ENV['USER']}~#{Pkg::Config.version}~#{Pkg::Config.pe_version}~#{dist}~#{Pkg::Config.team}"
|
142
|
+
else
|
143
|
+
metrics = "#{ENV['USER']}~#{Pkg::Config.version}~N/A~#{dist}~#{Pkg::Config.team}"
|
144
|
+
end
|
145
|
+
#
|
146
|
+
# Create the data files to send to jenkins
|
147
|
+
properties = Pkg::Config.config_to_yaml
|
148
|
+
bundle = Pkg::Util::Git.bundle('HEAD')
|
149
|
+
|
150
|
+
# Construct the parameters, which is an array of hashes we turn into JSON
|
151
|
+
parameters = [{ "name" => "BUILD_PROPERTIES", "file" => "file0" },
|
152
|
+
{ "name" => "PROJECT_BUNDLE", "file" => "file1" },
|
153
|
+
{ "name" => "PROJECT", "value" => "#{Pkg::Config.project}" },
|
154
|
+
{ "name" => "BUILD_TYPE", "label" => "#{build_type}" },
|
155
|
+
{ "name" => "METRICS", "value" => "#{metrics}" }]
|
156
|
+
|
157
|
+
# Initialize the args array that will hold all of the arguments we pass
|
158
|
+
# to the curl utility method.
|
159
|
+
args = []
|
160
|
+
|
161
|
+
# If the environment variable "DOWNSTREAM_JOB" was passed, we want to
|
162
|
+
# send this value to the build job as well, so it knows to trigger a
|
163
|
+
# downstream job, and with what URI.
|
164
|
+
if ENV['DOWNSTREAM_JOB']
|
165
|
+
parameters << { "name" => "DOWNSTREAM_JOB", "value" => ENV['DOWNSTREAM_JOB'] }
|
166
|
+
args << ["-Fname=DOWNSTREAM_JOB", "-Fvalue=#{ENV['DOWNSTREAM_JOB']}"]
|
167
|
+
end
|
168
|
+
|
169
|
+
# Contruct the json string
|
170
|
+
json = JSON.generate("parameter" => parameters)
|
171
|
+
|
172
|
+
# Construct the remaining form arguments. For visual clarity, params that are tied
|
173
|
+
# together are on the same line.
|
174
|
+
#
|
175
|
+
args << [
|
176
|
+
"-Fname=BUILD_PROPERTIES", "-Ffile0=@#{properties}",
|
177
|
+
"-Fname=PROJECT_BUNDLE", "-Ffile1=@#{bundle}",
|
178
|
+
"-Fname=PROJECT", "-Fvalue=#{Pkg::Config.project}",
|
179
|
+
"-Fname=BUILD_TYPE", "-Fvalue=#{build_type}",
|
180
|
+
"-Fname=METRICS", "-Fvalue=#{metrics}",
|
181
|
+
"-FSubmit=Build",
|
182
|
+
"-Fjson=#{json.to_json}",
|
183
|
+
]
|
184
|
+
|
185
|
+
# We have several arrays inside args by now, flatten it up.
|
186
|
+
args.flatten!
|
187
|
+
|
188
|
+
# Construct the job url
|
189
|
+
#
|
190
|
+
job_url = "#{Pkg::Config.jenkins_build_host}/job/#{Pkg::Config.jenkins_packaging_job}"
|
191
|
+
trigger_url = "#{job_url}/build"
|
192
|
+
|
193
|
+
# Call out to the curl_form_data utility method in 00_utils.rake
|
194
|
+
#
|
195
|
+
begin
|
196
|
+
_, retval = Pkg::Util::Net.curl_form_data(trigger_url, args)
|
197
|
+
if Pkg::Util::Execution.success?(retval)
|
198
|
+
puts "Build submitted. To view your build results, go to #{job_url}"
|
199
|
+
puts "Your packages will be available at http://#{Pkg::Config.builds_server}/#{Pkg::Config.project}/#{Pkg::Config.ref}"
|
200
|
+
else
|
201
|
+
fail "An error occurred submitting the job to jenkins. Take a look at the preceding http response for more info."
|
202
|
+
end
|
203
|
+
ensure
|
204
|
+
# Clean up after ourselves
|
205
|
+
rm bundle
|
206
|
+
rm properties
|
207
|
+
end
|
208
|
+
end
|
209
|
+
end
|
210
|
+
end
|
211
|
+
|
212
|
+
##
|
213
|
+
# A task listing for creating jenkins tasks for our various pl: and pe: build
|
214
|
+
# tasks. We can assume deb, mock, but not gem/dmg.
|
215
|
+
#
|
216
|
+
tasks = ["deb", "mock", "tar"]
|
217
|
+
tasks << "gem" if Pkg::Config.build_gem and !Pkg::Config.build_pe
|
218
|
+
tasks << "dmg" if Pkg::Config.build_dmg and !Pkg::Config.build_pe
|
219
|
+
|
220
|
+
namespace :pl do
|
221
|
+
namespace :jenkins do
|
222
|
+
tasks.each do |build_task|
|
223
|
+
desc "Queue pl:#{build_task} build on jenkins builder"
|
224
|
+
task build_task => "pl:fetch" do
|
225
|
+
Pkg::Util::RakeUtils.invoke_task("pl:jenkins:post_build", "pl:#{build_task}")
|
226
|
+
end
|
227
|
+
end
|
228
|
+
|
229
|
+
# While pl:remote:deb_all does all cows in serially, with jenkins we
|
230
|
+
# parallelize them. This breaks the cows up and posts a build for all of
|
231
|
+
# them. We have to sleep 5 because jenkins drops the builds when we're
|
232
|
+
# DOSing it with our packaging.
|
233
|
+
desc "Queue pl:deb_all on jenkins builder"
|
234
|
+
task :deb_all => "pl:fetch" do
|
235
|
+
Pkg::Config.cows.split(' ').each do |cow|
|
236
|
+
Pkg::Config.default_cow = cow
|
237
|
+
Pkg::Util::RakeUtils.invoke_task("pl:jenkins:post_build", "pl:deb")
|
238
|
+
sleep 5
|
239
|
+
end
|
240
|
+
end
|
241
|
+
|
242
|
+
# This does the mocks in parallel
|
243
|
+
desc "Queue pl:mock_all on jenkins builder"
|
244
|
+
task :mock_all => "pl:fetch" do
|
245
|
+
Pkg::Config.final_mocks.split(' ').each do |mock|
|
246
|
+
Pkg::Config.default_mock = mock
|
247
|
+
Pkg::Util::RakeUtils.invoke_task("pl:jenkins:post_build", "pl:mock")
|
248
|
+
sleep 5
|
249
|
+
end
|
250
|
+
end
|
251
|
+
|
252
|
+
task :uber_ship_lite => "pl:fetch" do
|
253
|
+
tasks = %w(
|
254
|
+
jenkins:retrieve
|
255
|
+
jenkins:sign_all
|
256
|
+
ship_rpms
|
257
|
+
ship_debs
|
258
|
+
ship_dmg
|
259
|
+
ship_swix
|
260
|
+
ship_msi
|
261
|
+
)
|
262
|
+
tasks.map { |t| "pl:#{t}" }.each do |t|
|
263
|
+
puts "Running #{t} . . ."
|
264
|
+
Rake::Task[t].invoke
|
265
|
+
end
|
266
|
+
end
|
267
|
+
|
268
|
+
task :ship_nightlies => "pl:fetch" do
|
269
|
+
Rake::Task['pl:jenkins:uber_ship_lite'].invoke
|
270
|
+
Rake::Task['pl:remote:update_foss_repos'].invoke
|
271
|
+
Rake::Task['pl:remote:deploy_nightlies_to_s3'].invoke
|
272
|
+
end
|
273
|
+
|
274
|
+
task :ship_final => "pl:fetch" do
|
275
|
+
Rake::Task['pl:jenkins:uber_ship_lite'].invoke
|
276
|
+
Rake::Task['pl:remote:update_foss_repos'].invoke
|
277
|
+
Rake::Task['pl:remote:deploy_final_builds_to_s3'].invoke
|
278
|
+
Rake::Task['pl:remote:deploy_to_rsync_server'].invoke
|
279
|
+
end
|
280
|
+
|
281
|
+
desc "Retrieve packages built by jenkins, sign, and ship all!"
|
282
|
+
task :uber_ship => "pl:fetch" do
|
283
|
+
uber_tasks = %w(
|
284
|
+
jenkins:retrieve
|
285
|
+
jenkins:sign_all
|
286
|
+
uber_ship
|
287
|
+
ship_gem
|
288
|
+
remote:update_apt_repo
|
289
|
+
remote:update_yum_repo
|
290
|
+
remote:update_ips_repo
|
291
|
+
remote:deploy_apt_repo
|
292
|
+
remote:deploy_yum_repo
|
293
|
+
remote:deploy_dmg_repo
|
294
|
+
remote:deploy_swix_repo
|
295
|
+
remote:deploy_msi_repo
|
296
|
+
remote:deploy_tar_repo
|
297
|
+
remote:deploy_apt_repo_to_s3
|
298
|
+
remote:deploy_yum_repo_to_s3
|
299
|
+
remote:deploy_downloads_to_s3
|
300
|
+
remote:deploy_to_rsync_server
|
301
|
+
)
|
302
|
+
|
303
|
+
if Pkg::Util.boolean_value(Pkg::Config.answer_override) && !Pkg::Config.foss_only
|
304
|
+
fail "Using ANSWER_OVERRIDE without FOSS_ONLY=true is dangerous!"
|
305
|
+
end
|
306
|
+
|
307
|
+
# Some projects such as pl-build-tools do not stage to a separate server - so we do to deploy
|
308
|
+
uber_tasks.delete("remote:deploy_apt_repo") if Pkg::Config.apt_host == Pkg::Config.apt_signing_server
|
309
|
+
uber_tasks.delete("remote:deploy_yum_repo") if Pkg::Config.yum_host == Pkg::Config.yum_staging_server
|
310
|
+
uber_tasks.delete("remote:deploy_dmg_repo") if Pkg::Config.dmg_host == Pkg::Config.dmg_staging_server
|
311
|
+
uber_tasks.delete("remote:deploy_swix_repo") if Pkg::Config.swix_host == Pkg::Config.swix_staging_server
|
312
|
+
uber_tasks.delete("remote:deploy_tar_repo") if Pkg::Config.tar_host == Pkg::Config.tar_staging_server
|
313
|
+
|
314
|
+
if Pkg::Config.s3_ship
|
315
|
+
uber_tasks.delete("remote:deploy_apt_repo")
|
316
|
+
uber_tasks.delete("remote:deploy_yum_repo")
|
317
|
+
uber_tasks.delete("remote:deploy_dmg_repo")
|
318
|
+
uber_tasks.delete("remote:deploy_swix_repo")
|
319
|
+
uber_tasks.delete("remote:deploy_msi_repo")
|
320
|
+
uber_tasks.delete("remote:deploy_tar_repo")
|
321
|
+
else
|
322
|
+
uber_tasks.delete("remote:deploy_apt_repo_to_s3")
|
323
|
+
uber_tasks.delete("remote:deploy_yum_repo_to_s3")
|
324
|
+
uber_tasks.delete("remote:deploy_downloads_to_s3")
|
325
|
+
uber_tasks.delete("remote:deploy_to_rsync_server")
|
326
|
+
end
|
327
|
+
|
328
|
+
# Delete the ship_gem task if we aren't building gems
|
329
|
+
uber_tasks.delete("ship_gem") unless Pkg::Config.build_gem
|
330
|
+
|
331
|
+
# I'm adding this check here because if we rework the task ordering we're
|
332
|
+
# probably going to need to muck about in here. -morgan
|
333
|
+
if uber_tasks.first == 'jenkins:retrieve'
|
334
|
+
# We need to run retrieve before we can delete tasks based on what
|
335
|
+
# packages were built. Before this we were deleting tasks based on files
|
336
|
+
# in a directory that hadn't been populated yet, so this would either
|
337
|
+
# fail since all tasks would be removed, or would be running based on
|
338
|
+
# files left over in packaging from the last ship.
|
339
|
+
puts 'Do you want to run pl:jenkins:retrieve?'
|
340
|
+
Rake::Task['pl:jenkins:retrieve'].invoke if Pkg::Util.ask_yes_or_no
|
341
|
+
uber_tasks.delete('jenkins:retrieve')
|
342
|
+
end
|
343
|
+
|
344
|
+
# Don't update and deploy repos if packages don't exist
|
345
|
+
# If we can't find a certain file type, delete the task
|
346
|
+
if Dir.glob("pkg/**/*.deb").empty?
|
347
|
+
uber_tasks.delete("remote:update_apt_repo")
|
348
|
+
uber_tasks.delete("remote:deploy_apt_repo")
|
349
|
+
end
|
350
|
+
|
351
|
+
if Dir.glob("pkg/**/*.rpm").empty?
|
352
|
+
uber_tasks.delete("remote:update_yum_repo")
|
353
|
+
uber_tasks.delete("remote:deploy_yum_repo")
|
354
|
+
end
|
355
|
+
|
356
|
+
if Dir.glob("pkg/**/*.p5p").empty?
|
357
|
+
uber_tasks.delete("remote:update_ips_repo")
|
358
|
+
end
|
359
|
+
|
360
|
+
if Dir.glob("pkg/**/*.dmg").empty?
|
361
|
+
uber_tasks.delete("remote:deploy_dmg_repo")
|
362
|
+
end
|
363
|
+
|
364
|
+
if Dir.glob("pkg/**/*.swix").empty?
|
365
|
+
uber_tasks.delete("remote:deploy_swix_repo")
|
366
|
+
end
|
367
|
+
|
368
|
+
if Dir.glob("pkg/**/*.msi").empty?
|
369
|
+
uber_tasks.delete("remote:deploy_msi_repo")
|
370
|
+
end
|
371
|
+
|
372
|
+
if Dir.glob("pkg/*.tar.gz").empty?
|
373
|
+
uber_tasks.delete("remote:deploy_tar_repo")
|
374
|
+
end
|
375
|
+
|
376
|
+
uber_tasks.map { |t| "pl:#{t}" }.each do |t|
|
377
|
+
puts "Do you want to run #{t}?"
|
378
|
+
Rake::Task[t].invoke if Pkg::Util.ask_yes_or_no
|
379
|
+
end
|
380
|
+
|
381
|
+
puts "Do you want to mark this release as successfully shipped?"
|
382
|
+
Rake::Task["pl:jenkins:ship"].invoke("shipped") if Pkg::Util.ask_yes_or_no
|
383
|
+
end
|
384
|
+
|
385
|
+
desc "Test shipping by replacing hosts with a VM"
|
386
|
+
task :test_ship, [:vm, :ship_task] do |t, args|
|
387
|
+
vm = args.vm or fail "`vm` is a required argument for #{t}"
|
388
|
+
ship_task = args.ship_task or fail "`ship_task` is a required argument for #{t}"
|
389
|
+
Pkg::Util::Ship.test_ship(vm, ship_task)
|
390
|
+
end
|
391
|
+
end
|
392
|
+
end
|
393
|
+
|
394
|
+
##
|
395
|
+
# If this is a PE project, we want PE tasks as well.
|
396
|
+
#
|
397
|
+
if Pkg::Config.build_pe
|
398
|
+
namespace :pe do
|
399
|
+
namespace :jenkins do
|
400
|
+
tasks.each do |build_task|
|
401
|
+
desc "Queue pe:#{build_task} build on jenkins builder"
|
402
|
+
task build_task => "pl:fetch" do
|
403
|
+
Pkg::Util.check_var("PE_VER", Pkg::Config.pe_version)
|
404
|
+
Pkg::Util::RakeUtils.invoke_task("pl:jenkins:post_build", "pe:#{build_task}")
|
405
|
+
end
|
406
|
+
end
|
407
|
+
|
408
|
+
# While pl:remote:deb_all does all cows in serially, with jenkins we
|
409
|
+
# parallelize them. This breaks the cows up and posts a build for all of
|
410
|
+
# them. We have to sleep 5 because jenkins drops the builds when we're
|
411
|
+
# DOSing it with our packaging.
|
412
|
+
desc "Queue pe:deb_all on jenkins builder"
|
413
|
+
task :deb_all => "pl:fetch" do
|
414
|
+
Pkg::Util.check_var("PE_VER", Pkg::Config.pe_version)
|
415
|
+
Pkg::Config.cows.split(' ').each do |cow|
|
416
|
+
Pkg::Config.default_cow = cow
|
417
|
+
Pkg::Util::RakeUtils.invoke_task("pl:jenkins:post_build", "pe:deb")
|
418
|
+
sleep 5
|
419
|
+
end
|
420
|
+
end
|
421
|
+
|
422
|
+
# This does the mocks in parallel
|
423
|
+
desc "Queue pe:mock_all on jenkins builder"
|
424
|
+
task :mock_all => "pl:fetch" do
|
425
|
+
Pkg::Config.final_mocks.split(' ').each do |mock|
|
426
|
+
Pkg::Config.default_mock = mock
|
427
|
+
Pkg::Util::RakeUtils.invoke_task("pl:jenkins:post_build", "pe:mock")
|
428
|
+
sleep 5
|
429
|
+
end
|
430
|
+
end
|
431
|
+
|
432
|
+
desc "Retrieve PE packages built by jenkins, sign, and ship all!"
|
433
|
+
task :uber_ship => "pl:fetch" do
|
434
|
+
Pkg::Util.check_var("PE_VER", Pkg::Config.pe_version)
|
435
|
+
["pl:jenkins:retrieve", "pl:jenkins:sign_all", "pe:ship_rpms", "pe:ship_debs"].each do |task|
|
436
|
+
Rake::Task[task].invoke
|
437
|
+
end
|
438
|
+
Rake::Task["pl:jenkins:ship"].invoke("shipped")
|
439
|
+
end
|
440
|
+
end
|
441
|
+
end
|
442
|
+
end
|
443
|
+
|
444
|
+
##
|
445
|
+
# This task allows the packaging repo to post to an arbitrary jenkins job but
|
446
|
+
# it is very limited in that it does not model well the key => value format
|
447
|
+
# used when submitting form data on websites. This is primarily because rake
|
448
|
+
# does not allow us to elegantly pass arbitrary key => value pairs on the
|
449
|
+
# command line and have any idea how to reference them inside rake. We can pass
|
450
|
+
# KEY=VALUE along with our invokation, but unless KEY is statically coded into
|
451
|
+
# our task, we won't know how to reference it. Thus, this task will only take
|
452
|
+
# one argument, the uri of the jenkins job to post to. This can be passed
|
453
|
+
# either as an argument directly or as an environment variable "JOB" with the
|
454
|
+
# uri as the value. The argument is required. The second requirement is that
|
455
|
+
# the job to be called accept a string parameter with the name SHA. This will
|
456
|
+
# be the SHA of the commit of the project source code HEAD, and should be used
|
457
|
+
# by the job to check out this specific ref. To maintain the abstraction of the
|
458
|
+
# jenkins jobs, this specific task passes on no information about the build
|
459
|
+
# itself. The assumption is that the upstream jobs know about their project,
|
460
|
+
# and so do the downstream jobs, but packaging itself has no business knowing
|
461
|
+
# about it.
|
462
|
+
#
|
463
|
+
namespace :pl do
|
464
|
+
namespace :jenkins do
|
465
|
+
desc "Trigger a jenkins uri with SHA of HEAD as a string param, requires \"URI\""
|
466
|
+
task :post, :uri do |t, args|
|
467
|
+
uri = (args.uri or ENV['URI']) or fail "pl:jenkins:post requires a URI, either via URI= or pl:jenkin:post[URI]"
|
468
|
+
|
469
|
+
# We use JSON for parsing the json part of the submission.
|
470
|
+
begin
|
471
|
+
require 'json'
|
472
|
+
rescue LoadError
|
473
|
+
fail "Couldn't require 'json'. JSON is required for sanely generating the string we curl to Jenkins."
|
474
|
+
end
|
475
|
+
|
476
|
+
# Assemble the JSON string for the JSON parameter
|
477
|
+
json = JSON.generate("parameter" => [{ "name" => "SHA", "value" => "#{Pkg::Config.ref}" }])
|
478
|
+
|
479
|
+
# Assemble our arguments to the post
|
480
|
+
args = [
|
481
|
+
"-Fname=SHA", "-Fvalue=#{Pkg::Config.ref}",
|
482
|
+
"-Fjson=#{json.to_json}",
|
483
|
+
"-FSubmit=Build"
|
484
|
+
]
|
485
|
+
|
486
|
+
_, retval = Pkg::Util::Net.curl_form_data(uri, args)
|
487
|
+
if Pkg::Util::Execution.success?(retval)
|
488
|
+
puts "Job triggered at #{uri}."
|
489
|
+
else
|
490
|
+
fail "An error occurred attempting to trigger the job at #{uri}. Please see the preceding http response for more info."
|
491
|
+
end
|
492
|
+
end
|
493
|
+
end
|
494
|
+
end
|