Skip to content

Commit 30ab628

Browse files
pbuskonicolasbenderc0d1ngm0nk3ymodulo11
authored
[RFC0031] Support for System Cloud Native Buildpacks (#3898)
Co-authored-by: Pavel Busko <[email protected]> Co-authored-by: Nicolas Bender <[email protected]> Co-authored-by: Ralf Pannemans <[email protected]> Co-authored-by: Johannes Dillmann <[email protected]>
1 parent 69f1380 commit 30ab628

File tree

60 files changed

+610
-231
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

60 files changed

+610
-231
lines changed

app/actions/build_create.rb

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -95,7 +95,6 @@ def create_and_stage(package:, lifecycle:, metadata: nil, start_after_staging: f
9595

9696
def requested_buildpacks_disabled!(lifecycle)
9797
return if lifecycle.type == Lifecycles::DOCKER
98-
return if lifecycle.type == Lifecycles::CNB
9998

10099
admin_buildpack_records = lifecycle.buildpack_infos.map(&:buildpack_record).compact
101100
disabled_buildpacks = admin_buildpack_records.reject(&:enabled)

app/actions/buildpack_create.rb

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ def create(message)
1414
buildpack = Buildpack.create(
1515
name: message.name,
1616
stack: message.stack,
17+
lifecycle: (message.lifecycle.nil? ? Config.config.get(:default_app_lifecycle) : message.lifecycle),
1718
enabled: (message.enabled.nil? ? DEFAULT_ENABLED : message.enabled),
1819
locked: (message.locked.nil? ? DEFAULT_LOCKED : message.locked)
1920
)
@@ -28,7 +29,9 @@ def create(message)
2829

2930
def validation_error!(error, create_message)
3031
error!(%(Stack '#{create_message.stack}' does not exist)) if error.errors.on(:stack)&.include?(:buildpack_stack_does_not_exist)
31-
error!(%(Buildpack with name '#{error.model.name}' and stack '#{error.model.stack}' already exists)) if error.errors.on(%i[name stack])&.include?(:unique)
32+
if error.errors.on(%i[name stack lifecycle])&.include?(:unique)
33+
error!(%(Buildpack with name '#{error.model.name}', stack '#{error.model.stack}' and lifecycle '#{error.model.lifecycle}' already exists))
34+
end
3235
error!(%(Buildpack with name '#{error.model.name}' and an unassigned stack already exists)) if error.errors.on(:stack)&.include?(:unique)
3336

3437
error!(error.message)

app/actions/buildpack_update.rb

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,10 @@ def validation_error!(error, message)
2727
error!(%(Stack '#{message.stack}' does not exist)) if error.errors.on(:stack)&.include?(:buildpack_stack_does_not_exist)
2828
error!(%(Buildpack stack cannot be changed)) if error.errors.on(:stack)&.include?(:buildpack_cant_change_stacks)
2929
error!(%(Buildpack with name '#{error.model.name}' and an unassigned stack already exists)) if error.errors.on(:stack)&.include?(:unique)
30-
error!(%(Buildpack with name '#{error.model.name}' and stack '#{error.model.stack}' already exists)) if error.errors.on(%i[name stack])&.include?(:unique)
30+
31+
if error.errors.on(%i[name stack lifecycle])&.include?(:unique)
32+
error!(%(Buildpack with name '#{error.model.name}', stack '#{error.model.stack}' and lifecycle '#{error.model.lifecycle}' already exists))
33+
end
3134

3235
error!(error.message)
3336
end

app/controllers/runtime/buildpacks_controller.rb

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,17 +7,18 @@ def self.dependencies
77
define_attributes do
88
attribute :name, String
99
attribute :stack, String, default: nil
10+
attribute :lifecycle, String, default: nil, exclude_in: :update
1011
attribute :position, Integer, default: 0
1112
attribute :enabled, Message::Boolean, default: true
1213
attribute :locked, Message::Boolean, default: false
1314
end
1415

15-
query_parameters :name, :stack
16+
query_parameters :name, :stack, :lifecycle
1617

1718
def self.translate_validation_exception(e, attributes)
18-
buildpack_errors = e.errors.on(%i[name stack])
19+
buildpack_errors = e.errors.on(%i[name stack lifecycle])
1920
if buildpack_errors && buildpack_errors.include?(:unique)
20-
CloudController::Errors::ApiError.new_from_details('BuildpackNameStackTaken', attributes['name'], attributes['stack'])
21+
CloudController::Errors::ApiError.new_from_details('BuildpackNameStackLifecycleTaken', attributes['name'], attributes['stack'], attributes['lifecycle'])
2122
else
2223
CloudController::Errors::ApiError.new_from_details('BuildpackInvalid', e.errors.full_messages)
2324
end

app/fetchers/buildpack_lifecycle_fetcher.rb

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,19 @@
1+
require 'cloud_controller/diego/lifecycles/lifecycles'
2+
13
module VCAP::CloudController
24
class BuildpackLifecycleFetcher
35
class << self
4-
def fetch(buildpack_names, stack_name)
6+
def fetch(buildpack_names, stack_name, lifecycle=Config.config.get(:default_app_lifecycle))
57
{
68
stack: Stack.find(name: stack_name),
7-
buildpack_infos: ordered_buildpacks(buildpack_names, stack_name)
9+
buildpack_infos: ordered_buildpacks(buildpack_names, stack_name, lifecycle)
810
}
911
end
1012

1113
private
1214

13-
def ordered_buildpacks(buildpack_names, stack_name)
14-
buildpacks_with_stacks, buildpacks_without_stacks = Buildpack.list_admin_buildpacks(stack_name).partition(&:stack)
15+
def ordered_buildpacks(buildpack_names, stack_name, lifecycle)
16+
buildpacks_with_stacks, buildpacks_without_stacks = Buildpack.list_admin_buildpacks(stack_name, lifecycle).partition(&:stack)
1517

1618
buildpack_names.map do |buildpack_name|
1719
buildpack_record = buildpacks_with_stacks.find { |b| b.name == buildpack_name } || buildpacks_without_stacks.find { |b| b.name == buildpack_name }

app/fetchers/buildpack_list_fetcher.rb

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
require 'cloud_controller/paging/sequel_paginator'
22
require 'cloud_controller/paging/paginated_result'
3+
require 'cloud_controller/diego/lifecycles/lifecycles'
34
require 'fetchers/null_filter_query_generator'
45
require 'fetchers/base_list_fetcher'
56

@@ -18,6 +19,7 @@ def filter(message, dataset)
1819
dataset = dataset.where(name: message.names) if message.requested?(:names)
1920

2021
dataset = NullFilterQueryGenerator.add_filter(dataset, :stack, message.stacks) if message.requested?(:stacks)
22+
dataset = dataset.where(lifecycle: message.requested?(:lifecycle) ? message.lifecycle : Config.config.get(:default_app_lifecycle))
2123

2224
if message.requested?(:label_selector)
2325
dataset = LabelSelectorQueryGenerator.add_selector_queries(

app/jobs/runtime/buildpack_installer_factory.rb

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -37,8 +37,7 @@ def plan(buildpack_name, manifest_fields)
3737

3838
planned_jobs = []
3939

40-
found_buildpacks = Buildpack.where(name: buildpack_name).all
41-
40+
found_buildpacks = Buildpack.where(name: buildpack_name, lifecycle: manifest_fields[0][:options][:lifecycle]).all
4241
ensure_no_attempt_to_upgrade_a_stackless_locked_buildpack(buildpack_name, found_buildpacks, manifest_fields)
4342

4443
manifest_fields.each do |buildpack_fields|

app/jobs/runtime/create_buildpack_installer.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ def perform
1010
buildpacks_lock = Locking[name: 'buildpacks']
1111
buildpacks_lock.db.transaction do
1212
buildpacks_lock.lock!
13-
buildpack = Buildpack.create(name: name, stack: stack_name)
13+
buildpack = Buildpack.create(name: name, stack: stack_name, lifecycle: options[:lifecycle])
1414
end
1515
begin
1616
buildpack_uploader.upload_buildpack(buildpack, file, File.basename(file))

app/messages/app_manifest_message.rb

Lines changed: 12 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,6 @@ def self.underscore_keys(hash)
7272
validate :validate_buildpack_and_buildpacks_combination!
7373
validate :validate_docker_enabled!
7474
validate :validate_cnb_enabled!
75-
validate :validate_cnb_buildpacks!
7675
validate :validate_docker_buildpacks_combination!
7776
validate :validate_service_bindings_message!, if: ->(record) { record.requested?(:services) }
7877
validate :validate_env_update_message!, if: ->(record) { record.requested?(:env) }
@@ -128,7 +127,7 @@ def app_lifecycle_hash
128127
cnb_lifecycle_data
129128
elsif requested?(:docker)
130129
docker_lifecycle_data
131-
else
130+
elsif requested?(:buildpacks) || requested?(:buildpack) || requested?(:stack)
132131
buildpacks_lifecycle_data
133132
end
134133

@@ -285,15 +284,6 @@ def docker_lifecycle_data
285284
end
286285

287286
def cnb_lifecycle_data
288-
return unless requested?(:buildpacks) || requested?(:buildpack) || requested?(:stack)
289-
290-
if requested?(:buildpacks)
291-
requested_buildpacks = @buildpacks
292-
elsif requested?(:buildpack)
293-
requested_buildpacks = []
294-
requested_buildpacks.push(@buildpack)
295-
end
296-
297287
{
298288
type: Lifecycles::CNB,
299289
data: {
@@ -305,16 +295,8 @@ def cnb_lifecycle_data
305295
end
306296

307297
def buildpacks_lifecycle_data
308-
return unless requested?(:buildpacks) || requested?(:buildpack) || requested?(:stack)
309-
310-
if requested?(:buildpacks)
311-
requested_buildpacks = @buildpacks
312-
elsif requested?(:buildpack)
313-
requested_buildpacks = []
314-
requested_buildpacks.push(@buildpack) unless should_autodetect?(@buildpack)
315-
end
316-
317298
{
299+
type: Lifecycles::BUILDPACK,
318300
data: {
319301
buildpacks: requested_buildpacks,
320302
stack: @stack
@@ -485,13 +467,6 @@ def validate_cnb_enabled!
485467
errors.add(:base, e.message)
486468
end
487469

488-
def validate_cnb_buildpacks!
489-
return unless @lifecycle == 'cnb'
490-
return if requested?(:lifecycle) && (requested?(:buildpack) || requested?(:buildpacks))
491-
492-
errors.add(:base, 'Buildpack(s) must be specified when using Cloud Native Buildpacks')
493-
end
494-
495470
def validate_docker_buildpacks_combination!
496471
return unless requested?(:docker) && (requested?(:buildpack) || requested?(:buildpacks))
497472

@@ -501,5 +476,15 @@ def validate_docker_buildpacks_combination!
501476
def add_process_error!(error_message, type)
502477
errors.add(:base, %(Process "#{type}": #{error_message}))
503478
end
479+
480+
def requested_buildpacks
481+
return nil unless requested?(:buildpacks) || requested?(:buildpack)
482+
return @buildpacks if requested?(:buildpacks)
483+
484+
buildpacks = []
485+
buildpacks.push(@buildpack) if requested?(:buildpack) && !should_autodetect?(@buildpack)
486+
487+
buildpacks
488+
end
504489
end
505490
end

app/messages/buildpack_create_message.rb

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,13 @@
11
require 'messages/metadata_base_message'
22
require 'messages/validators'
3+
require 'cloud_controller/diego/lifecycles/lifecycles'
34

45
module VCAP::CloudController
56
class BuildpackCreateMessage < MetadataBaseMessage
67
MAX_BUILDPACK_NAME_LENGTH = 250
78
MAX_STACK_LENGTH = 250
89

9-
register_allowed_keys %i[name stack position enabled locked]
10+
register_allowed_keys %i[name stack position enabled locked lifecycle]
1011
validates_with NoAdditionalKeysValidator
1112

1213
validates :name,
@@ -32,5 +33,10 @@ class BuildpackCreateMessage < MetadataBaseMessage
3233
validates :locked,
3334
allow_nil: true,
3435
boolean: true
36+
37+
validates :lifecycle,
38+
string: true,
39+
allow_nil: true,
40+
inclusion: { in: [VCAP::CloudController::Lifecycles::BUILDPACK, VCAP::CloudController::Lifecycles::CNB], message: 'must be either "buildpack" or "cnb"' }
3541
end
3642
end

0 commit comments

Comments
 (0)