dtk-client 0.10.5 → 0.10.6

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 (41) hide show
  1. checksums.yaml +13 -5
  2. data/.gitignore +1 -0
  3. data/bin/dtk-puppet +38 -0
  4. data/lib/cli/command/module/delete_from_remote.rb +3 -4
  5. data/lib/cli/command/module/pull_dtkn.rb +3 -1
  6. data/lib/cli/command/module/uninstall.rb +2 -2
  7. data/lib/cli/command/service/uninstall.rb +3 -3
  8. data/lib/cli/command/token.rb +1 -1
  9. data/lib/cli/version.rb +1 -1
  10. data/lib/client/error/subclasses.rb +7 -0
  11. data/lib/client/git_repo/adapter/git_gem.rb +38 -5
  12. data/lib/client/git_repo.rb +8 -3
  13. data/lib/client/load_source/component_info.rb +1 -4
  14. data/lib/client/load_source/service_info.rb +5 -7
  15. data/lib/client/load_source.rb +62 -10
  16. data/lib/client/module_ref.rb +2 -0
  17. data/lib/client/operation/client_module_dir/git_repo/internal/dtkn.rb +6 -1
  18. data/lib/client/operation/client_module_dir/git_repo/internal.rb +8 -2
  19. data/lib/client/operation/client_module_dir/git_repo.rb +13 -4
  20. data/lib/client/operation/module/delete_from_remote.rb +2 -2
  21. data/lib/client/operation/module/install/common_module.rb +1 -1
  22. data/lib/client/operation/module/list.rb +1 -1
  23. data/lib/client/operation/module/publish.rb +1 -0
  24. data/lib/client/operation/module/pull_dtkn.rb +4 -3
  25. data/lib/client/operation/module/push_dtkn/convert_source.rb +18 -5
  26. data/lib/client/operation/module/push_dtkn.rb +1 -1
  27. data/lib/client/operation/module/stage.rb +1 -1
  28. data/lib/client/operation/module/uninstall.rb +53 -29
  29. data/lib/client/operation/service/converge.rb +1 -1
  30. data/lib/client/operation/service/delete.rb +13 -2
  31. data/lib/client/operation/service/exec.rb +2 -2
  32. data/lib/client/operation/service/uninstall.rb +11 -8
  33. data/lib/client/render/view/table/processor.rb +7 -0
  34. data/lib/client/render.rb +1 -0
  35. data/lib/client/response/render_helper.rb +5 -2
  36. data/lib/client/service_and_component_info/transform_from/info/component.rb +1 -1
  37. data/lib/client/util/os_util.rb +25 -0
  38. data/lib/dtk_puppet/parse_structure.rb +180 -0
  39. data/lib/dtk_puppet/parser.rb +92 -0
  40. data/lib/dtk_puppet.rb +24 -0
  41. metadata +16 -11
@@ -54,21 +54,24 @@ module DTK::Client; class Operation::Module
54
54
 
55
55
  create_and_checkout_branch?(current_branch, target_repo_dir, "remotes/dtkn/master") do |repo|
56
56
  FileUtils.mkdir_p("#{target_repo_dir}/assemblies") unless File.exists?("#{target_repo_dir}/assemblies")
57
-
57
+
58
58
  args = [transform_helper, ServiceInfo.info_type, service_info['remote_repo_url'], parent]
59
59
  service_file_path__content_array.each { |file| Operation::ClientModuleDir.create_file_with_content("#{service_file_path(target_repo_dir, file, *args)}", file[:content]) }
60
-
60
+
61
61
  commit_and_push_to_remote(repo, target_repo_dir, "master", "dtkn")
62
62
  end
63
63
  end
64
64
 
65
65
  def self.transform_component_info(target_repo_dir, parent, component_info, parsed_common_module, current_branch)
66
- transform_helper = ServiceAndComponentInfo::TransformTo.new(target_repo_dir, parent.module_ref, parent.version, parsed_common_module)
66
+ transform_helper = ServiceAndComponentInfo::TransformTo.new(target_repo_dir, parent.module_ref, parent.version, parsed_common_module)
67
67
  component_file_path__content_array = ComponentInfo.transform_info(transform_helper, component_info['remote_repo_url'], parent)
68
+ component_info_remote = "remotes/dtkn-component-info/master"
68
69
 
69
- create_and_checkout_branch?(current_branch, target_repo_dir, "remotes/dtkn-component-info/master") do |repo|
70
- component_file_path__content_array.each { |file| Operation::ClientModuleDir.create_file_with_content("#{file_path(target_repo_dir, file)}", file[:content]) }
70
+ create_and_checkout_branch?(current_branch, target_repo_dir, component_info_remote) do |repo|
71
+ # find deleted files from master branch and delete them in component info cached branch ("remotes/dtkn-component-info/master")
72
+ delete_diffs(repo, component_info_remote, current_branch, target_repo_dir)
71
73
 
74
+ component_file_path__content_array.each { |file| Operation::ClientModuleDir.create_file_with_content("#{file_path(target_repo_dir, file)}", file[:content]) }
72
75
  commit_and_push_to_remote(repo, target_repo_dir, "master", "dtkn-component-info")
73
76
  end
74
77
  end
@@ -77,6 +80,16 @@ module DTK::Client; class Operation::Module
77
80
 
78
81
  attr_reader :info_processor, :target_repo_dir, :parent
79
82
 
83
+ def self.delete_diffs(repo, component_info_remote, current_branch, target_repo_dir)
84
+ if diffs = repo.diff_name_status(component_info_remote, current_branch)
85
+ deletes_and_renames = diffs.select{ |k,v| v.eql?('D') || v.start_with?('R') }
86
+ unless deletes_and_renames.empty?
87
+ to_delete = deletes_and_renames.keys.select { |key| !key.include?('dtk.model.yaml') && !key.include?('module_refs.yaml') }
88
+ to_delete.each { |file| Operation::ClientModuleDir.rm_f("#{target_repo_dir}/#{file}") }
89
+ end
90
+ end
91
+ end
92
+
80
93
  def self.write_output_path_text_pairs(transform_helper, target_repo_dir, info_types_processed)
81
94
  end
82
95
 
@@ -52,7 +52,7 @@ module DTK::Client
52
52
  end
53
53
 
54
54
  error_msg = "To allow push-dtkn to go through, invoke 'dtk push' to push the changes to server before invoking push-dtkn again"
55
- GitRepo.modified_with_diff?(@target_repo_dir, { :error_msg => error_msg })
55
+ GitRepo.modified_with_diff?(@target_repo_dir, { :error_msg => error_msg, :command => 'push-dtkn' })
56
56
 
57
57
  query_string_hash = QueryStringHash.new(
58
58
  :module_name => @module_ref.module_name,
@@ -36,7 +36,7 @@ module DTK::Client
36
36
  )
37
37
 
38
38
  error_msg = "To allow stage to go through, invoke 'dtk push' to push the changes to server before invoking stage again"
39
- GitRepo.modified_with_diff?(directory_path || module_ref.client_dir_path, { :error_msg => error_msg }) unless force
39
+ GitRepo.modified_with_diff?(directory_path || module_ref.client_dir_path, { :error_msg => error_msg, :command => 'stage' }) unless force
40
40
  service_name ||= rest_post("#{BaseRoute}/generate_service_name", post_body).data
41
41
  base_path = ClientModuleDir.ret_base_path(:service, service_name)
42
42
 
@@ -23,8 +23,7 @@ module DTK::Client
23
23
  module_ref = args.required(:module_ref)
24
24
  name = args.required(:name)
25
25
  version = args.required(:version)
26
- versions = nil
27
-
26
+
28
27
  unless name.nil?
29
28
  query_string_hash = QueryStringHash.new(
30
29
  :detail_to_include => ['remotes', 'versions']
@@ -32,44 +31,69 @@ module DTK::Client
32
31
  response = rest_get("#{BaseRoute}/list", query_string_hash)
33
32
  installed_modules = response.data
34
33
 
35
- name.gsub!("/", ":")
36
- installed_modules.each do |module_val|
37
- if module_val["display_name"].eql? name
38
- val = name.split(":")
39
- if version.nil?
40
- versions = module_val["versions"].split(",").map(&:strip)
41
- if versions.size > 1
42
- version = Console.version_prompt(versions, "Select which module version to uninstall: ", { :add_all => true})
43
- module_val["versions"] if version.eql? "all"
44
- else
45
- version = module_val["versions"]
46
- end
47
- end
48
-
49
- module_opts = {
50
- :module_name => val[1],
51
- :namespace => val[0],
52
- :version => version
53
- }
54
- module_ref = ModuleRef.new(module_opts)
55
- end
56
- end
34
+ module_ref = process_module_ref(installed_modules, name, version)
57
35
  end
58
-
36
+
59
37
  raise Error::Usage, "Invalid module name." if module_ref.nil?
60
38
 
39
+ delete_versions = module_ref.version
40
+
61
41
  unless args[:skip_prompt]
62
- return false unless Console.prompt_yes_no("Are you sure you want to uninstall module '#{module_ref.pretty_print}' from the DTK Server?", :add_options => true)
42
+ if delete_versions && delete_versions.is_a?(Array)
43
+ return false unless Console.prompt_yes_no("Are you sure you want to uninstall all module versions for '#{module_ref.namespace}/#{module_ref.module_name}' from the DTK Server?", :add_options => true)
44
+ else
45
+ return false unless Console.prompt_yes_no("Are you sure you want to uninstall module '#{module_ref.pretty_print}' from the DTK Server?", :add_options => true)
46
+ end
47
+
63
48
  end
64
49
 
65
50
  post_body = module_ref_post_body(module_ref)
66
- post_body.merge!(:versions => versions) if versions
67
-
68
51
  rest_post("#{BaseRoute}/delete", post_body)
69
- OsUtil.print_info("DTK module '#{module_ref.pretty_print}' has been uninstalled successfully.")
52
+
53
+ error_msg =
54
+ if delete_versions && delete_versions.is_a?(Array) && delete_versions.size > 1
55
+ "All versions of dtk module '#{module_ref.namespace}/#{module_ref.module_name}' have been uninstalled."
56
+ else
57
+ "DTK module '#{module_ref.pretty_print}' has been uninstalled successfully."
58
+ end
59
+
60
+ OsUtil.print_info(error_msg)
70
61
  nil
71
62
  end
72
63
  end
64
+
65
+ def self.process_module_ref(installed_modules, name, version)
66
+ name.gsub!('/', ':')
67
+ module_ref = nil
68
+
69
+ installed_modules.each do |module_val|
70
+ if module_val["display_name"].eql? name
71
+ val = name.split(":")
72
+ if version.nil?
73
+ versions = module_val["versions"].split(",").map(&:strip)
74
+ versions.each { |value| value.tr!('*', '') }
75
+
76
+ if versions.size > 1
77
+ version = Console.version_prompt(versions, "Select which module version to uninstall: ", { :add_all => true})
78
+ version = versions if version.eql? "all"
79
+ else
80
+ version = module_val["versions"]
81
+ version.tr!('*', '') if version.include?('*')
82
+ end
83
+ end
84
+
85
+ module_opts = {
86
+ :module_name => val[1],
87
+ :namespace => val[0],
88
+ :version => version
89
+ }
90
+
91
+ module_ref = ModuleRef.new(module_opts)
92
+ end
93
+ end
94
+
95
+ module_ref
96
+ end
73
97
 
74
98
  end
75
99
  end
@@ -29,7 +29,7 @@ module DTK::Client
29
29
  )
30
30
 
31
31
  error_msg = "To allow converge to go through, invoke 'dtk push' to push the changes to server before invoking converge again"
32
- GitRepo.modified_with_diff?(module_dir, { :error_msg => error_msg }) unless force
32
+ GitRepo.modified_with_diff?(module_dir, { :error_msg => error_msg, :command => 'converge' }) unless force
33
33
  violations = find_violations(service_instance)
34
34
  return violations if violations
35
35
 
@@ -30,14 +30,25 @@ module DTK::Client
30
30
  end
31
31
 
32
32
  error_msg = "To allow delete to go through, invoke 'dtk push' to push the changes to server before invoking delete again"
33
- GitRepo.modified_with_diff?(directory_path || @module_ref.client_dir_path, { :error_msg => error_msg }) unless force
33
+ GitRepo.modified_with_diff?(directory_path || @module_ref.client_dir_path, { :error_msg => error_msg, :command => 'delete' }) unless force
34
34
  post_body = PostBody.new(
35
35
  :service_instance => service_instance,
36
36
  :recursive? => recursive
37
37
  )
38
- rest_post("#{BaseRoute}/delete", post_body)
38
+ response = rest_post("#{BaseRoute}/delete", post_body)
39
39
 
40
40
  OsUtil.print_info("Delete procedure started. For more information use 'dtk task-status'.")
41
+ display_node_info(response.data)
42
+ end
43
+ end
44
+
45
+ def self.display_node_info(nodes, message = '')
46
+ if nodes.size > 0
47
+ nodes.each do |node|
48
+ return if node['admin_op_status'] == 'pending' || node['external_ref']["instance_id"].nil?
49
+ message += "#{node["display_name"]} - #{ node["external_ref"]["instance_id"]}\n" unless node["display_name"].eql?("node") && node["dtk_client_type"].eql?("node_group")
50
+ end
51
+ OsUtil.print("Nodes that will be deleted: \n" + message)
41
52
  end
42
53
  end
43
54
 
@@ -35,8 +35,8 @@ module DTK::Client
35
35
  end
36
36
 
37
37
  error_msg = "To allow #{args[:command]} to go through, invoke 'dtk push' to push the changes to server before invoking #{args[:command]} again"
38
- GitRepo.modified_with_diff?(directory_path, { :error_msg => error_msg })
39
-
38
+ GitRepo.modified_with_diff?(directory_path, { :error_msg => error_msg, :command => 'exec'})
39
+
40
40
  post_body = PostBody.new(
41
41
  :task_params? => task_params
42
42
  )
@@ -22,7 +22,9 @@ module DTK::Client
22
22
  wrap_operation(args) do |args|
23
23
  service_instance = args.required(:service_instance)
24
24
  recursive = args.required(:recursive)
25
- delete = args.required(:delete)
25
+ delete = args.required(:delete)
26
+ path = args[:directory_path]
27
+ node = []
26
28
 
27
29
  unless args[:skip_prompt]
28
30
  return false unless Console.prompt_yes_no("Are you sure you want to uninstall the infrastructure associated with '#{service_instance}' and delete this service instance from the server?", :add_options => true)
@@ -30,19 +32,20 @@ module DTK::Client
30
32
 
31
33
  post_body = PostBody.new(
32
34
  :service_instance => service_instance,
33
- :recursive? => recursive,
35
+ :recursive? => recursive,
34
36
  :delete => delete
35
37
  )
36
- rest_post("#{BaseRoute}/uninstall", post_body)
38
+ response = rest_post("#{BaseRoute}/uninstall", post_body)
37
39
 
38
- ClientModuleDir.rm_f(args[:directory_path]) if args[:purge]
40
+ ClientModuleDir.rm_f(path) if args[:purge]
39
41
 
40
- OsUtil.print_info("DTK module '#{service_instance}' has been uninstalled successfully.")
42
+ info = "DTK module '#{service_instance}' has been uninstalled successfully."
43
+ OsUtil.print_info(info)
44
+ Delete.display_node_info(response.data) if delete
41
45
  end
42
46
  end
43
47
 
48
+
44
49
  end
45
50
  end
46
- end
47
-
48
-
51
+ end
@@ -45,6 +45,7 @@ module DTK::Client
45
45
  @evaluated_data = []
46
46
  @error_data = []
47
47
  @action_data = []
48
+ @footnote = nil
48
49
  end
49
50
  private :initialize
50
51
 
@@ -61,6 +62,7 @@ module DTK::Client
61
62
  data = [data] unless data.kind_of?(Array)
62
63
 
63
64
  print_error_table = opts[:print_error_table]
65
+ @footnote = opts[:footnote]
64
66
 
65
67
 
66
68
  data.each do |data_element|
@@ -158,6 +160,11 @@ module DTK::Client
158
160
  printed << message
159
161
  end
160
162
  end
163
+
164
+ if @footnote
165
+ printf " \n"
166
+ printf "%15s %s\n", "INFO:".colorize(:yellow), @footnote.colorize(:yellow)
167
+ end
161
168
  end
162
169
 
163
170
 
data/lib/client/render.rb CHANGED
@@ -53,6 +53,7 @@ module DTK::Client
53
53
  if render_type == Type::TABLE
54
54
  render_opts = {
55
55
  :print_error_table => opts[:print_error_table],
56
+ :footnote => opts[:footnote]
56
57
  }
57
58
  get_adapter(Type::TABLE, opts).render(ruby_obj, render_opts)
58
59
  elsif ruby_obj.kind_of?(Hash)
@@ -25,6 +25,7 @@ module DTK::Client
25
25
  @semantic_datatype = nil
26
26
  @skip_render = false
27
27
  @render_type = Render::Type::DEFAULT
28
+ @footnote = nil
28
29
  end
29
30
  private :render_attributes_init!
30
31
 
@@ -36,12 +37,13 @@ module DTK::Client
36
37
  render_opts = {
37
38
  :render_type => @render_type,
38
39
  :semantic_datatype => @semantic_datatype,
39
- :print_error_table => @print_error_table
40
+ :print_error_table => @print_error_table,
41
+ :footnote => @footnote
40
42
  }
41
43
  Render.render(data, render_opts)
42
44
  end
43
45
 
44
- def set_render_as_table!(semantic_datatype = nil)
46
+ def set_render_as_table!(semantic_datatype = nil, footnote = nil)
45
47
  return self unless ok?
46
48
 
47
49
  unless semantic_datatype ||= semantic_datatype_in_payload
@@ -53,6 +55,7 @@ module DTK::Client
53
55
  end
54
56
  @semantic_datatype = normalize_semantic_datatype(semantic_datatype)
55
57
  @render_type = Render::Type::TABLE
58
+ @footnote = footnote
56
59
  self
57
60
  end
58
61
 
@@ -44,7 +44,7 @@ module DTK::Client
44
44
 
45
45
  def component_dsl_path
46
46
  matches = directory_file_paths.select { |path| component_dsl_input_files_processor.match?(path) }
47
- raise Error, "Unexpected that there is not a unique component dsl file" if matches.size != 1
47
+ raise Error::MissingDslFile, "Unexpected that there is not a unique component dsl file" if matches.size != 1
48
48
  matches.first
49
49
  end
50
50
 
@@ -96,6 +96,31 @@ module DTK::Client
96
96
  nil
97
97
  end
98
98
 
99
+ def self.gem_list
100
+ `gem list`.split("\n")
101
+ end
102
+
103
+ def self.gem_names_versions_hash
104
+ name_version_hash = {}
105
+ gem_list.each do |gem|
106
+ if gem_match = gem.match(/(^.*)\((.*)\)/)
107
+ name = gem_match[1].strip
108
+ versions = (gem_match[2]||'').split(',')
109
+ name_version_hash.merge!(name => versions)
110
+ end
111
+ end
112
+ name_version_hash
113
+ end
114
+
115
+ def self.gem_installed?(gem_name, gem_version = nil)
116
+ gems_hash = gem_names_versions_hash
117
+ if gem_version
118
+ (gems_hash[gem_name]||[]).include?(gem_version)
119
+ else
120
+ gems_hash.keys.include?(gem_name)
121
+ end
122
+ end
123
+
99
124
  private
100
125
 
101
126
  def self.genv(name)
@@ -0,0 +1,180 @@
1
+ module DTK::Puppet
2
+ class ParseStructure < Hash
3
+ def initialize(ast_item = nil, _opts = {})
4
+ return super() if ast_item.nil?
5
+ end
6
+
7
+ #### used in generate_meta
8
+ def config_agent_type
9
+ :puppet
10
+ end
11
+
12
+ def render_hash_form(module_name)
13
+ rendered_hash = {}
14
+
15
+ self[:children].each do |child|
16
+ name = child['name'].gsub("#{module_name}::", '')
17
+ type = child['type']
18
+ type_name = child['name']
19
+ attributes = nil
20
+
21
+ attributes = process_attributes(child['attributes']) if child['attributes']
22
+ actions = calculate_action(type, type_name)
23
+
24
+ child_name = name.gsub('::', '_')
25
+ child_hash = { child_name => {} }
26
+
27
+ child_hash[child_name].merge!('attributes' => attributes) if attributes
28
+ child_hash[child_name].merge!('actions' => actions)
29
+
30
+ rendered_hash.merge!(child_hash)
31
+ end
32
+
33
+ rendered_hash
34
+ end
35
+
36
+ def process_attributes(attributes)
37
+ processed_atttibutes = {}
38
+ attributes.each do |attr|
39
+ attr_name = attr['name']
40
+ attr_type = attr['type']
41
+ attr_hash = { attr_name => { 'type' => attr_type } }
42
+
43
+ if required = attr['required']
44
+ attr_hash[attr_name].merge!('required' => required)
45
+ end
46
+
47
+ processed_atttibutes.merge!(attr_hash)
48
+ end
49
+
50
+ processed_atttibutes
51
+ end
52
+
53
+ def remove_quotations(str)
54
+ if str.starts_with?('"')
55
+ str = str.slice(1..-1)
56
+ end
57
+ if str.ends_with?('"')
58
+ str = str.slice(0..-2)
59
+ end
60
+ end
61
+
62
+ def calculate_action(type, type_name)
63
+ { 'create' => { "puppet_#{type}" => type_name } }
64
+ end
65
+
66
+ def string_to_boolean(string)
67
+ if string.to_s == 'true'
68
+ true
69
+ elsif string.to_s == 'false'
70
+ false
71
+ end
72
+ end
73
+
74
+ def self.create(ast_obj, opts = {})
75
+ new(ast_obj, opts)
76
+ end
77
+
78
+ TPS = [:hostclass, :definition]
79
+ class TopPS < self
80
+ def initialize(ast_array = nil, opts = {})
81
+ self[:children] = []
82
+ add_children(ast_array, opts)
83
+ super
84
+ end
85
+
86
+ def add_children(ast_array, opts = {})
87
+ return unless ast_array
88
+
89
+ ast_array.instantiate('').each do |ast_item|
90
+ ast_item_type = ast_item.type
91
+ child =
92
+ if TPS.include?(ast_item_type)
93
+ ComponentPS.create(ast_item, opts)
94
+ else
95
+ fail DTK::Client::Error.new("Unexpected top level ast type (#{ast_item.class})")
96
+ end
97
+ self[:children] << child if child
98
+ end
99
+ end
100
+ end
101
+
102
+ class ComponentPS < self
103
+ def initialize(ast_item, opts = {})
104
+ ast_item_type = ast_item.type
105
+ type =
106
+ case ast_item_type
107
+ when :hostclass
108
+ 'class'
109
+ when :definition
110
+ 'definition'
111
+ else
112
+ fail DTK::Client::Error.new('unexpected type for ast_item')
113
+ end
114
+
115
+ self['type'] = type
116
+ self['name'] = ast_item.name
117
+ attributes = []
118
+
119
+ attributes << AttributePS.create_name_attribute if ast_item_type == :definition
120
+ (ast_item.arguments || []).each { |arg| attributes << AttributePS.create(arg, opts) }
121
+
122
+ self['attributes'] = attributes unless attributes.empty?
123
+ super
124
+ end
125
+ end
126
+
127
+ AttrTypes = {
128
+ Puppet::Pops::Model::LiteralHash => 'hash',
129
+ Puppet::Pops::Model::VariableExpression => 'string',
130
+ Puppet::Pops::Model::LiteralUndef => 'string',
131
+ Puppet::Pops::Model::LiteralBoolean => 'boolean',
132
+ Puppet::Pops::Model::LiteralString => 'string',
133
+ Puppet::Pops::Model::LiteralInteger => 'integer',
134
+ Puppet::Pops::Model::LiteralList => 'array',
135
+ Puppet::Pops::Model::ConcatenatedString => 'string',
136
+ Puppet::Pops::Model::QualifiedName => 'string'
137
+ }
138
+ class AttributePS < self
139
+ def initialize(arg, opts = {})
140
+ self['name'] = arg[0]
141
+
142
+ if arg_1 = arg[1]
143
+ self['type'] = type?(arg_1)
144
+ self['required'] = opts[:required] if opts.key?(:required)
145
+
146
+ unless def_value(arg_1)
147
+ self['required'] ||= true
148
+ end
149
+ else
150
+ self['type'] = 'string'
151
+ self['required'] = true
152
+ end
153
+
154
+ super
155
+ end
156
+
157
+ def type?(arg)
158
+ if arg_value = arg.value
159
+ AttrTypes[arg_value.class] || 'string'
160
+ else
161
+ 'string'
162
+ end
163
+ end
164
+
165
+ def def_value(default_ast_obj)
166
+ # if arg_value = default_ast_obj.value
167
+ # default_ast_obj.source_text unless IgnoreValues.include?(arg_value.class)
168
+ # else
169
+ default_ast_obj.source_text
170
+ # end
171
+ end
172
+ # IgnoreValues = [Puppet::Pops::Model::VariableExpression]
173
+
174
+ def self.create_name_attribute
175
+ new(['name'], 'required' => true)
176
+ end
177
+ end
178
+
179
+ end
180
+ end
@@ -0,0 +1,92 @@
1
+ #
2
+ # Copyright (C) 2010-2016 dtk contributors
3
+ #
4
+ # This file is part of the dtk project.
5
+ #
6
+ # Licensed under the Apache License, Version 2.0 (the "License");
7
+ # you may not use this file except in compliance with the License.
8
+ # You may obtain a copy of the License at
9
+ #
10
+ # http://www.apache.org/licenses/LICENSE-2.0
11
+ #
12
+ # Unless required by applicable law or agreed to in writing, software
13
+ # distributed under the License is distributed on an "AS IS" BASIS,
14
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ # See the License for the specific language governing permissions and
16
+ # limitations under the License.
17
+ #
18
+ module DTK
19
+ module Puppet
20
+ class Parser
21
+ def self.parse(argv)
22
+ parse_puppet_module_directory
23
+ end
24
+
25
+ def self.parse_puppet_module_directory
26
+ current_dir = Client::OsUtil.current_dir
27
+ dir_content = Dir.glob("#{current_dir}/**/*")
28
+
29
+ if module_yaml_file = dir_content.find { |path| path =~ /dtk.module.yaml$/ }
30
+ fail DTK::Client::Error::Usage.new("Dtk module file 'dtk.module.yaml' exists already. Please delete it first and execute puppet scaffolding again.")
31
+ end
32
+
33
+ metadata_file = dir_content.find { |path| path =~ /metadata.json$/ }
34
+ file_content = File.read(metadata_file)
35
+ metadata_hash = JSON.parse(file_content)
36
+
37
+ full_module_name = metadata_hash['name'].gsub('-', '/')
38
+ module_version = metadata_hash['version']
39
+ dependencies = process_metadata_dependencies(metadata_hash['dependencies'])
40
+
41
+ module_hash = {
42
+ 'module' => full_module_name,
43
+ 'version' => module_version
44
+ }
45
+ module_hash.merge!('dependencies' => dependencies) unless dependencies.empty?
46
+
47
+ all_files = dir_content.select { |path| path =~ /manifests.+\.pp$/ }
48
+ if all_files.empty?
49
+ all_files = dir_content.select { |path| path =~ /puppet\/manifests.+\.pp$/ }
50
+ end
51
+
52
+ namespace, module_name = full_module_name.split('/')
53
+
54
+ component_defs = process_manifest_files(all_files, module_name)
55
+ module_hash['component_defs'] = component_defs
56
+
57
+ File.open("#{current_dir}/dtk.module.yaml", 'wb') { |file| file.write(module_hash.to_yaml) }
58
+ DTK::Client::OsUtil.print_info("'dtk.module.yaml' file has been created successfully.")
59
+ end
60
+
61
+ def self.process_manifest_files(files, module_name)
62
+ ret = ParseStructure::TopPS.new()
63
+ parser = ::Puppet::Parser::ParserFactory.parser
64
+
65
+ files.each do |file|
66
+ parser.file = file
67
+ initial_import = parser.parse
68
+
69
+ known_resource_types = ::Puppet::Resource::TypeCollection.new('production')
70
+ known_resource_types.import_ast(initial_import, '')
71
+ krt_code = known_resource_types.hostclass('').code
72
+
73
+ ret.add_children(krt_code)
74
+ end
75
+
76
+ ret.render_hash_form(module_name)
77
+ end
78
+
79
+ def self.process_metadata_dependencies(dependencies)
80
+ dependency_hash = {}
81
+
82
+ if dependencies
83
+ dependencies.each do |dependency|
84
+ dependency_hash.merge!(dependency['name'] => 'master')
85
+ end
86
+ end
87
+
88
+ dependency_hash
89
+ end
90
+ end
91
+ end
92
+ end
data/lib/dtk_puppet.rb ADDED
@@ -0,0 +1,24 @@
1
+ #
2
+ # Copyright (C) 2010-2016 dtk contributors
3
+ #
4
+ # This file is part of the dtk project.
5
+ #
6
+ # Licensed under the Apache License, Version 2.0 (the "License");
7
+ # you may not use this file except in compliance with the License.
8
+ # You may obtain a copy of the License at
9
+ #
10
+ # http://www.apache.org/licenses/LICENSE-2.0
11
+ #
12
+ # Unless required by applicable law or agreed to in writing, software
13
+ # distributed under the License is distributed on an "AS IS" BASIS,
14
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ # See the License for the specific language governing permissions and
16
+ # limitations under the License.
17
+ #
18
+ module DTK
19
+ module Puppet
20
+ require_relative('dtk_puppet/parser')
21
+ require_relative('dtk_puppet/parse_structure')
22
+ require_relative('client/error')
23
+ end
24
+ end