Class: Jets::Cfn::Builder::Api::Pages::Base

Inherits:
Object
  • Object
show all
Extended by:
Memoist
Defined in:
lib/jets/cfn/builder/api/pages/base.rb

Direct Known Subclasses

Methods, Resources

Constant Summary collapse

@@pages =
{}

Class Method Summary collapse

Class Method Details

.build_uids_mapObject

Build map that has uids as keys and page number as value For Resources, the uid is the path

Example: {"a1"=>0, "a2"=>0, "b1"=>1, "b2"=>1, "c1"=>2, "c2"=>2}

For Methods, the uid is the method|path

Example: {"GET|a1"=>0, "GET|a2"=>0, "GET|b1"=>1, "GET|b2"=>1, "GET|c1"=>2, "GET|c2"=>2}


59
60
61
62
63
64
65
66
# File 'lib/jets/cfn/builder/api/pages/base.rb', line 59

def build_uids_map
  map = {}
  # uids is interface method
  uids.each do |uid|
    map[uid] = find_page_index(uid)
  end
  map
end

.find_page_index(new_uid) ⇒ Object



68
69
70
71
72
73
74
75
76
77
# File 'lib/jets/cfn/builder/api/pages/base.rb', line 68

def find_page_index(new_uid)
  slices = previously_deployed || []
  slices.each_with_index do |slice, page_number|
    items = slice["items"]
    items.find do |old_uid|
      return page_number if old_uid == new_uid # found
    end
  end
  nil # not found
end

.page_limitObject

Relevant CloudFormation limits:

Resources 500
Parameters 200
Outputs 200

For API Gateway Methods template, Lambda Functions and APIGW Resources are passed in as parameters. Each APIGW Method can use 2 parameters. So use page limit of 100 to provide a buffer. Technically, can use a different limit for Resources and Cors templates, but keeping all at 100 for consistency.

JETS_API_PAGE_LIMIT is based on that docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/cloudformation-limits.html



100
101
102
# File 'lib/jets/cfn/builder/api/pages/base.rb', line 100

def page_limit
  Integer(ENV['JETS_API_PAGE_LIMIT'] || 100)
end

.pagesObject

Returns: Array<Page>



10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
# File 'lib/jets/cfn/builder/api/pages/base.rb', line 10

def pages
  return @@pages[self.name] if @@pages[self.name]

  pages = []
  uids_map = build_uids_map
  uids_map.each do |uid, existing_page|
    if existing_page
      pages[existing_page] ||= []
      pages[existing_page] << uid
    end
  end
  pages.compact! # not using page 0 so need to compact to remove the first nil element

  # Remove existing uids from uids_map. Leave behind new uids
  pages.each do |page|
    page.each do |i|
      uids_map.delete(i)
    end
  end

  # Fill up available space in each page so all existing pages are full
  keys = uids_map.keys
  pages.each do |page|
    break if keys.empty?
    while page.size < page_limit
      uid = keys.shift
      break if uid.nil?
      page << uid
    end
  end

  # Add remaining slices to new additional pages
  pages += keys.each_slice(page_limit).to_a

  @@pages[self.name] = []
  pages.each_with_index do |uids, i|
    # Note: page number starts at 1
    # Because of this we need to do a pages.compact! above to remove the first nil element. Feel this is easier for follow for us humans.
    @@pages[self.name] << Page.new(items: uids, number: i+1)
  end

  @@pages[self.name]
end

.previously_deployedObject



79
80
81
82
83
84
# File 'lib/jets/cfn/builder/api/pages/base.rb', line 79

def previously_deployed
  state = Jets::Router::State.new
  name = self.to_s.split('::').last.downcase
  deployed = state.load(name) # IE: state.load("resources") or state.load("methods")
  deployed
end