puppet 3.7.4-x64-mingw32 → 3.7.5-x64-mingw32

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of puppet might be problematic. Click here for more details.

Files changed (115) hide show
  1. checksums.yaml +7 -0
  2. data/CONTRIBUTING.md +11 -6
  3. data/ext/build_defaults.yaml +2 -2
  4. data/ext/systemd/puppet.service +1 -0
  5. data/lib/hiera/puppet_function.rb +71 -0
  6. data/lib/puppet.rb +12 -0
  7. data/lib/puppet/application/device.rb +22 -5
  8. data/lib/puppet/daemon.rb +13 -4
  9. data/lib/puppet/defaults.rb +27 -4
  10. data/lib/puppet/environments.rb +1 -1
  11. data/lib/puppet/error.rb +4 -0
  12. data/lib/puppet/functions.rb +118 -65
  13. data/lib/puppet/functions/assert_type.rb +5 -5
  14. data/lib/puppet/functions/each.rb +12 -12
  15. data/lib/puppet/functions/epp.rb +3 -4
  16. data/lib/puppet/functions/filter.rb +12 -12
  17. data/lib/puppet/functions/hiera.rb +29 -0
  18. data/lib/puppet/functions/hiera_array.rb +34 -0
  19. data/lib/puppet/functions/hiera_hash.rb +36 -0
  20. data/lib/puppet/functions/hiera_include.rb +50 -0
  21. data/lib/puppet/functions/inline_epp.rb +2 -3
  22. data/lib/puppet/functions/map.rb +12 -12
  23. data/lib/puppet/functions/reduce.rb +6 -6
  24. data/lib/puppet/functions/scanf.rb +3 -3
  25. data/lib/puppet/functions/slice.rb +10 -9
  26. data/lib/puppet/functions/with.rb +3 -4
  27. data/lib/puppet/graph/simple_graph.rb +5 -5
  28. data/lib/puppet/metatype/manager.rb +1 -1
  29. data/lib/puppet/node/environment.rb +1 -1
  30. data/lib/puppet/parser/ast/arithmetic_operator.rb +1 -1
  31. data/lib/puppet/parser/ast/collexpr.rb +1 -1
  32. data/lib/puppet/parser/compiler.rb +3 -3
  33. data/lib/puppet/parser/functions/create_resources.rb +1 -9
  34. data/lib/puppet/parser/functions/defined.rb +1 -1
  35. data/lib/puppet/parser/functions/hiera.rb +20 -11
  36. data/lib/puppet/parser/functions/hiera_array.rb +23 -13
  37. data/lib/puppet/parser/functions/hiera_hash.rb +25 -15
  38. data/lib/puppet/parser/functions/hiera_include.rb +20 -9
  39. data/lib/puppet/parser/functions/lookup.rb +1 -1
  40. data/lib/puppet/parser/functions/realize.rb +1 -1
  41. data/lib/puppet/parser/functions/scanf.rb +21 -12
  42. data/lib/puppet/parser/parser_factory.rb +2 -2
  43. data/lib/puppet/parser/relationship.rb +1 -1
  44. data/lib/puppet/parser/scope.rb +34 -7
  45. data/lib/puppet/pops.rb +2 -0
  46. data/lib/puppet/pops/binder/lookup.rb +24 -7
  47. data/lib/puppet/pops/binder/producers.rb +2 -2
  48. data/lib/puppet/pops/evaluator/closure.rb +1 -1
  49. data/lib/puppet/pops/evaluator/evaluator_impl.rb +109 -17
  50. data/lib/puppet/pops/evaluator/puppet_proc.rb +69 -0
  51. data/lib/puppet/pops/evaluator/runtime3_converter.rb +175 -0
  52. data/lib/puppet/pops/evaluator/runtime3_support.rb +15 -128
  53. data/lib/puppet/pops/functions/dispatch.rb +21 -17
  54. data/lib/puppet/pops/functions/dispatcher.rb +3 -3
  55. data/lib/puppet/pops/functions/function.rb +46 -14
  56. data/lib/puppet/pops/issues.rb +2 -2
  57. data/lib/puppet/pops/model/model_label_provider.rb +1 -1
  58. data/lib/puppet/pops/parser/egrammar.ra +2 -0
  59. data/lib/puppet/pops/parser/eparser.rb +732 -724
  60. data/lib/puppet/pops/parser/heredoc_support.rb +1 -1
  61. data/lib/puppet/pops/parser/lexer2.rb +20 -22
  62. data/lib/puppet/pops/types/class_loader.rb +1 -1
  63. data/lib/puppet/pops/types/type_calculator.rb +104 -37
  64. data/lib/puppet/pops/types/type_factory.rb +1 -1
  65. data/lib/puppet/pops/types/types.rb +4 -1
  66. data/lib/puppet/pops/types/types_meta.rb +2 -2
  67. data/lib/puppet/pops/validation/checker4_0.rb +5 -3
  68. data/lib/puppet/provider/service/systemd.rb +1 -0
  69. data/lib/puppet/provider/yumrepo/inifile.rb +4 -1
  70. data/lib/puppet/resource.rb +3 -2
  71. data/lib/puppet/resource/catalog.rb +3 -2
  72. data/lib/puppet/resource/type.rb +1 -1
  73. data/lib/puppet/settings/environment_conf.rb +12 -4
  74. data/lib/puppet/type/package.rb +23 -13
  75. data/lib/puppet/util/autoload.rb +7 -7
  76. data/lib/puppet/util/errors.rb +4 -2
  77. data/lib/puppet/util/network_device/config.rb +5 -0
  78. data/lib/puppet/version.rb +1 -1
  79. data/lib/puppetx.rb +2 -2
  80. data/spec/fixtures/unit/pops/loaders/loaders/mix_4x_and_3x_functions/usee/lib/puppet/parser/functions/callee.rb +8 -0
  81. data/spec/fixtures/unit/pops/loaders/loaders/mix_4x_and_3x_functions/usee/lib/puppet/parser/functions/callee_ws.rb +8 -0
  82. data/spec/fixtures/unit/pops/loaders/loaders/mix_4x_and_3x_functions/usee/metadata.json +9 -0
  83. data/spec/fixtures/unit/pops/loaders/loaders/mix_4x_and_3x_functions/user/lib/puppet/functions/user/caller.rb +5 -0
  84. data/spec/fixtures/unit/pops/loaders/loaders/mix_4x_and_3x_functions/user/lib/puppet/functions/user/caller_ws.rb +12 -0
  85. data/spec/fixtures/unit/pops/loaders/loaders/mix_4x_and_3x_functions/user/metadata.json +9 -0
  86. data/spec/integration/parser/environment_spec.rb +47 -0
  87. data/spec/integration/parser/future_compiler_spec.rb +11 -6
  88. data/spec/unit/application/device_spec.rb +52 -14
  89. data/spec/unit/daemon_spec.rb +0 -2
  90. data/spec/unit/environments_spec.rb +2 -2
  91. data/spec/unit/functions/assert_type_spec.rb +4 -25
  92. data/spec/unit/functions/hiera_spec.rb +127 -0
  93. data/spec/unit/functions/with_spec.rb +9 -4
  94. data/spec/unit/functions4_spec.rb +98 -35
  95. data/spec/unit/hiera/backend/puppet_backend_spec.rb +1 -1
  96. data/spec/unit/parser/functions/create_resources_spec.rb +2 -2
  97. data/spec/unit/parser/functions/defined_spec.rb +5 -0
  98. data/spec/unit/parser/functions/lookup_spec.rb +5 -1
  99. data/spec/unit/parser/functions/scanf_spec.rb +30 -0
  100. data/spec/unit/parser/scope_spec.rb +5 -0
  101. data/spec/unit/pops/binder/injector_spec.rb +1 -1
  102. data/spec/unit/pops/evaluator/evaluating_parser_spec.rb +33 -5
  103. data/spec/unit/pops/loaders/loaders_spec.rb +22 -1
  104. data/spec/unit/pops/parser/lexer2_spec.rb +28 -16
  105. data/spec/unit/pops/parser/parse_heredoc_spec.rb +21 -0
  106. data/spec/unit/pops/types/type_calculator_spec.rb +141 -19
  107. data/spec/unit/pops/types/type_factory_spec.rb +2 -2
  108. data/spec/unit/pops/validator/validator_spec.rb +25 -3
  109. data/spec/unit/provider/service/systemd_spec.rb +20 -4
  110. data/spec/unit/provider/user/hpux_spec.rb +1 -1
  111. data/spec/unit/provider/yumrepo/inifile_spec.rb +1 -0
  112. data/spec/unit/settings/environment_conf_spec.rb +12 -1
  113. data/spec/unit/type/package_spec.rb +0 -20
  114. data/spec/unit/util/network_device/config_spec.rb +6 -0
  115. metadata +3422 -3419
@@ -64,7 +64,7 @@ module Puppet::Pops::Parser::HeredocSupport
64
64
  # and it should start scanning after the first found \n (or if not found == error).
65
65
 
66
66
  if ctx[:newline_jump]
67
- scn.pos = lexing_context[:newline_jump]
67
+ scn.pos = ctx[:newline_jump]
68
68
  else
69
69
  scn.scan_until(/\n/) || lex_error("Heredoc without any following lines of text")
70
70
  end
@@ -160,9 +160,9 @@ class Puppet::Pops::Parser::Lexer2
160
160
  # a letter a-z and may not contain dashes (\w includes letters, digits and _).
161
161
  #
162
162
  PATTERN_CLASSREF = %r{((::){0,1}[A-Z][\w]*)+}
163
- PATTERN_NAME = %r{((::)?[a-z][\w]*)(::[a-z][\w]*)*}
163
+ PATTERN_NAME = %r{^((::)?[a-z][\w]*)(::[a-z][\w]*)*$}
164
164
 
165
- PATTERN_BARE_WORD = %r{[a-z_](?:[\w-]*[\w])?}
165
+ PATTERN_BARE_WORD = %r{((?:::){0,1}(?:[a-z_](?:[\w-]*[\w])?))+}
166
166
 
167
167
  PATTERN_DOLLAR_VAR = %r{\$(::)?(\w+::)*\w+}
168
168
  PATTERN_NUMBER = %r{\b(?:0[xX][0-9A-Fa-f]+|0?\d+(?:\.\d+)?(?:[eE]-?\d+)?)\b}
@@ -536,10 +536,13 @@ class Puppet::Pops::Parser::Lexer2
536
536
  lex_error("Illegal fully qualified class reference")
537
537
  end
538
538
  else
539
- # NAME or error
540
- value = scn.scan(PATTERN_NAME)
539
+ value = scn.scan(PATTERN_BARE_WORD)
541
540
  if value
542
- emit_completed([:NAME, value.freeze, scn.pos-before], before)
541
+ if value =~ PATTERN_NAME
542
+ emit_completed([:NAME, value.freeze, scn.pos-before], before)
543
+ else
544
+ emit_completed([:WORD, value.freeze, scn.pos - before], before)
545
+ end
543
546
  else
544
547
  # move to faulty position ('::' was ok)
545
548
  scn.pos = scn.pos + 2
@@ -580,25 +583,20 @@ class Puppet::Pops::Parser::Lexer2
580
583
 
581
584
  when 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm',
582
585
  'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', '_'
583
- value = scn.scan(PATTERN_NAME)
584
- # NAME or false start because followed by hyphen(s), underscore or word
585
- if value && !scn.match?(/^-+\w/)
586
+
587
+ value = scn.scan(PATTERN_BARE_WORD)
588
+ if value && value =~ PATTERN_NAME
586
589
  emit_completed(KEYWORDS[value] || [:NAME, value.freeze, scn.pos - before], before)
590
+ elsif value
591
+ emit_completed([:WORD, value.freeze, scn.pos - before], before)
587
592
  else
588
- # Restart and check entire pattern (for ease of detecting non allowed trailing hyphen)
589
- scn.pos = before
590
- value = scn.scan(PATTERN_BARE_WORD)
591
- # If the WORD continues with :: it must be a correct fully qualified name
592
- if value && !(fully_qualified = scn.match?(/::/))
593
- emit_completed([:WORD, value.freeze, scn.pos - before], before)
593
+ # move to faulty position ([a-z_] was ok)
594
+ scn.pos = scn.pos + 1
595
+ fully_qualified = scn.match?(/::/)
596
+ if fully_qualified
597
+ lex_error("Illegal fully qualified name")
594
598
  else
595
- # move to faulty position ([a-z_] was ok)
596
- scn.pos = scn.pos + 1
597
- if fully_qualified
598
- lex_error("Illegal fully qualified name")
599
- else
600
- lex_error("Illegal name or bare word")
601
- end
599
+ lex_error("Illegal name or bare word")
602
600
  end
603
601
  end
604
602
 
@@ -685,7 +683,7 @@ class Puppet::Pops::Parser::Lexer2
685
683
  true
686
684
 
687
685
  # Operands (that can be followed by DIV (even if illegal in grammar)
688
- when :NAME, :CLASSREF, :NUMBER, :STRING, :BOOLEAN, :DQPRE, :DQMID, :DQPOST, :HEREDOC, :REGEX
686
+ when :NAME, :CLASSREF, :NUMBER, :STRING, :BOOLEAN, :DQPRE, :DQMID, :DQPOST, :HEREDOC, :REGEX, :VARIABLE, :WORD
689
687
  false
690
688
 
691
689
  else
@@ -66,7 +66,7 @@ class Puppet::Pops::Types::ClassLoader
66
66
  when Puppet::Pops::Types::PPatternType ; String
67
67
  when Puppet::Pops::Types::PEnumType ; String
68
68
  when Puppet::Pops::Types::PFloatType ; Float
69
- when Puppet::Pops::Types::PNilType ; NilClass
69
+ when Puppet::Pops::Types::PUndefType ; NilClass
70
70
  when Puppet::Pops::Types::PCallableType ; Proc
71
71
  else
72
72
  nil
@@ -197,7 +197,7 @@ class Puppet::Pops::Types::TypeCalculator
197
197
  data_variant.addTypes(@data_hash.copy)
198
198
  data_variant.addTypes(@data_array.copy)
199
199
  data_variant.addTypes(Types::PScalarType.new)
200
- data_variant.addTypes(Types::PNilType.new)
200
+ data_variant.addTypes(Types::PUndefType.new)
201
201
  data_variant.addTypes(@data_tuple_t.copy)
202
202
  @data_variant_t = data_variant
203
203
 
@@ -212,7 +212,7 @@ class Puppet::Pops::Types::TypeCalculator
212
212
  non_empty_string.size_type.to = nil # infinity
213
213
  @non_empty_string_t = non_empty_string
214
214
 
215
- @nil_t = Types::PNilType.new
215
+ @nil_t = Types::PUndefType.new
216
216
  end
217
217
 
218
218
  # Convenience method to get a data type for comparisons
@@ -322,7 +322,7 @@ class Puppet::Pops::Types::TypeCalculator
322
322
  when c == Regexp
323
323
  type = Types::PRegexpType.new()
324
324
  when c == NilClass
325
- type = Types::PNilType.new()
325
+ type = Types::PUndefType.new()
326
326
  when c == FalseClass, c == TrueClass
327
327
  type = Types::PBooleanType.new()
328
328
  when c == Class
@@ -430,6 +430,14 @@ class Puppet::Pops::Types::TypeCalculator
430
430
  return x < y ? x <= o && y >= o : y <= o && x >= o
431
431
  end
432
432
 
433
+ # @api private
434
+ def instance_of_PStringType(t, o)
435
+ return false unless o.is_a?(String)
436
+ # true if size compliant
437
+ size_t = t.size_type || @collection_default_size_t
438
+ instance_of_PIntegerType(size_t, o.size)
439
+ end
440
+
433
441
  def instance_of_PTupleType(t, o)
434
442
  return false unless o.is_a?(Array)
435
443
  # compute the tuple's min/max size, and check if that size matches
@@ -463,12 +471,12 @@ class Puppet::Pops::Types::TypeCalculator
463
471
  instance_of(@data_variant_t, o)
464
472
  end
465
473
 
466
- def instance_of_PNilType(t, o)
474
+ def instance_of_PUndefType(t, o)
467
475
  o.nil? || o == :undef
468
476
  end
469
477
 
470
478
  def instance_of_POptionalType(t, o)
471
- instance_of_PNilType(t, o) || instance_of(t.optional_type, o)
479
+ instance_of_PUndefType(t, o) || instance_of(t.optional_type, o)
472
480
  end
473
481
 
474
482
  def instance_of_PVariantType(t, o)
@@ -497,11 +505,11 @@ class Puppet::Pops::Types::TypeCalculator
497
505
  return t.is_a?(Types::PAnyType)
498
506
  end
499
507
 
500
- # Answers if t represents the puppet type PNilType
508
+ # Answers if t represents the puppet type PUndefType
501
509
  # @api public
502
510
  #
503
511
  def is_pnil?(t)
504
- return t.nil? || t.is_a?(Types::PNilType)
512
+ return t.nil? || t.is_a?(Types::PUndefType)
505
513
  end
506
514
 
507
515
  # Answers, 'What is the common type of t1 and t2?'
@@ -787,7 +795,50 @@ class Puppet::Pops::Types::TypeCalculator
787
795
 
788
796
  # @api private
789
797
  def infer_NilClass(o)
790
- Types::PNilType.new()
798
+ Types::PUndefType.new()
799
+ end
800
+
801
+ # @api private
802
+ # @param o [Proc]
803
+ def infer_Proc(o)
804
+ min = 0
805
+ max = 0
806
+ if o.respond_to?(:parameters)
807
+ mapped_types = o.parameters.map do |p|
808
+ param_t = Types::PAnyType.new
809
+ case p[0]
810
+ when :rest
811
+ max = :default
812
+ break param_t
813
+ when :req
814
+ min += 1
815
+ end
816
+ max += 1
817
+ param_t
818
+ end
819
+ else
820
+ # Cannot correctly compute the signature in Ruby 1.8.7 because arity for
821
+ # optional values is screwed up (there is no way to get the upper limit),
822
+ # an optional looks the same as a varargs.
823
+ arity = o.arity
824
+ if arity < 0
825
+ min = -arity - 1
826
+ max = :default # i.e. infinite (which is wrong when there are optional - flaw in 1.8.7)
827
+ else
828
+ min = max = arity
829
+ end
830
+ mapped_types = Array.new(min) { Types::PAnyType.new }
831
+ end
832
+ if min == 0 || min != max
833
+ mapped_types << min
834
+ mapped_types << max
835
+ end
836
+ Types::TypeFactory.callable(*mapped_types)
837
+ end
838
+
839
+ # @api private
840
+ def infer_PuppetProc(o)
841
+ infer_Closure(o.closure)
791
842
  end
792
843
 
793
844
  # Inference of :default as PDefaultType, and all other are Ruby[Symbol]
@@ -831,7 +882,7 @@ class Puppet::Pops::Types::TypeCalculator
831
882
  type = Types::PArrayType.new()
832
883
  type.element_type =
833
884
  if o.empty?
834
- Types::PNilType.new()
885
+ Types::PUndefType.new()
835
886
  else
836
887
  infer_and_reduce_type(o)
837
888
  end
@@ -843,8 +894,8 @@ class Puppet::Pops::Types::TypeCalculator
843
894
  def infer_Hash(o)
844
895
  type = Types::PHashType.new()
845
896
  if o.empty?
846
- ktype = Types::PNilType.new()
847
- etype = Types::PNilType.new()
897
+ ktype = Types::PUndefType.new()
898
+ etype = Types::PUndefType.new()
848
899
  else
849
900
  ktype = infer_and_reduce_type(o.keys())
850
901
  etype = infer_and_reduce_type(o.values())
@@ -871,7 +922,7 @@ class Puppet::Pops::Types::TypeCalculator
871
922
  def infer_set_Array(o)
872
923
  if o.empty?
873
924
  type = Types::PArrayType.new()
874
- type.element_type = Types::PNilType.new()
925
+ type.element_type = Types::PUndefType.new()
875
926
  type.size_type = size_as_type(o)
876
927
  else
877
928
  type = Types::PTupleType.new()
@@ -881,19 +932,33 @@ class Puppet::Pops::Types::TypeCalculator
881
932
  end
882
933
 
883
934
  def infer_set_Hash(o)
884
- type = Types::PHashType.new()
885
935
  if o.empty?
886
- ktype = Types::PNilType.new()
887
- vtype = Types::PNilType.new()
936
+ type = Types::PHashType.new
937
+ type.key_type = Types::PUndefType.new
938
+ type.element_type = Types::PUndefType.new
939
+ type.size_type = size_as_type(o)
888
940
  else
889
- ktype = Types::PVariantType.new()
890
- ktype.types = o.keys.map() {|k| infer_set(k) }
891
- etype = Types::PVariantType.new()
892
- etype.types = o.values.map() {|e| infer_set(e) }
941
+ if o.keys.find {|k| !instance_of_PStringType(@non_empty_string_t, k) }
942
+ type = Types::PHashType.new
943
+ ktype = Types::PVariantType.new
944
+ ktype.types = o.keys.map {|k| infer_set(k) }
945
+ etype = Types::PVariantType.new
946
+ etype.types = o.values.map {|e| infer_set(e) }
947
+ type.key_type = unwrap_single_variant(ktype)
948
+ type.element_type = unwrap_single_variant(etype)
949
+ type.size_type = size_as_type(o)
950
+ else
951
+ elements = []
952
+ o.each_pair do |k,v|
953
+ element = Types::PStructElement.new
954
+ element.name = k
955
+ element.type = infer_set(v)
956
+ elements << element
957
+ end
958
+ type = Types::PStructType.new
959
+ type.elements = elements
960
+ end
893
961
  end
894
- type.key_type = unwrap_single_variant(ktype)
895
- type.element_type = unwrap_single_variant(etype)
896
- type.size_type = size_as_type(o)
897
962
  type
898
963
  end
899
964
 
@@ -917,9 +982,9 @@ class Puppet::Pops::Types::TypeCalculator
917
982
  end
918
983
 
919
984
  # @api private
920
- def assignable_PNilType(t, t2)
985
+ def assignable_PUndefType(t, t2)
921
986
  # Only undef/nil is assignable to nil type
922
- t2.is_a?(Types::PNilType)
987
+ t2.is_a?(Types::PUndefType)
923
988
  end
924
989
 
925
990
  # Anything is assignable to a Unit type
@@ -1013,7 +1078,7 @@ class Puppet::Pops::Types::TypeCalculator
1013
1078
  if args_tuple.size_type
1014
1079
  raise ArgumentError, "Callable tuple may not have a size constraint when used as args"
1015
1080
  end
1016
- # Assume no block was given - i.e. it is nil, and its type is PNilType
1081
+ # Assume no block was given - i.e. it is nil, and its type is PUndefType
1017
1082
  block_t = @nil_t
1018
1083
  if self.class.is_kind_of_callable?(args_tuple.types.last)
1019
1084
  # a split is needed to make it possible to use required, optional, and varargs semantics
@@ -1052,8 +1117,8 @@ class Puppet::Pops::Types::TypeCalculator
1052
1117
  assignable?(callable_t.block_type || @nil_t, @nil_t)
1053
1118
  end
1054
1119
 
1055
- def callable_PNilType(nil_t, callable_t)
1056
- # if callable_t is Optional (or indeed PNilType), this means that 'missing callable' is accepted
1120
+ def callable_PUndefType(nil_t, callable_t)
1121
+ # if callable_t is Optional (or indeed PUndefType), this means that 'missing callable' is accepted
1057
1122
  assignable?(callable_t, nil_t)
1058
1123
  end
1059
1124
 
@@ -1127,22 +1192,23 @@ class Puppet::Pops::Types::TypeCalculator
1127
1192
  # @api private
1128
1193
  #
1129
1194
  def assignable_PStructType(t, t2)
1130
- return true if t == t2 || t.elements.empty? && (t2.is_a?(Types::PHashType))
1131
- h = t.hashed_elements
1132
1195
  if t2.is_a?(Types::PStructType)
1196
+ h = t.hashed_elements
1133
1197
  h2 = t2.hashed_elements
1134
- h.size == h2.size && h.all? {|k, v| assignable?(v, h2[k]) }
1198
+ (h2.keys - h.keys).empty? && h.all? {|k, v| v2 = h2[k]; assignable?(v, v2.nil? ? @nil_t : v2) }
1135
1199
  elsif t2.is_a?(Types::PHashType)
1136
1200
  size_t2 = t2.size_type || @collection_default_size_t
1137
1201
  size_t = Types::PIntegerType.new
1138
- size_t.from = size_t.to = h.size
1202
+ elements = t.elements
1203
+ size_t.from = elements.count {|e| !assignable?(e.type, @nil_t) }
1204
+ size_t.to = elements.size
1139
1205
  # compatible size
1140
1206
  # hash key type must be string of min 1 size
1141
1207
  # hash value t must be assignable to each key
1142
1208
  element_type = t2.element_type
1143
1209
  assignable_PIntegerType(size_t, size_t2) &&
1144
- assignable?(@non_empty_string_t, t2.key_type) &&
1145
- h.all? {|k,v| assignable?(v, element_type) }
1210
+ (size_t2.to == 0 || assignable?(@non_empty_string_t, t2.key_type)) &&
1211
+ elements.all? {|e| assignable?(e.type, element_type) }
1146
1212
  else
1147
1213
  false
1148
1214
  end
@@ -1150,7 +1216,7 @@ class Puppet::Pops::Types::TypeCalculator
1150
1216
 
1151
1217
  # @api private
1152
1218
  def assignable_POptionalType(t, t2)
1153
- return true if t2.is_a?(Types::PNilType)
1219
+ return true if t2.is_a?(Types::PUndefType)
1154
1220
  if t2.is_a?(Types::POptionalType)
1155
1221
  assignable?(t.optional_type, t2.optional_type)
1156
1222
  else
@@ -1364,6 +1430,7 @@ class Puppet::Pops::Types::TypeCalculator
1364
1430
  def assignable_PHashType(t, t2)
1365
1431
  case t2
1366
1432
  when Types::PHashType
1433
+ return true if (t.size_type.nil? || t.size_type.from == 0) && t2.is_the_empty_hash?
1367
1434
  return false unless assignable?(t.key_type, t2.key_type) && assignable?(t.element_type, t2.element_type)
1368
1435
  assignable_PCollectionType(t, t2)
1369
1436
  when Types::PStructType
@@ -1373,10 +1440,10 @@ class Puppet::Pops::Types::TypeCalculator
1373
1440
  size_t = t.size_type || @collection_default_size_t
1374
1441
  min, max = size_t.range
1375
1442
  struct_size = t2.elements.size
1443
+ key_type = t.key_type
1376
1444
  element_type = t.element_type
1377
1445
  ( struct_size >= min && struct_size <= max &&
1378
- assignable?(t.key_type, @non_empty_string_t) &&
1379
- t2.hashed_elements.all? {|k,v| assignable?(element_type, v) })
1446
+ t2.elements.all? {|e| instance_of(key_type, e.name) && assignable?(element_type, e.type) })
1380
1447
  else
1381
1448
  false
1382
1449
  end
@@ -1453,7 +1520,7 @@ class Puppet::Pops::Types::TypeCalculator
1453
1520
  def string_PAnyType(t) ; "Any" ; end
1454
1521
 
1455
1522
  # @api private
1456
- def string_PNilType(t) ; 'Undef' ; end
1523
+ def string_PUndefType(t) ; 'Undef' ; end
1457
1524
 
1458
1525
  # @api private
1459
1526
  def string_PDefaultType(t) ; 'Default' ; end
@@ -264,7 +264,7 @@ module Puppet::Pops::Types::TypeFactory
264
264
  # Creates an instance of the Undef type
265
265
  # @api public
266
266
  def self.undef()
267
- Types::PNilType.new()
267
+ Types::PUndefType.new()
268
268
  end
269
269
 
270
270
  # Creates an instance of the Default type
@@ -344,10 +344,13 @@ module Puppet::Pops
344
344
  self.element_type == o.element_type &&
345
345
  self.size_type == o.size_type
346
346
  end
347
+
348
+ def is_the_empty_hash?
349
+ size_type.is_a?(PIntegerType) && size_type.from == 0 && size_type.to == 0 && key_type.is_a?(PUndefType) && element_type.is_a?(PUndefType)
350
+ end
347
351
  end
348
352
  end
349
353
 
350
-
351
354
  class PRuntimeType < PAnyType
352
355
  module ClassModule
353
356
  def hash
@@ -36,7 +36,7 @@ module Puppet::Pops::Types
36
36
 
37
37
  # @api public
38
38
  #
39
- class PNilType < PAnyType
39
+ class PUndefType < PAnyType
40
40
  end
41
41
 
42
42
 
@@ -212,7 +212,7 @@ module Puppet::Pops::Types
212
212
  has_attr 'title', String
213
213
  end
214
214
 
215
- # Represents a type that accept PNilType instead of the type parameter
215
+ # Represents a type that accept PUndefType instead of the type parameter
216
216
  # required_type - is a short hand for Variant[T, Undef]
217
217
  # @api public
218
218
  #
@@ -478,11 +478,13 @@ class Puppet::Pops::Validation::Checker4_0
478
478
 
479
479
  # Checks that variable is either strictly 0, or a non 0 starting decimal number, or a valid VAR_NAME
480
480
  def check_VariableExpression(o)
481
- # The expression must be a qualified name
482
- if !o.expr.is_a?(Model::QualifiedName)
481
+ # The expression must be a qualified name or an integer
482
+ name_expr = o.expr
483
+ return if name_expr.is_a?(Model::LiteralInteger)
484
+ if !name_expr.is_a?(Model::QualifiedName)
483
485
  acceptor.accept(Issues::ILLEGAL_EXPRESSION, o, :feature => 'name', :container => o)
484
486
  else
485
- # name must be either a decimal value, or a valid NAME
487
+ # name must be either a decimal string value, or a valid NAME
486
488
  name = o.expr.value
487
489
  if name[0,1] =~ /[0-9]/
488
490
  unless name =~ Puppet::Pops::Patterns::NUMERIC_VAR_NAME
@@ -7,6 +7,7 @@ Puppet::Type.type(:service).provide :systemd, :parent => :base do
7
7
 
8
8
  defaultfor :osfamily => [:archlinux]
9
9
  defaultfor :osfamily => :redhat, :operatingsystemmajrelease => "7"
10
+ defaultfor :osfamily => :redhat, :operatingsystem => :fedora, :operatingsystemmajrelease => ["17", "18", "19", "20", "21"]
10
11
 
11
12
  def self.instances
12
13
  i = []