pakyow-core 1.0.0.rc5 → 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (64) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +5 -0
  3. data/lib/pakyow/{environment/actions → actions}/dispatch.rb +0 -0
  4. data/lib/pakyow/{environment/actions → actions}/input_parser.rb +0 -0
  5. data/lib/pakyow/{environment/actions → actions}/logger.rb +0 -0
  6. data/lib/pakyow/{environment/actions → actions}/normalizer.rb +0 -0
  7. data/lib/pakyow/{app.rb → application.rb} +26 -26
  8. data/lib/pakyow/application/behavior/aspects.rb +51 -0
  9. data/lib/pakyow/application/behavior/endpoints.rb +43 -0
  10. data/lib/pakyow/application/behavior/frameworks.rb +47 -0
  11. data/lib/pakyow/application/behavior/helpers.rb +107 -0
  12. data/lib/pakyow/{environment → application}/behavior/initializers.rb +4 -4
  13. data/lib/pakyow/application/behavior/isolating.rb +71 -0
  14. data/lib/pakyow/application/behavior/operations.rb +49 -0
  15. data/lib/pakyow/application/behavior/pipeline.rb +60 -0
  16. data/lib/pakyow/application/behavior/plugins.rb +151 -0
  17. data/lib/pakyow/application/behavior/rescuing.rb +53 -0
  18. data/lib/pakyow/application/behavior/restarting.rb +72 -0
  19. data/lib/pakyow/application/behavior/sessions.rb +38 -0
  20. data/lib/pakyow/{behavior → application}/config.rb +1 -1
  21. data/lib/pakyow/{app → application}/connection.rb +4 -4
  22. data/lib/pakyow/{app → application}/connection/behavior/session.rb +1 -1
  23. data/lib/pakyow/{app → application}/connection/behavior/values.rb +1 -1
  24. data/lib/pakyow/{app → application}/connection/behavior/verifier.rb +1 -1
  25. data/lib/pakyow/{app → application}/connection/session/base.rb +1 -1
  26. data/lib/pakyow/{app → application}/connection/session/cookie.rb +2 -2
  27. data/lib/pakyow/application/helpers/app.rb +30 -0
  28. data/lib/pakyow/application/helpers/connection.rb +47 -0
  29. data/lib/pakyow/behavior/initializers.rb +3 -3
  30. data/lib/pakyow/behavior/input_parsing.rb +55 -0
  31. data/lib/pakyow/behavior/plugins.rb +3 -130
  32. data/lib/pakyow/behavior/restarting.rb +28 -46
  33. data/lib/pakyow/behavior/running.rb +127 -0
  34. data/lib/pakyow/behavior/silencing.rb +21 -0
  35. data/lib/pakyow/behavior/timezone.rb +19 -0
  36. data/lib/pakyow/behavior/verification.rb +1 -1
  37. data/lib/pakyow/behavior/verifier.rb +30 -0
  38. data/lib/pakyow/behavior/watching.rb +73 -0
  39. data/lib/pakyow/config.rb +168 -0
  40. data/lib/pakyow/environment.rb +31 -31
  41. data/lib/pakyow/helper.rb +9 -0
  42. data/lib/pakyow/loader.rb +7 -1
  43. data/lib/pakyow/plugin.rb +22 -21
  44. metadata +42 -42
  45. data/lib/pakyow/behavior/aspects.rb +0 -49
  46. data/lib/pakyow/behavior/endpoints.rb +0 -41
  47. data/lib/pakyow/behavior/frameworks.rb +0 -45
  48. data/lib/pakyow/behavior/helpers.rb +0 -108
  49. data/lib/pakyow/behavior/isolating.rb +0 -69
  50. data/lib/pakyow/behavior/operations.rb +0 -47
  51. data/lib/pakyow/behavior/pipeline.rb +0 -58
  52. data/lib/pakyow/behavior/rescuing.rb +0 -51
  53. data/lib/pakyow/behavior/sessions.rb +0 -36
  54. data/lib/pakyow/environment/behavior/config.rb +0 -172
  55. data/lib/pakyow/environment/behavior/input_parsing.rb +0 -57
  56. data/lib/pakyow/environment/behavior/plugins.rb +0 -23
  57. data/lib/pakyow/environment/behavior/restarting.rb +0 -54
  58. data/lib/pakyow/environment/behavior/running.rb +0 -129
  59. data/lib/pakyow/environment/behavior/silencing.rb +0 -23
  60. data/lib/pakyow/environment/behavior/timezone.rb +0 -21
  61. data/lib/pakyow/environment/behavior/verifier.rb +0 -32
  62. data/lib/pakyow/environment/behavior/watching.rb +0 -75
  63. data/lib/pakyow/helpers/app.rb +0 -28
  64. data/lib/pakyow/helpers/connection.rb +0 -45
@@ -0,0 +1,127 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "async/reactor"
4
+ require "async/io/shared_endpoint"
5
+ require "async/http/endpoint"
6
+
7
+ require "pakyow/support/extension"
8
+
9
+ require "pakyow/process_manager"
10
+ require "pakyow/processes/proxy"
11
+ require "pakyow/processes/server"
12
+
13
+ module Pakyow
14
+ module Behavior
15
+ module Running
16
+ extend Support::Extension
17
+
18
+ apply_extension do
19
+ unfreezable :process_manager
20
+
21
+ class_state :processes, default: []
22
+
23
+ on "run" do
24
+ if config.server.proxy
25
+ # Find a port to run the environment on, start the proxy on the configured port.
26
+ #
27
+ port = Processes::Proxy.find_local_port
28
+ process :proxy, restartable: false do
29
+ Processes::Proxy.new(
30
+ host: config.server.host,
31
+ port: config.server.port,
32
+ proxy_port: port
33
+ ).run
34
+ end
35
+ else
36
+ # Run the environment on the configured port.
37
+ #
38
+ port = config.server.port
39
+ end
40
+
41
+ endpoint = Async::HTTP::Endpoint.parse(
42
+ "http://#{config.server.host}:#{port}"
43
+ )
44
+
45
+ bound_endpoint = Async::Reactor.run {
46
+ Async::IO::SharedEndpoint.bound(endpoint)
47
+ }.wait
48
+
49
+ process :server, count: config.server.count do
50
+ Pakyow.config.server.port = port
51
+
52
+ Processes::Server.new(
53
+ protocol: endpoint.protocol,
54
+ scheme: endpoint.scheme,
55
+ endpoint: bound_endpoint
56
+ ).run
57
+ end
58
+
59
+ unless config.server.proxy || ENV.key?("PW_RESPAWN")
60
+ Pakyow.logger << Processes::Server.running_text(
61
+ scheme: endpoint.scheme, host: config.server.host, port: port
62
+ )
63
+ end
64
+ end
65
+ end
66
+
67
+ class_methods do
68
+ def process(name, count: 1, restartable: true, &block)
69
+ @processes << {
70
+ name: name,
71
+ block: block,
72
+ count: count,
73
+ restartable: restartable
74
+ }
75
+ end
76
+
77
+ def run
78
+ performing :run do
79
+ @process_manager = @processes.each_with_object(ProcessManager.new) { |process, manager|
80
+ manager.add(process)
81
+ }
82
+
83
+ root_pid = Process.pid
84
+
85
+ at_exit do
86
+ if Process.pid == root_pid
87
+ shutdown
88
+ else
89
+ @apps.select { |app|
90
+ app.respond_to?(:shutdown)
91
+ }.each(&:shutdown)
92
+ end
93
+ end
94
+ end
95
+
96
+ @process_manager.wait
97
+
98
+ if @respawn
99
+ # Replace the master process with a copy of itself.
100
+ #
101
+ exec "PW_RESPAWN=true #{$0} #{ARGV.join(" ")}"
102
+ end
103
+ rescue SignalException
104
+ exit
105
+ end
106
+
107
+ def shutdown
108
+ if $stdout.isatty
109
+ # Don't let ^C mess up our output.
110
+ #
111
+ puts
112
+ end
113
+
114
+ Pakyow.logger << "Goodbye"
115
+
116
+ performing :shutdown do
117
+ @process_manager.stop
118
+ end
119
+ end
120
+
121
+ def restart
122
+ @process_manager.restart
123
+ end
124
+ end
125
+ end
126
+ end
127
+ end
@@ -0,0 +1,21 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "pakyow/support/extension"
4
+
5
+ module Pakyow
6
+ module Behavior
7
+ module Silencing
8
+ extend Support::Extension
9
+
10
+ apply_extension do
11
+ class_state :silencers, default: []
12
+ end
13
+
14
+ class_methods do
15
+ def silence(&block)
16
+ @silencers << block
17
+ end
18
+ end
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,19 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "pakyow/support/extension"
4
+
5
+ module Pakyow
6
+ module Behavior
7
+ # Sets up the timezone for the environment.
8
+ #
9
+ module Timezone
10
+ extend Support::Extension
11
+
12
+ apply_extension do
13
+ after "configure" do
14
+ ENV["TZ"] = config.timezone.to_s
15
+ end
16
+ end
17
+ end
18
+ end
19
+ end
@@ -23,7 +23,7 @@ module Pakyow
23
23
  end
24
24
 
25
25
  original_values = values.deep_dup
26
- result = Verifier.new(&block).call(values, context: self)
26
+ result = Pakyow::Verifier.new(&block).call(values, context: self)
27
27
 
28
28
  unless result.verified?
29
29
  error = InvalidData.new_with_message(:verification)
@@ -0,0 +1,30 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "pakyow/support/extension"
4
+ require "pakyow/support/message_verifier"
5
+
6
+ module Pakyow
7
+ module Behavior
8
+ module Verifier
9
+ extend Support::Extension
10
+
11
+ class_methods do
12
+ attr_reader :verifier
13
+ end
14
+
15
+ apply_extension do
16
+ before :boot do
17
+ config.secrets.reject! { |secret|
18
+ secret.nil? || secret.empty?
19
+ }
20
+
21
+ if config.secrets.any?
22
+ @verifier = Support::MessageVerifier.new(config.secrets[0])
23
+ else
24
+ raise "Pakyow will not boot without a secret configured in `Pakyow.config.secrets`"
25
+ end
26
+ end
27
+ end
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,73 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "filewatcher"
4
+
5
+ require "pakyow/support/extension"
6
+
7
+ module Pakyow
8
+ module Behavior
9
+ module Watching
10
+ extend Support::Extension
11
+
12
+ apply_extension do
13
+ class_state :on_change_matchers, default: {}
14
+ class_state :watched_paths, default: []
15
+
16
+ unfreezable :filewatcher, :filewatcher_thread
17
+
18
+ after "run" do
19
+ @filewatcher = Filewatcher.new(
20
+ @watched_paths.map { |path|
21
+ File.expand_path(path)
22
+ }
23
+ )
24
+
25
+ @filewatcher_thread = Thread.new do
26
+ @filewatcher.watch(&method(:watch_callback))
27
+ end
28
+ end
29
+
30
+ on "shutdown" do
31
+ @filewatcher.stop
32
+ @filewatcher_thread.join
33
+ end
34
+ end
35
+
36
+ class_methods do
37
+ # Register a callback to be called when a file changes.
38
+ #
39
+ def on_change(matcher, &block)
40
+ (@on_change_matchers[matcher] ||= []) << block
41
+ end
42
+
43
+ # Register one or more path for changes.
44
+ #
45
+ def watch(*paths, &block)
46
+ @watched_paths.concat(paths).uniq!
47
+
48
+ if block
49
+ paths.each do |path|
50
+ on_change(File.expand_path(path), &block)
51
+ end
52
+ end
53
+ end
54
+
55
+ # @api private
56
+ def change_callbacks(path)
57
+ @on_change_matchers.each_with_object([]) { |(matcher, blocks), matched_blocks|
58
+ if matcher.match?(path)
59
+ matched_blocks.concat(blocks)
60
+ end
61
+ }
62
+ end
63
+
64
+ # @api private
65
+ def watch_callback(path, _event)
66
+ change_callbacks(path).each do |callback|
67
+ instance_exec(&callback)
68
+ end
69
+ end
70
+ end
71
+ end
72
+ end
73
+ end
@@ -0,0 +1,168 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "pakyow/support/extension"
4
+
5
+ require "pakyow/logger/formatters/human"
6
+ require "pakyow/logger/formatters/logfmt"
7
+
8
+ module Pakyow
9
+ module Config
10
+ extend Support::Extension
11
+
12
+ apply_extension do
13
+ setting :default_env, :development
14
+ setting :freeze_on_boot, true
15
+ setting :exit_on_boot_failure, true
16
+ setting :timezone, :utc
17
+ setting :secrets, ["pakyow"]
18
+
19
+ setting :connection_class do
20
+ require "pakyow/connection"
21
+ Connection
22
+ end
23
+
24
+ setting :root do
25
+ File.expand_path(".")
26
+ end
27
+
28
+ setting :lib do
29
+ File.join(config.root, "lib")
30
+ end
31
+
32
+ setting :environment_path do
33
+ File.join(config.root, "config/environment")
34
+ end
35
+
36
+ setting :loader_path do
37
+ File.join(config.root, "config/loader")
38
+ end
39
+
40
+ defaults :test do
41
+ setting :exit_on_boot_failure, false
42
+ end
43
+
44
+ defaults :production do
45
+ setting :secrets, [ENV["SECRET"].to_s.strip]
46
+ end
47
+
48
+ configurable :server do
49
+ setting :host, "localhost"
50
+ setting :port, 3000
51
+ setting :count, 1
52
+ setting :proxy, true
53
+
54
+ defaults :production do
55
+ setting :proxy, false
56
+
57
+ setting :host do
58
+ ENV["HOST"] || "0.0.0.0"
59
+ end
60
+
61
+ setting :port do
62
+ ENV["PORT"] || 3000
63
+ end
64
+
65
+ setting :count do
66
+ ENV["WORKERS"] || 5
67
+ end
68
+ end
69
+ end
70
+
71
+ configurable :cli do
72
+ setting :repl do
73
+ require "irb"; IRB
74
+ end
75
+ end
76
+
77
+ configurable :logger do
78
+ setting :enabled, true
79
+ setting :sync, true
80
+
81
+ setting :level do
82
+ if config.logger.enabled
83
+ :debug
84
+ else
85
+ :off
86
+ end
87
+ end
88
+
89
+ setting :formatter do
90
+ Logger::Formatters::Human
91
+ end
92
+
93
+ setting :destinations do
94
+ if config.logger.enabled
95
+ { stdout: $stdout }
96
+ else
97
+ {}
98
+ end
99
+ end
100
+
101
+ defaults :test do
102
+ setting :enabled, false
103
+ end
104
+
105
+ defaults :production do
106
+ setting :level do
107
+ if config.logger.enabled
108
+ :info
109
+ else
110
+ :off
111
+ end
112
+ end
113
+
114
+ setting :formatter do
115
+ Logger::Formatters::Logfmt
116
+ end
117
+ end
118
+
119
+ defaults :ludicrous do
120
+ setting :enabled, false
121
+ end
122
+ end
123
+
124
+ configurable :normalizer do
125
+ setting :strict_path, true
126
+ setting :strict_www, false
127
+ setting :require_www, true
128
+ end
129
+
130
+ configurable :tasks do
131
+ setting :paths, ["./tasks", File.expand_path("../tasks", __FILE__)]
132
+ setting :prelaunch, []
133
+ end
134
+
135
+ configurable :redis do
136
+ configurable :connection do
137
+ setting :url do
138
+ ENV["REDIS_URL"] || "redis://127.0.0.1:6379"
139
+ end
140
+
141
+ setting :timeout, 5
142
+ setting :driver, nil
143
+ setting :id, nil
144
+ setting :tcp_keepalive, 5
145
+ setting :reconnect_attempts, 1
146
+ setting :inherit_socket, false
147
+ end
148
+
149
+ configurable :pool do
150
+ setting :size, 3
151
+ setting :timeout, 1
152
+ end
153
+
154
+ setting :key_prefix, "pw"
155
+ end
156
+
157
+ configurable :cookies do
158
+ setting :domain
159
+ setting :path, "/"
160
+ setting :max_age
161
+ setting :expires
162
+ setting :secure
163
+ setting :http_only
164
+ setting :same_site
165
+ end
166
+ end
167
+ end
168
+ end