terraspace 0.6.7 → 0.6.8

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 790cbc55c399a3130eaaaa9e1e3af636a2b182cb28c2ca008e14a48d75883e47
4
- data.tar.gz: 72d05ffb527f163d2b3be47542b77764ddbc599858e6dde6381058e992bc531c
3
+ metadata.gz: ac0b4566fae8a6be4cfb7907e60d1d0ec3cdf4f7426989a68e5a7c22c55b4cc5
4
+ data.tar.gz: 66bd6807da803a3891ba2d78b5e21e5dcf0af2e8a1ed303ceb8c9e70c6916ea7
5
5
  SHA512:
6
- metadata.gz: a598f6c5e693d42c113a5aac0f4d2e63c41821a2414095ed65415fa6b11ab1636ce48d6a98ada24557c6b685642f1ac420fc9850544bd1cbda80e3de91036d48
7
- data.tar.gz: f0a0955bbc1f7846e855141514a69b0aaffc81283081a5a90384fb85e4ec7946a65f19fa1dc3ff5df0e7c9f656ac5563fecca2c8a1a1959c83fa29d9daeae4bd
6
+ metadata.gz: d14b3c79add9cf2075c27682ad466f4afeb474a21943868d3dc1260afd129d127387e0089fa44e08e695bb5c28080b6dcbfdcd6774c3fff244782a50dd8a4f7c
7
+ data.tar.gz: c54ed8c38625bccd2ce424a18b70b4ca9198a4921bf10a57e452e0c6d7b1f2ae500f9565ba123cbaa071d7fec9767fa1d263e8a315dc1427ea5d983c8309c790
data/CHANGELOG.md CHANGED
@@ -3,6 +3,9 @@
3
3
  All notable changes to this project will be documented in this file.
4
4
  This project *loosely tries* to adhere to [Semantic Versioning](http://semver.org/), even before v1.0.
5
5
 
6
+ ## [0.6.8] - 2021-05-07
7
+ - [#110](https://github.com/boltops-tools/terraspace/pull/110) fix popen deadlock with large amounts of output [#97](https://github.com/boltops-tools/terraspace/pull/97) Terraspace hangs when TF_LOG=TRACE environment variable exists #97
8
+
6
9
  ## [0.6.7] - 2021-05-05
7
10
  - [#108](https://github.com/boltops-tools/terraspace/pull/108) provide runner context to terraspace hook
8
11
 
@@ -30,16 +30,16 @@ module Terraspace::Hooks
30
30
  logger.warn "WARN: execute option not set for hook: #{@hook.inspect}"
31
31
  end
32
32
 
33
- if executor
34
- meth = executor.method(:call)
35
- case meth.arity
36
- when 0
37
- executor.call # backwards compatibility
38
- when 1
39
- executor.call(self)
40
- else
41
- raise "The #{executor} call method definition has been more than 1 arguments and is not supported"
42
- end
33
+ return unless executor
34
+
35
+ meth = executor.method(:call)
36
+ case meth.arity
37
+ when 0
38
+ executor.call # backwards compatibility
39
+ when 1
40
+ executor.call(self)
41
+ else
42
+ raise "The #{executor} call method definition has been more than 1 arguments and is not supported"
43
43
  end
44
44
  end
45
45
  end
@@ -29,70 +29,82 @@ module Terraspace
29
29
 
30
30
  def popen3(env)
31
31
  Open3.popen3(env, @command, chdir: @mod.cache_dir) do |stdin, stdout, stderr, wait_thread|
32
- mimic_terraform_input(stdin, stdout)
33
- while out = stdout.gets
34
- terraform_to_stdout(out)
35
- end
36
-
37
- while err = stderr.gets
38
- @error ||= Error.new
39
- @error.lines << err # aggregate all error lines
40
- unless @error.known?
41
- # Sometimes may print a "\e[31m\n" which like during dependencies fetcher init
42
- # suppress it so dont get a bunch of annoying "newlines"
43
- next if err == "\e[31m\n" && @options[:suppress_error_color]
44
- logger.error(err)
45
- end
46
- end
47
-
32
+ handle_streams(stdin, stdout, stderr)
48
33
  status = wait_thread.value.exitstatus
49
34
  exit_status(status)
50
35
  end
51
36
  end
52
37
 
53
- def exit_status(status)
54
- return if status == 0
38
+ BLOCK_SIZE = Integer(ENV['TS_BUFFER_BLOCK_SIZE'] || 102400)
39
+ BUFFER_TIMEOUT = Integer(ENV['TS_BUFFER_TIMEOUT'] || 3600) # 3600s = 1h
40
+ def handle_streams(stdin, stdout, stderr)
41
+ files = [stdout, stderr]
42
+ # note: t=0 and t=nil means no timeout. See: https://bit.ly/2PURlCX
43
+ t = BUFFER_TIMEOUT.to_i unless BUFFER_TIMEOUT.nil?
44
+ Timeout::timeout(t) do
45
+ until all_eof?(files) do
46
+ ready = IO.select(files, nil, nil, 0.1)
47
+ next unless ready
55
48
 
56
- exit_on_fail = @options[:exit_on_fail].nil? ? true : @options[:exit_on_fail]
57
- if @error && @error.known?
58
- raise @error.instance
59
- elsif exit_on_fail
60
- logger.error "Error running command: #{@command}".color(:red)
61
- exit status
49
+ readable = ready[0]
50
+ readable.each do |f|
51
+ buffer = f.read_nonblock(BLOCK_SIZE, exception: false)
52
+ next unless buffer
53
+
54
+ lines = buffer.split("\n")
55
+ lines.each do |line|
56
+ terraform_to_stdout(line)
57
+ handle_input(stdin, line)
58
+ end
59
+ end
60
+ end
62
61
  end
63
62
  end
64
63
 
64
+ def all_eof?(files)
65
+ files.find { |f| !f.eof }.nil?
66
+ end
67
+
65
68
  # Terraform doesnt seem to stream the line that prompts with "Enter a value:" when using Open3.popen3
66
69
  # Hack around it by mimicking the "Enter a value:" prompt
67
70
  #
68
71
  # Note: system does stream the prompt but using Open3.popen3 so we can capture output to save to logs.
69
- def mimic_terraform_input(stdin, stdout)
70
- shown = false
72
+ def handle_input(stdin, line)
73
+ # stdout doesnt seem to flush and show "Enter a value: " look for earlier output
71
74
  patterns = [
72
75
  "Only 'yes' will be accepted", # prompt for apply. can happen on apply
73
76
  "\e[0m\e[1mvar.", # prompts for variable input. can happen on plan or apply. looking for bold marker also in case "var." shows up somewhere else
74
77
  ]
75
- while out = stdout.gets
76
- terraform_to_stdout(out) unless shown && out.include?("Enter a value:")
77
- shown = false if out.include?("Enter a value:") # reset shown in case of multiple input prompts
78
+ if patterns.any? { |pattern| line.include?(pattern) }
79
+ print "\n Enter a value: ".bright
80
+ stdin.write_nonblock($stdin.gets)
81
+ end
82
+ end
78
83
 
79
- # Sometimes stdout doesnt flush and show "Enter a value: ", so mimic it
80
- if patterns.any? { |pattern| out.include?(pattern) }
81
- print " Enter a value: ".bright
82
- shown = true
83
- stdin.write_nonblock($stdin.gets)
84
- end
84
+ def exit_status(status)
85
+ return if status == 0
86
+
87
+ exit_on_fail = @options[:exit_on_fail].nil? ? true : @options[:exit_on_fail]
88
+ if @error && @error.known?
89
+ raise @error.instance
90
+ elsif exit_on_fail
91
+ logger.error "Error running command: #{@command}".color(:red)
92
+ exit status
85
93
  end
86
94
  end
87
95
 
88
- # Allows piping to jq. IE:
89
- # terraspace show demo --json | jq
90
- def terraform_to_stdout(out)
91
- # so terraform output goes stdout
96
+ def terraform_to_stdout(line)
97
+ prompted = line.include?('Enter a value')
98
+ @prompt_shown ||= prompted
99
+ return if @prompt_shown && prompted
100
+
101
+ # Terraspace logger has special stdout method so original terraform output
102
+ # can be piped to jq. IE:
103
+ # terraspace show demo --json | jq
92
104
  if logger.respond_to?(:stdout) && !@options[:log_to_stderr]
93
- logger.stdout(out)
105
+ logger.stdout(line)
94
106
  else
95
- logger.info(out)
107
+ logger.info(line)
96
108
  end
97
109
  end
98
110
  end
@@ -1,3 +1,3 @@
1
1
  module Terraspace
2
- VERSION = "0.6.7"
2
+ VERSION = "0.6.8"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: terraspace
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.6.7
4
+ version: 0.6.8
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tung Nguyen
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2021-05-05 00:00:00.000000000 Z
11
+ date: 2021-05-07 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activesupport