tormanager 0.4.0 → 0.5.0

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
  SHA1:
3
- metadata.gz: f4f5f15e6d06ba9f2ea927a1a09e492cb06fcdb8
4
- data.tar.gz: fcffe0b51611f91a85c4bd17407de5ee364acd98
3
+ metadata.gz: a1d766b2c286eacb7f7efa82f21dc1662e212f4d
4
+ data.tar.gz: 32410bc4be8b53b6b655bb769d670685bf822a98
5
5
  SHA512:
6
- metadata.gz: f781d354d3d9a0ecc9740568c58fe308ae540b18ad63e6162dc46ea92e2dba5d71a0e9a789a79bf4c074c7b9019699ba69a8d034a122ffb33fe6dbd80a385b18
7
- data.tar.gz: 09b546d6a5ce6f314b2de9972a283ae8043167e78988521346c67ea6de6333b0e653308fba1611d5a73366b1416b2b35ea9e687feb362087199c1cff5db216fa
6
+ metadata.gz: a82a54925256086092b0077286a4d550367281dcad947ffbe31aeb022643c215c34042fbf2ab2d75d63f76225d9eb24e8843792446a67a01f49f2116aada385b
7
+ data.tar.gz: f5abb39b3cec9703b81731696d8e9e36f1c3103f65ec47202b2436081e6b445e8b24a517d9b80439f02f1c1e913c82d96098f94dcaf5b8f78d2ef22e1fdcf2bd
data/lib/tormanager.rb CHANGED
@@ -4,3 +4,4 @@ require "tormanager/control"
4
4
  require "tormanager/tor_process"
5
5
  require "tormanager/proxy"
6
6
  require "tormanager/ip_address_control"
7
+ require "tormanager/create_eye_config"
@@ -0,0 +1,27 @@
1
+ module TorManager
2
+ class CreateEyeConfig
3
+ def initialize params={}
4
+ @settings = params
5
+ end
6
+
7
+ def create
8
+ File.open(@settings[:eye_tor_config_path], "w") do |file|
9
+ file.puts read_eye_tor_config_template_and_substitute_keywords
10
+ end
11
+ end
12
+
13
+ private
14
+
15
+ def read_eye_tor_config_template_and_substitute_keywords
16
+ text = File.read(@settings[:eye_tor_config_template])
17
+ eye_tor_config_template_substitution_keywords.each do |keyword|
18
+ text = text.gsub(/\[\[\[#{keyword}\]\]\]/, @settings[keyword.to_sym].to_s)
19
+ end
20
+ text
21
+ end
22
+
23
+ def eye_tor_config_template_substitution_keywords
24
+ @settings.keys.map(&:to_s)
25
+ end
26
+ end
27
+ end
@@ -1,6 +1,8 @@
1
1
  require 'rest-client'
2
2
 
3
3
  module TorManager
4
+ TorUnavailable = Class.new(StandardError)
5
+
4
6
  class IpAddressControl
5
7
  attr_accessor :ip
6
8
 
@@ -24,7 +26,7 @@ module TorManager
24
26
  private
25
27
 
26
28
  def ensure_tor_is_available
27
- raise "Cannot proceed, Tor is not running on port " +
29
+ raise TorUnavailable, "Cannot proceed, Tor is not running on port " +
28
30
  "#{@tor_process.settings[:tor_port]}" unless
29
31
  TorProcess.tor_running_on? port: @tor_process.settings[:tor_port],
30
32
  parent_pid: @tor_process.settings[:parent_pid]
@@ -70,7 +72,7 @@ module TorManager
70
72
 
71
73
  def tor_switch_endpoint
72
74
  Tor::Controller.connect(:port => @tor_process.settings[:control_port]) do |tor|
73
- tor.authenticate("")
75
+ tor.authenticate(@tor_process.settings[:control_password])
74
76
  tor.signal("newnym")
75
77
  sleep 10
76
78
  end
@@ -1,6 +1,8 @@
1
1
  require 'socket'
2
2
 
3
3
  module TorManager
4
+ CannotKillProcess = Class.new(StandardError)
5
+
4
6
  class ProcessHelper
5
7
  class << self
6
8
  def query_process query
@@ -12,14 +14,14 @@ module TorManager
12
14
 
13
15
  def kill_process pids
14
16
  to_array(pids).each do |pid|
15
- try_to_kill pid: pid, attempts: 5
17
+ try_to_kill pid: Integer(pid), attempts: 5
16
18
  end
17
19
  end
18
20
 
19
21
  def process_pid_running? pid
20
22
  begin
21
23
  return false if pid.to_s == ''.freeze
22
- ipid = pid.to_i
24
+ ipid = Integer(pid)
23
25
  return false if ipid <= 0
24
26
  Process.kill(0, ipid)
25
27
  return true
@@ -63,12 +65,12 @@ module TorManager
63
65
  def try_to_kill params={}
64
66
  pid = params.fetch(:pid, nil)
65
67
  return unless pid && process_pid_running?(pid)
66
- params.fetch(:attempts, 5).times do |k|
67
- k < 3 ? Process.kill('TERM', pid) :
68
+ params.fetch(:attempts, 5).times do |i|
69
+ i < 3 ? Process.kill('TERM', pid) :
68
70
  Process.kill('KILL', pid)
69
71
  sleep 0.5
70
72
  break unless process_pid_running? pid
71
- raise "Couldnt kill pid: #{pid}" if k >= 4
73
+ raise CannotKillProcess, "Couldnt kill pid: #{pid}" if i >= 4
72
74
  end
73
75
  end
74
76
  end
@@ -4,6 +4,12 @@ require 'fileutils'
4
4
  require 'securerandom'
5
5
 
6
6
  module TorManager
7
+ Error = Class.new(StandardError)
8
+ TorPortInUse = Class.new(Error)
9
+ TorControlPortInUse = Class.new(Error)
10
+ TorFailedToStart = Class.new(Error)
11
+ TorFailedToStop = Class.new(Error)
12
+
7
13
  class TorProcess
8
14
  attr_accessor :settings
9
15
 
@@ -88,31 +94,29 @@ module TorManager
88
94
  end
89
95
 
90
96
  def tor_port_is_open?
91
- raise "Cannot spawn Tor process as port " +
97
+ raise TorPortInUse, "Cannot spawn Tor process as port " +
92
98
  "#{@settings[:tor_port]} is in use" unless
93
99
  ProcessHelper.port_is_open?(@settings[:tor_port])
94
100
  true
95
101
  end
96
102
 
97
103
  def control_port_is_open?
98
- raise "Cannot spawn Tor process as control port " +
104
+ raise TorControlPortInUse, "Cannot spawn Tor process as control port " +
99
105
  "#{@settings[:control_port]} is in use" unless
100
106
  ProcessHelper.port_is_open?(@settings[:control_port])
101
107
  true
102
108
  end
103
109
 
104
110
  def prepare_tor_start_and_monitor
105
- build_eye_config_from_template
111
+ #build_eye_config_from_template
112
+ eye_config = CreateEyeConfig.new(
113
+ @settings.merge(
114
+ eye_tor_config_path: eye_config_filename))
115
+ eye_config.create
106
116
  make_dirs
107
117
  start_tor_and_monitor
108
118
  end
109
119
 
110
- def build_eye_config_from_template
111
- File.open(eye_config_filename, "w") do |file|
112
- file.puts read_eye_tor_config_template_and_substitute_keywords
113
- end
114
- end
115
-
116
120
  def eye_config_filename
117
121
  @eye_config_filename || File.join(@settings[:log_dir],
118
122
  "tormanager.tor.#{@settings[:tor_port]}.#{Process.pid}.eye.rb")
@@ -122,23 +126,6 @@ module TorManager
122
126
  @eye_app_name || "tormanager-tor-#{@settings[:tor_port]}-#{Process.pid}"
123
127
  end
124
128
 
125
- def read_eye_tor_config_template_and_substitute_keywords
126
- text = File.read(@settings[:eye_tor_config_template])
127
- eye_tor_config_template_substitution_keywords.each do |keyword|
128
- text = text.gsub(/\[\[\[#{keyword}\]\]\]/, @settings[keyword.to_sym].to_s)
129
- end
130
- text
131
- end
132
-
133
- def eye_tor_config_template_substitution_keywords
134
- remove_settings_that_are_not_eye_tor_config_template_keywords(
135
- @settings.keys.map(&:to_s))
136
- end
137
-
138
- def remove_settings_that_are_not_eye_tor_config_template_keywords keywords
139
- keywords - ['eye_tor_config_template', 'control_password', 'dont_remove_tor_config']
140
- end
141
-
142
129
  def make_dirs
143
130
  [@settings[:log_dir], @settings[:pid_dir],
144
131
  @settings[:tor_data_dir]].each do |path|
@@ -159,7 +146,7 @@ module TorManager
159
146
  application: eye_app_name,
160
147
  process: 'tor') == 'up'
161
148
  sleep 2
162
- raise "Tor didnt start up after 20 seconds! See log: " +
149
+ raise TorFailedToStart, "Tor didnt start up after 20 seconds! See log: " +
163
150
  "#{File.join(@settings[:log_dir],
164
151
  eye_app_name + ".log")}" if i >= 9
165
152
  end
@@ -172,7 +159,8 @@ module TorManager
172
159
  process: 'tor')
173
160
  break if ['unknown','unmonitored'].include?(tor_status)
174
161
  sleep 2
175
- raise "Tor didnt stop after 20 seconds! Last status: #{tor_status} See log: " +
162
+ raise TorFailedToStop,
163
+ "Tor didnt stop after 20 seconds! Last status: #{tor_status} See log: " +
176
164
  "#{File.join(@settings[:log_dir],
177
165
  eye_app_name + ".log")}" if i >= 9
178
166
  end
@@ -1,3 +1,3 @@
1
1
  module TorManager
2
- VERSION = "0.4.0"
2
+ VERSION = "0.5.0"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: tormanager
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.0
4
+ version: 0.5.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - joshweir
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2017-08-14 00:00:00.000000000 Z
11
+ date: 2017-08-19 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -155,9 +155,9 @@ files:
155
155
  - bin/setup
156
156
  - lib/tormanager.rb
157
157
  - lib/tormanager/control.rb
158
+ - lib/tormanager/create_eye_config.rb
158
159
  - lib/tormanager/eye/eye.tor.test.rb
159
160
  - lib/tormanager/eye/sugar.rb
160
- - lib/tormanager/eye/tor.god.rb
161
161
  - lib/tormanager/eye/tor.template.eye.rb
162
162
  - lib/tormanager/ip_address_control.rb
163
163
  - lib/tormanager/process_helper.rb
@@ -1,105 +0,0 @@
1
- require 'fileutils'
2
-
3
- opts = {}
4
- opts[:parent_id] = ARGV[0]
5
- opts[:tor_port] = ARGV[1] || 9050
6
- opts[:control_port] = ARGV[2] || 50500
7
- opts[:pid_dir] = ARGV[3] || "/tmp"
8
- opts[:log_dir] = ARGV[4] || "/tmp"
9
- opts[:tor_data_dir] = ARGV[5] || "/tmp/tor_data/"
10
- opts[:tor_new_circuit_period] = ARGV[6] || 60
11
- opts[:max_tor_memory_usage_mb] = ARGV[7] || 200
12
- opts[:max_tor_cpu_percentage] = ARGV[8] || 10
13
- opts[:max_tor_memory_usage_times] = [3,5]
14
- opts[:max_tor_cpu_percentage_times] = [3,5]
15
-
16
- raise 'parent_id is required' unless opts[:parent_id]
17
-
18
- module God
19
- module Behaviors
20
- class WaitBehavior < Behavior
21
- attr_accessor :delay
22
-
23
- def after_start
24
- sleep delay.to_i if delay.to_i > 0
25
- end
26
- end
27
- end
28
- end
29
-
30
- God.watch do |w|
31
- the_name = "tormanager-tor-#{opts[:tor_port]}-#{opts[:parent_id]}"
32
- w.name = the_name
33
- w.start = "tor --SocksPort #{opts[:tor_port]} --ControlPort #{opts[:control_port]} " +
34
- "--CookieAuthentication 0 --HashedControlPassword \"16:3E49D6163CCA95F2605B339" +
35
- "E07F753C8F567DE4200E33FDF4CC6B84E44\" --NewCircuitPeriod " +
36
- "#{opts[:tor_new_circuit_period]} --DataDirectory " +
37
- File.join(opts[:tor_data_dir], opts[:tor_port]) + " --Log \"notice syslog\""
38
- #w.pid_file = File.join(opts[:pid_dir], "#{the_name}.pid")
39
- #w.log = File.join(opts[:log_dir], "#{the_name}.log") if opts[:log_dir].length > 0
40
- w.keepalive
41
-
42
- # clean pid files before start if necessary
43
- w.behavior(:clean_pid_file)
44
- w.behavior(:wait_behavior) do |b|
45
- b.delay = 10
46
- end
47
-
48
- =begin
49
- # determine the state on startup
50
- w.transition(:init, { true => :up, false => :start }) do |on|
51
- sleep 5
52
- on.condition(:process_running) do |c|
53
- c.interval = 5
54
- c.running = true
55
- end
56
- end
57
-
58
- # determine when process has finished starting
59
- w.transition([:start, :restart], :up) do |on|
60
- on.condition(:process_running) do |c|
61
- c.interval = 20
62
- c.running = true
63
- end
64
-
65
- # failsafe
66
- on.condition(:tries) do |c|
67
- c.interval = 20
68
- c.times = 5
69
- c.transition = :start
70
- end
71
- end
72
-
73
- # start if process is not running
74
- #w.transition(:up, :start) do |on|
75
- # on.condition(:process_exits) do |c|
76
- # c.interval = 20
77
- # end
78
- #end
79
-
80
- # restart if memory or cpu is too high
81
- w.transition(:up, :restart) do |on|
82
- on.condition(:memory_usage) do |c|
83
- c.interval = 20
84
- c.above = opts[:max_tor_memory_usage_mb]
85
- c.times = opts[:max_tor_memory_usage_times]
86
- end
87
-
88
- on.condition(:cpu_usage) do |c|
89
- c.interval = 10
90
- c.above = opts[:max_tor_cpu_percentage]
91
- c.times = opts[:max_tor_cpu_percentage_times]
92
- end
93
- end
94
-
95
- # lifecycle
96
- w.lifecycle do |on|
97
- on.condition(:flapping) do |c|
98
- c.to_state = [:start, :restart]
99
- c.times = 5
100
- c.within = 5.minute
101
- c.transition = :unmonitored
102
- end
103
- end
104
- =end
105
- end