procon_bypass_man 0.1.23 → 0.2.2

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 (64) hide show
  1. checksums.yaml +4 -4
  2. data/.circleci/config.yml +13 -0
  3. data/.github/workflows/gitleacks.yml +12 -0
  4. data/.github/workflows/release.yml +1 -0
  5. data/.github/workflows/ruby.yml +1 -1
  6. data/CHANGELOG.md +20 -0
  7. data/Gemfile +6 -3
  8. data/Gemfile.lock +3 -3
  9. data/README.md +2 -2
  10. data/bin/generate_default_app +10 -0
  11. data/docs/getting_started.md +52 -7
  12. data/docs/setup_raspi.md +0 -1
  13. data/lib/procon_bypass_man/background/jobs/base_job.rb +1 -1
  14. data/lib/procon_bypass_man/background/jobs/concerns/{job_runnable.rb → job_performable.rb} +1 -1
  15. data/lib/procon_bypass_man/background.rb +1 -1
  16. data/lib/procon_bypass_man/buttons_setting_configuration/loader.rb +1 -1
  17. data/lib/procon_bypass_man/{commands → bypass}/bypass_command.rb +11 -19
  18. data/lib/procon_bypass_man/bypass/usb_hid_logger.rb +0 -1
  19. data/lib/procon_bypass_man/bypass.rb +9 -14
  20. data/lib/procon_bypass_man/commands/print_boot_message_command.rb +1 -2
  21. data/lib/procon_bypass_man/commands/send_error_command.rb +2 -2
  22. data/lib/procon_bypass_man/commands.rb +0 -3
  23. data/lib/procon_bypass_man/configuration.rb +22 -3
  24. data/lib/procon_bypass_man/device_connection/command.rb +28 -0
  25. data/lib/procon_bypass_man/{device_connector.rb → device_connection/executor.rb} +51 -38
  26. data/lib/procon_bypass_man/device_connection/output_report_generator.rb +42 -0
  27. data/lib/procon_bypass_man/device_connection/output_report_markerable.rb +28 -0
  28. data/lib/procon_bypass_man/device_connection/output_report_sub_command_table.rb +133 -0
  29. data/lib/procon_bypass_man/device_connection/output_report_watcher.rb +41 -0
  30. data/lib/procon_bypass_man/device_connection/pre_bypass.rb +67 -0
  31. data/lib/procon_bypass_man/device_connection/procon_setting_overrider.rb +78 -0
  32. data/lib/procon_bypass_man/device_connection/spoofing_output_report_watcher.rb +39 -0
  33. data/lib/procon_bypass_man/device_connection.rb +16 -0
  34. data/lib/procon_bypass_man/device_model.rb +17 -0
  35. data/lib/procon_bypass_man/io_monitor.rb +20 -1
  36. data/lib/procon_bypass_man/procon/macro_builder.rb +5 -3
  37. data/lib/procon_bypass_man/procon_display/bypass_hook.rb +11 -0
  38. data/lib/procon_bypass_man/procon_display/http_request.rb +31 -0
  39. data/lib/procon_bypass_man/procon_display/http_response.rb +23 -0
  40. data/lib/procon_bypass_man/procon_display/server.rb +33 -0
  41. data/lib/procon_bypass_man/procon_display/server_app.rb +17 -0
  42. data/lib/procon_bypass_man/procon_display/status.rb +20 -0
  43. data/lib/procon_bypass_man/procon_display.rb +11 -0
  44. data/lib/procon_bypass_man/{commands → remote_pbm_action/commands}/run_remote_pbm_action_dispatch_command.rb +0 -0
  45. data/lib/procon_bypass_man/remote_pbm_action/restore_pbm_setting.rb +7 -1
  46. data/lib/procon_bypass_man/remote_pbm_action.rb +1 -0
  47. data/lib/procon_bypass_man/runner.rb +4 -7
  48. data/lib/procon_bypass_man/support/callbacks.rb +68 -34
  49. data/lib/procon_bypass_man/support/never_exit_accidentally.rb +3 -3
  50. data/lib/procon_bypass_man/support/usb_device_controller.rb +2 -2
  51. data/lib/procon_bypass_man/support/yaml_loader.rb +12 -0
  52. data/lib/procon_bypass_man/version.rb +1 -1
  53. data/lib/procon_bypass_man/websocket/client.rb +1 -4
  54. data/lib/procon_bypass_man.rb +66 -41
  55. data/procon_bypass_man.gemspec +1 -1
  56. data/project_template/README.md +0 -5
  57. data/project_template/app.rb +24 -6
  58. data/project_template/app.rb.erb +64 -0
  59. data/project_template/lib/app_generator.rb +31 -0
  60. data/project_template/web.rb +1 -1
  61. data/sig/main.rbs +3 -3
  62. data/tmp/.keep +0 -0
  63. metadata +30 -8
  64. data/lib/procon_bypass_man/commands/connect_device_command.rb +0 -18
@@ -0,0 +1,11 @@
1
+ module ProconBypassMan::ProconDisplay::BypassHook
2
+ include ProconBypassMan::Callbacks
3
+
4
+ define_callbacks :send_procon_to_gadget
5
+
6
+ set_callback :send_procon_to_gadget, :after, :write_procon_display_Status
7
+
8
+ def write_procon_display_Status
9
+ ProconBypassMan::ProconDisplay::Status.instance.current = bypass_value.binary.to_procon_reader.to_hash.dup
10
+ end
11
+ end
@@ -0,0 +1,31 @@
1
+ module ProconBypassMan::ProconDisplay
2
+ # NOTE Support GET only
3
+ class HttpRequest
4
+ def self.parse(conn)
5
+ headers = {}
6
+ loop do
7
+ line = conn.gets("\n")&.strip
8
+ break if line.nil? || line.strip.empty?
9
+ key, value = line.split(/:\s/, 2)
10
+ headers[key] = value
11
+ end
12
+
13
+ new(headers)
14
+ end
15
+
16
+ def initialize(headers)
17
+ @headers = headers
18
+ end
19
+
20
+ def path
21
+ request_method_and_path = @headers.detect { |key, _value| key.start_with?("GET") }.first
22
+ if request_method_and_path =~ /(?:GET) ([^ ]+)/ && (path = $1)
23
+ return path
24
+ end
25
+ end
26
+
27
+ def to_hash
28
+ { "PATH" => path }
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,23 @@
1
+ module ProconBypassMan::ProconDisplay
2
+ class HttpResponse
3
+ def initialize(body, status: , format: "text/json")
4
+ @body = body&.to_json
5
+ @status = status
6
+ @format = format
7
+ end
8
+
9
+ def to_s
10
+ <<~EOH
11
+ HTTP/1.1 #{@status}
12
+ Content-Length: #{@body&.bytes&.size || 0}
13
+ Content-Type: #{@format}
14
+ Access-Control-Allow-Origin: *
15
+ Access-Control-Allow-Methods: GET
16
+ Access-Control-Allow-Private-Network:true
17
+ Connection: close
18
+
19
+ #{@body}
20
+ EOH
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,33 @@
1
+ require 'socket'
2
+
3
+ module ProconBypassMan::ProconDisplay
4
+ class Server
5
+ PORT = 9900
6
+
7
+ def self.start!
8
+ Thread.new do
9
+ new.start_with_foreground
10
+ end
11
+ end
12
+
13
+ def initialize
14
+ @server = TCPServer.new('0.0.0.0', PORT)
15
+ end
16
+
17
+ def start_with_foreground
18
+ loop do
19
+ conn = @server.accept
20
+ response = ServerApp.new(
21
+ HttpRequest.parse(conn).to_hash
22
+ ).call
23
+ conn.write(response)
24
+ conn.close
25
+ end
26
+ rescue Errno::EADDRINUSE => e
27
+ ProconBypassMan::SendErrorCommand.execute(error: e)
28
+ rescue => e
29
+ ProconBypassMan::SendErrorCommand.execute(error: e)
30
+ retry
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,17 @@
1
+ module ProconBypassMan::ProconDisplay
2
+ class ServerApp
3
+ def initialize(env)
4
+ @env = env
5
+ end
6
+
7
+ def call
8
+ case @env["PATH"]
9
+ when "/input"
10
+ response = ProconBypassMan::ProconDisplay::Status.instance.current
11
+ HttpResponse.new(response, status: 200).to_s
12
+ else
13
+ HttpResponse.new(nil, status: 404).to_s
14
+ end
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,20 @@
1
+ require 'singleton'
2
+
3
+ class ProconBypassMan::ProconDisplay::Status
4
+ include Singleton
5
+
6
+ # @return [Hash]
7
+ def current
8
+ @current || {}
9
+ end
10
+
11
+ # @return [void]
12
+ # @param [Hash] value
13
+ def current=(value)
14
+ if value.is_a?(Hash)
15
+ @current = value
16
+ else
17
+ @current = nil
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,11 @@
1
+ # 入力表示用
2
+
3
+ module ProconBypassMan::ProconDisplay
4
+ end
5
+
6
+ require "procon_bypass_man/procon_display/server"
7
+ require "procon_bypass_man/procon_display/server_app"
8
+ require "procon_bypass_man/procon_display/status"
9
+ require "procon_bypass_man/procon_display/http_response"
10
+ require "procon_bypass_man/procon_display/http_request"
11
+ require "procon_bypass_man/procon_display/bypass_hook"
@@ -17,7 +17,8 @@ module ProconBypassMan
17
17
  path: ProconBypassMan::ButtonsSettingConfiguration.instance.setting_path,
18
18
  content: setting,
19
19
  )
20
- ProconBypassMan.hot_reload!
20
+
21
+ hot_reload!
21
22
  end
22
23
 
23
24
  private
@@ -29,6 +30,11 @@ module ProconBypassMan
29
30
  def after_action_callback
30
31
  be_processed
31
32
  end
33
+
34
+ # @return [void]
35
+ def hot_reload!
36
+ Process.kill(:USR2, ProconBypassMan.pid)
37
+ end
32
38
  end
33
39
  end
34
40
  end
@@ -6,6 +6,7 @@ module ProconBypassMan
6
6
  require "procon_bypass_man/remote_pbm_action/stop_pbm_action"
7
7
  require "procon_bypass_man/remote_pbm_action/restore_pbm_setting.rb"
8
8
  require "procon_bypass_man/remote_pbm_action/commands/update_remote_pbm_action_status_command"
9
+ require "procon_bypass_man/remote_pbm_action/commands/run_remote_pbm_action_dispatch_command"
9
10
  require "procon_bypass_man/remote_pbm_action/value_objects/remote_pbm_action_object"
10
11
 
11
12
  ACTION_CHANGE_PBM_VERSION = "change_pbm_version"
@@ -8,8 +8,6 @@ class ProconBypassMan::Runner
8
8
  def initialize(gadget: , procon: )
9
9
  @gadget = gadget
10
10
  @procon = procon
11
-
12
- ProconBypassMan::PrintBootMessageCommand.execute
13
11
  end
14
12
 
15
13
  def run
@@ -30,6 +28,7 @@ class ProconBypassMan::Runner
30
28
  $will_terminate_token = false
31
29
  DRb.start_service if defined?(DRb)
32
30
  ProconBypassMan::RemoteMacroReceiver.start!
31
+ ProconBypassMan::ProconDisplay::Server.start!
33
32
  ProconBypassMan::BypassCommand.new(gadget: @gadget, procon: @procon).execute # ここでblockingする
34
33
  next
35
34
  }
@@ -41,9 +40,9 @@ class ProconBypassMan::Runner
41
40
  handle_signal(signal)
42
41
  end
43
42
  rescue InterruptForRestart
43
+ ProconBypassMan::PrintMessageCommand.execute(text: "設定ファイルの再読み込みを開始します")
44
44
  Process.kill("USR2", child_pid)
45
45
  Process.wait
46
- ProconBypassMan::PrintMessageCommand.execute(text: "Reloading config file")
47
46
  begin
48
47
  ProconBypassMan::ButtonsSettingConfiguration::Loader.reload_setting
49
48
  ProconBypassMan::SendReloadConfigEventCommand.execute
@@ -53,12 +52,10 @@ class ProconBypassMan::Runner
53
52
  end
54
53
  ProconBypassMan::PrintMessageCommand.execute(text: "バイパス処理を再開します")
55
54
  rescue Interrupt
55
+ puts
56
+ ProconBypassMan::PrintMessageCommand.execute(text: "処理を終了します")
56
57
  Process.kill("TERM", child_pid)
57
58
  Process.wait
58
- ProconBypassMan::PrintMessageCommand.execute(text: "処理を終了します")
59
- ProconBypassMan::UsbDeviceController.reset
60
- @gadget&.close
61
- @procon&.close
62
59
  break
63
60
  end
64
61
  end
@@ -1,21 +1,15 @@
1
1
  module ProconBypassMan
2
- module Callbacks
3
- class CallbacksChain
4
- attr_accessor :filter, :chain_method
5
- def initialize(filter: , chain_method: , block: )
6
- @filter = filter
7
- @chain_method = chain_method
8
- @block = block
9
- end
10
- end
2
+ module CallbacksRegisterable
3
+ attr_accessor :callbacks
11
4
 
12
- # TODO __callbacksをincludeしたクラス側で保持する. 今はnemespaceがない
13
- module M
14
- class << self
15
- attr_accessor :__callbacks
16
- end
5
+ def register_callback_module(mod)
6
+ self.callbacks ||= []
7
+ callbacks << mod
8
+ self.include(mod)
17
9
  end
10
+ end
18
11
 
12
+ module Callbacks
19
13
  module ClassMethods
20
14
  def define_callbacks(name)
21
15
  self.singleton_class.attr_accessor "_#{name}_callbacks"
@@ -29,8 +23,9 @@ module ProconBypassMan
29
23
  end
30
24
 
31
25
  def set_callback(kind, filter, chain_method, &block)
32
- ProconBypassMan::Callbacks::M.__callbacks ||= {}
33
- ProconBypassMan::Callbacks::M.__callbacks[kind] = CallbacksChain.new(
26
+ self.__callbacks ||= {}
27
+ self.__callbacks[kind] ||= CallbackChain.new
28
+ self.__callbacks[kind].append Callback.new(
34
29
  filter: filter,
35
30
  chain_method: chain_method,
36
31
  block: block,
@@ -38,33 +33,72 @@ module ProconBypassMan
38
33
  end
39
34
  end
40
35
 
36
+ def self.included(mod)
37
+ mod.singleton_class.attr_accessor :__callbacks
38
+ mod.extend(ClassMethods)
39
+ end
40
+
41
+ class CallbackChain
42
+ attr_accessor :callbacks
43
+
44
+ def initialize
45
+ self.callbacks = {}
46
+ end
47
+
48
+ def empty?
49
+ callbacks.empty?
50
+ end
51
+
52
+ def append(callback)
53
+ self.callbacks[callback.filter] ||= []
54
+ self.callbacks[callback.filter] << callback
55
+ end
56
+
57
+ def [](filter)
58
+ self.callbacks[filter]
59
+ end
60
+ end
61
+
62
+ class Callback
63
+ attr_accessor :filter, :chain_method
64
+
65
+ def initialize(filter: , chain_method: , block: )
66
+ @filter = filter
67
+ @chain_method = chain_method
68
+ @block = block
69
+ end
70
+ end
71
+
41
72
  # TODO haltしたらcallbackを止める
42
- # TODO 複数をチェインできるようにする
43
73
  def run_callbacks(kind, &block)
44
- chain = get_callbacks(kind) or raise("unknown callback")
45
- case chain.filter
46
- when :before
47
- send chain.chain_method
48
- block.call
49
- when :after
74
+ chains = get_callbacks(kind) or raise("unknown callback")
75
+ if chains.nil? || chains.empty?
50
76
  block.call
77
+ return
78
+ end
79
+
80
+ chains[:before]&.each do |chain|
81
+ send chain.chain_method
82
+ end
83
+ block.call
84
+ chains[:after]&.each do |chain|
51
85
  send chain.chain_method
52
- else
53
- raise("unknown filter")
54
86
  end
55
87
  end
56
88
 
57
- # def __run_callbacks__(name, &block)
58
- # puts "called"
59
- # end
60
-
61
89
  def get_callbacks(kind) # :nodoc:
62
- ProconBypassMan::Callbacks::M.__callbacks[kind.to_sym]
63
- end
90
+ # classに直接moduleをincludeしている場合
91
+ if defined?(self.class.__callbacks)
92
+ return self.class.__callbacks[kind.to_sym]
93
+ end
64
94
 
65
- def set_callbacks(name, callbacks) # :nodoc:
66
- send "_#{name}_callbacks=", callbacks
67
- ProconBypassMan::Callbacks::M.__callbacks[kind.to_sym] = callbacks
95
+ list = self.class.callbacks.flat_map { |callback_mod|
96
+ callback_mod.__callbacks && callback_mod.__callbacks[kind.to_sym]
97
+ }.compact
98
+ table = {}
99
+ table[:before] = list.flat_map { |x| x[:before] }.compact
100
+ table[:after] = list.flat_map { |x| x[:after] }.compact
101
+ table
68
102
  end
69
103
  end
70
104
  end
@@ -1,11 +1,11 @@
1
1
  module ProconBypassMan
2
2
  module NeverExitAccidentally
3
- def exit_if_allow(status)
3
+ def self.exit_if_allow_at_config
4
4
  if ProconBypassMan.never_exit_accidentally
5
- eternal_sleep
5
+ ProconBypassMan.eternal_sleep
6
6
  else
7
7
  yield if block_given?
8
- exit(status)
8
+ exit 1
9
9
  end
10
10
  end
11
11
  end
@@ -1,13 +1,13 @@
1
1
  class ProconBypassMan::UsbDeviceController
2
2
  class << self
3
- def reset
3
+ def reset(cooldown: 0.5)
4
4
  [ "echo > /sys/kernel/config/usb_gadget/procon/UDC",
5
5
  "ls /sys/class/udc > /sys/kernel/config/usb_gadget/procon/UDC",
6
6
  ].each do |shell|
7
7
  system shell
8
8
  ProconBypassMan.logger.debug { "[SHELL] #{shell}" }
9
9
  end
10
- sleep 0.5
10
+ sleep cooldown
11
11
  end
12
12
 
13
13
  def init
@@ -0,0 +1,12 @@
1
+ class ProconBypassMan::YamlLoader
2
+ # @param [String] path
3
+ # @return [Hash]
4
+ def self.load(path: )
5
+ YAML.load_file(path).tap do |y|
6
+ # 行末に空白があるとto_yamlしたときに改行コードがエスケープされてしまうのでstrip
7
+ y.transform_values do |v|
8
+ v.strip! if v.is_a?(String)
9
+ end
10
+ end
11
+ end
12
+ end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module ProconBypassMan
4
- VERSION = "0.1.23"
4
+ VERSION = "0.2.2"
5
5
  end
@@ -23,8 +23,7 @@ module ProconBypassMan
23
23
  ProconBypassMan.logger.info('websocket client: successfully connected in ProconBypassMan::Websocket::Client')
24
24
  }
25
25
  client.subscribed { |msg|
26
- ProconBypassMan.logger.info('websocket client: subscribed')
27
- puts({ event: :subscribed, msg: msg })
26
+ ProconBypassMan.logger.info("websocket client: subscribed(#{msg})")
28
27
  ProconBypassMan::SyncDeviceStatsJob.perform(ProconBypassMan::DeviceStatus.current)
29
28
  }
30
29
 
@@ -39,13 +38,11 @@ module ProconBypassMan
39
38
 
40
39
  client.disconnected {
41
40
  ProconBypassMan.logger.info('websocket client: disconnected!!')
42
- puts :disconnected
43
41
  client.reconnect!
44
42
  sleep 2
45
43
  }
46
44
  client.errored { |msg|
47
45
  ProconBypassMan.logger.error("websocket client: errored!!, #{msg}")
48
- puts :errored
49
46
  client.reconnect!
50
47
  sleep 2
51
48
  }
@@ -14,11 +14,14 @@ require "pbmenv"
14
14
  require_relative "procon_bypass_man/version"
15
15
  require_relative "procon_bypass_man/remote_pbm_action"
16
16
  require_relative "procon_bypass_man/remote_macro"
17
+
18
+ require_relative "procon_bypass_man/device_connection"
17
19
  require_relative "procon_bypass_man/support/usb_device_controller"
18
20
  require_relative "procon_bypass_man/support/device_procon_finder"
19
21
  require_relative "procon_bypass_man/support/device_mouse_finder"
20
22
  require_relative "procon_bypass_man/support/signal_handler"
21
23
  require_relative "procon_bypass_man/support/callbacks"
24
+ require_relative "procon_bypass_man/support/yaml_loader"
22
25
  require_relative "procon_bypass_man/support/yaml_writer"
23
26
  require_relative "procon_bypass_man/support/safe_timeout"
24
27
  require_relative "procon_bypass_man/support/compress_array"
@@ -33,16 +36,17 @@ require_relative "procon_bypass_man/support/server_pool"
33
36
  require_relative "procon_bypass_man/support/analog_stick_hypotenuse_tilting_power_scaler"
34
37
  require_relative "procon_bypass_man/support/never_exit_accidentally"
35
38
  require_relative "procon_bypass_man/support/cycle_sleep"
39
+ require_relative "procon_bypass_man/procon_display"
36
40
  require_relative "procon_bypass_man/background"
37
41
  require_relative "procon_bypass_man/commands"
38
42
  require_relative "procon_bypass_man/bypass"
39
- require_relative "procon_bypass_man/device_connector"
40
43
  require_relative "procon_bypass_man/device_status"
41
44
  require_relative "procon_bypass_man/runner"
42
45
  require_relative "procon_bypass_man/processor"
43
46
  require_relative "procon_bypass_man/configuration"
44
47
  require_relative "procon_bypass_man/buttons_setting_configuration"
45
48
  require_relative "procon_bypass_man/procon"
49
+ require_relative "procon_bypass_man/device_model"
46
50
  require_relative "procon_bypass_man/procon/button"
47
51
  require_relative "procon_bypass_man/procon/analog_stick_cap"
48
52
  require_relative "procon_bypass_man/procon/analog_stick_manipulator"
@@ -61,52 +65,59 @@ module ProconBypassMan
61
65
  extend ProconBypassMan::NeverExitAccidentally
62
66
 
63
67
  class CouldNotLoadConfigError < StandardError; end
64
- class EternalConnectionError < StandardError; end
68
+ class NotFoundProconError < StandardError; end
65
69
 
66
70
  # @return [void]
67
71
  def self.run(setting_path: nil)
68
- ProconBypassMan::Scheduler.start!
69
- ProconBypassMan::Background::JobRunner.start!
70
- ProconBypassMan::Websocket::Client.start!
71
- ProconBypassMan::QueueOverProcess.start!
72
-
73
72
  ProconBypassMan::PrintMessageCommand.execute(text: "PBMを起動しています")
74
73
  initialize_pbm
75
- ProconBypassMan::ButtonsSettingConfiguration::Loader.load(setting_path: setting_path)
76
- gadget, procon = ProconBypassMan::ConnectDeviceCommand.execute!
77
- Runner.new(gadget: gadget, procon: procon).run # ここでblockingする
78
- FileUtils.rm_rf(ProconBypassMan.pid_path)
79
- FileUtils.rm_rf(ProconBypassMan.digest_path)
80
- ProconBypassMan::QueueOverProcess.shutdown
81
- rescue ProconBypassMan::CouldNotLoadConfigError
82
- ProconBypassMan::SendErrorCommand.execute(error: "設定ファイルが不正です。設定ファイルの読み込みに失敗しました")
83
- ProconBypassMan::DeviceStatus.change_to_setting_syntax_error_and_shutdown!
84
- # TODO シグナルトラップをしていないのでUSR2を送ったときにプロセスが停止している. 明示的にハンドリングするべき.
85
- ProconBypassMan.exit_if_allow(1) do
86
- FileUtils.rm_rf(ProconBypassMan.pid_path)
87
- FileUtils.rm_rf(ProconBypassMan.digest_path)
88
- ProconBypassMan::QueueOverProcess.shutdown
74
+
75
+ begin
76
+ ProconBypassMan::ButtonsSettingConfiguration::Loader.load(setting_path: setting_path)
77
+ rescue ProconBypassMan::CouldNotLoadConfigError
78
+ ProconBypassMan::SendErrorCommand.execute(error: "設定ファイルが不正です。設定ファイルの読み込みに失敗しました")
79
+ ProconBypassMan::DeviceStatus.change_to_setting_syntax_error_and_shutdown!
80
+ # TODO シグナルトラップをしていないのでUSR2を送ったときにプロセスが停止している. 明示的にハンドリングするべき.
81
+ ProconBypassMan::NeverExitAccidentally.exit_if_allow_at_config do
82
+ terminate_pbm
83
+ end
84
+ return
89
85
  end
90
- rescue ProconBypassMan::ConnectDeviceCommand::NotFoundProconError
91
- ProconBypassMan::SendErrorCommand.execute(error: "プロコンが見つかりませんでした。")
92
- ProconBypassMan::DeviceStatus.change_to_procon_not_found_error!
93
- # TODO シグナルトラップをしていないのでUSR2を送ったときにプロセスが停止している. 明示的にハンドリングするべき.
94
- ProconBypassMan.exit_if_allow(1) do
95
- FileUtils.rm_rf(ProconBypassMan.pid_path)
96
- FileUtils.rm_rf(ProconBypassMan.digest_path)
97
- ProconBypassMan::QueueOverProcess.shutdown
86
+
87
+ begin
88
+ gadget, procon = ProconBypassMan::DeviceConnection::Command.execute!
89
+ rescue ProconBypassMan::DeviceConnection::NotFoundProconError
90
+ ProconBypassMan::SendErrorCommand.execute(error: "プロコンが見つかりませんでした。")
91
+ ProconBypassMan::DeviceStatus.change_to_procon_not_found_error!
92
+ # TODO シグナルトラップをしていないので以下の状態に、USR2を送ったときにプロセスが停止してしまう
93
+ ProconBypassMan::NeverExitAccidentally.exit_if_allow_at_config do
94
+ terminate_pbm
95
+ end
96
+ return
97
+ rescue ProconBypassMan::DeviceConnection::TimeoutError
98
+ ProconBypassMan::SendErrorCommand.execute(error: "接続の見込みがないのでsleepしまくります")
99
+ ProconBypassMan::DeviceStatus.change_to_connected_but_sleeping!
100
+ %w(TERM INT).each do |sig|
101
+ Kernel.trap(sig) { exit 0 }
102
+ end
103
+ Kernel.trap :USR2 do
104
+ exit 0 # TODO retryする
105
+ end
106
+ eternal_sleep
107
+ return
98
108
  end
99
- rescue ProconBypassMan::EternalConnectionError
100
- ProconBypassMan::SendErrorCommand.execute(error: "接続の見込みがないのでsleepしまくります")
101
- ProconBypassMan::DeviceStatus.change_to_connected_but_sleeping!
102
- FileUtils.rm_rf(ProconBypassMan.pid_path)
103
- eternal_sleep
109
+
110
+ ready_pbm
111
+ Runner.new(gadget: gadget, procon: procon).run # ここでblockingする
112
+ terminate_pbm
104
113
  end
105
114
 
115
+ # 実行ファイル(app.rb)から呼び出している
116
+ # @return [void]
106
117
  def self.configure(&block)
107
118
  @@configuration = ProconBypassMan::Configuration.new
108
119
  @@configuration.instance_eval(&block)
109
- @@configuration
120
+ nil
110
121
  end
111
122
 
112
123
  # @return [ProconBypassMan::Configuration]
@@ -123,20 +134,34 @@ module ProconBypassMan
123
134
  ProconBypassMan::IOMonitor.reset!
124
135
  end
125
136
 
137
+ # @return [void]
126
138
  def self.initialize_pbm
139
+ ProconBypassMan::Scheduler.start!
140
+ ProconBypassMan::Background::JobRunner.start!
141
+ ProconBypassMan::Websocket::Client.start!
142
+ ProconBypassMan::QueueOverProcess.start!
143
+
127
144
  ProconBypassMan::WriteDeviceIdCommand.execute
128
145
  ProconBypassMan::WriteSessionIdCommand.execute
129
- system("renice -n -20 -p #{$$}")
146
+ `renice -n -20 -p #{$$}`
130
147
  File.write(pid_path, $$)
131
148
  ProconBypassMan::DeviceStatus.change_to_running!
132
149
  end
133
150
 
134
- def self.eternal_sleep
135
- sleep(999999999)
151
+ def self.ready_pbm
152
+ ProconBypassMan::PrintBootMessageCommand.execute
153
+ ProconBypassMan::ReportLoadConfigJob.perform_async(ProconBypassMan.config.raw_setting)
154
+ end
155
+
156
+ # @return [void]
157
+ def self.terminate_pbm
158
+ FileUtils.rm_rf(ProconBypassMan.pid_path)
159
+ FileUtils.rm_rf(ProconBypassMan.digest_path)
160
+ ProconBypassMan::QueueOverProcess.shutdown
136
161
  end
137
162
 
138
- # @return [Void]
139
- def self.hot_reload!
140
- Process.kill(:USR2, pid)
163
+ # @return [void]
164
+ def self.eternal_sleep
165
+ sleep(999999999)
141
166
  end
142
167
  end
@@ -12,7 +12,7 @@ Gem::Specification.new do |spec|
12
12
  spec.description = spec.summary
13
13
  spec.homepage = "https://github.com/splaplapla/procon_bypass_man"
14
14
  spec.license = "MIT"
15
- spec.required_ruby_version = Gem::Requirement.new(">= 3.0.0")
15
+ spec.required_ruby_version = Gem::Requirement.new(">= 2.5.0")
16
16
 
17
17
  spec.metadata["homepage_uri"] = spec.homepage
18
18
  spec.metadata["source_code_uri"] = spec.homepage
@@ -1,6 +1,5 @@
1
1
  # Project Template
2
2
  * これらは https://github.com/splaplapla/pbmenv がinstallするときに配備するファイルです
3
- * pbm_webはオプショナルです
4
3
 
5
4
  ## systemdを使ってサービスに登録する方法
6
5
  systemctl enableした後は、次回のOS起動時にserviceも自動起動します
@@ -8,13 +7,9 @@ systemctl enableした後は、次回のOS起動時にserviceも自動起動し
8
7
  * pbm
9
8
  * sudo systemctl link /usr/share/pbm/current/systemd_units/pbm.service
10
9
  * sudo systemctl enable pbm.service
11
- * pbm_web
12
- * sudo systemctl link /usr/share/pbm/current/systemd_units/pbm_web.service
13
- * sudo systemctl enable pbm_web.service
14
10
 
15
11
  ## systemdを使ってサービスから解除する方法
16
12
  * sudo systemctl disable pbm.service
17
- * sudo systemctl disable pbm_web.service
18
13
 
19
14
  ### CheatSheet
20
15
  * systemctl daemon-reload