jrack_handlers 1.0.1-java

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,4 @@
1
+ *.gem
2
+ .bundle
3
+ Gemfile.lock
4
+ pkg/*
data/Gemfile ADDED
@@ -0,0 +1,3 @@
1
+ source :rubygems
2
+
3
+ gemspec
@@ -0,0 +1,3 @@
1
+ h1. README
2
+
3
+ Rack handlers for Java web servers. Currently includes a handler for "Webbit":https://github.com/joewalnes/webbit.
@@ -0,0 +1 @@
1
+ require 'bundler/gem_tasks'
@@ -0,0 +1,24 @@
1
+ # encoding: utf-8
2
+
3
+ $: << File.expand_path('../lib', __FILE__)
4
+
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = 'jrack_handlers'
8
+ s.version = '1.0.1'
9
+ s.platform = 'java'
10
+ s.authors = ['Theo Hultberg']
11
+ s.email = ['theo@burtcorp.com']
12
+ s.homepage = 'http://github.com/burtcorp/jrack_handlers'
13
+ s.summary = %q{Rack handlers for Java webservers}
14
+ s.description = %q{Rack handler implementations for Java webservers, such as Webbit}
15
+
16
+ s.rubyforge_project = 'jrack_handlers'
17
+
18
+ s.files = `git ls-files`.split("\n")
19
+ # s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
20
+ # s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
21
+ s.require_paths = %w(lib)
22
+
23
+ s.add_runtime_dependency 'webbit-jars', '>= 0.2.17'
24
+ end
@@ -0,0 +1,153 @@
1
+ # encoding: utf-8
2
+
3
+ require 'webbit-jars'
4
+
5
+
6
+ module Rack
7
+ module Handler
8
+ import org.webbitserver.WebServers
9
+ import org.webbitserver.HttpHandler
10
+ import java.util.concurrent.Executors
11
+
12
+ class Webbit
13
+ include HttpHandler
14
+
15
+ def self.run(app, options={})
16
+ port = (options[:port] || options[:Port]).to_i
17
+ worker_threads = options.fetch(:worker_threads, 1).to_i
18
+ @executor = Executors.new_fixed_thread_pool(worker_threads)
19
+ @handler = Webbit.new(app)
20
+ @server = WebServers.create_web_server(@executor, port)
21
+ @server.add(@handler)
22
+ @server.start
23
+ $stderr.puts("Webbit server started on port #{port}, #{worker_threads} worker threads")
24
+ install_shutdown_hook!
25
+ end
26
+
27
+ def self.shutdown
28
+ @server.stop
29
+ $stderr.puts('Webbit server shutting down')
30
+ @server.join
31
+ @executor.shutdown
32
+ @executor, @server, @handler = nil, nil, nil
33
+ $stderr.puts('Webbit server stopped')
34
+ end
35
+
36
+ def initialize(app)
37
+ @app = app
38
+ end
39
+
40
+ def handleHttpRequest(request, response, control)
41
+ # TODO: there is something not working with chunked responses
42
+ status, headers, body = @app.call(create_env(request))
43
+ headers.each do |key, value|
44
+ response.header(key, value)
45
+ end
46
+ body.each do |chunk|
47
+ response.content(chunk.to_java_bytes)
48
+ end
49
+ response.status(status)
50
+ body.close if body.respond_to?(:close)
51
+ rescue => e
52
+ response.content(e.message + "\n\n")
53
+ response.content(e.backtrace.join("\n"))
54
+ response.status(500)
55
+ ensure
56
+ response.end
57
+ end
58
+
59
+ private
60
+
61
+ EMPTY_STRING = ''.freeze
62
+ QUESTION_MARK = '?'.freeze
63
+ COLON = ':'.freeze
64
+ SLASH = '/'.freeze
65
+ HTTP = 'http'.freeze
66
+ HOST = 'Host'.freeze
67
+ LOCALHOST = 'localhost'.freeze
68
+ CONTENT_TYPE = 'Content-Type'.freeze
69
+ CONTENT_LENGTH = 'Content-Length'.freeze
70
+
71
+ REQUEST_METHOD_KEY = 'REQUEST_METHOD'.freeze
72
+ SCRIPT_NAME_KEY = 'SCRIPT_NAME'.freeze
73
+ PATH_INFO_KEY = 'PATH_INFO'.freeze
74
+ QUERY_STRING_KEY = 'QUERY_STRING'.freeze
75
+ SERVER_NAME_KEY = 'SERVER_NAME'.freeze
76
+ SERVER_PORT_KEY = 'SERVER_PORT'.freeze
77
+ CONTENT_TYPE_KEY = 'CONTENT_TYPE'.freeze
78
+ CONTENT_LENGTH_KEY = 'CONTENT_LENGTH'.freeze
79
+ REMOTE_ADDR_KEY = 'REMOTE_ADDR'.freeze
80
+ REMOTE_HOST_KEY = 'REMOTE_HOST'.freeze
81
+ REQUEST_URI_KEY = 'REQUEST_URI'.freeze
82
+ REQUEST_PATH_KEY = 'REQUEST_PATH'.freeze
83
+ RACK_VERSION_KEY = 'rack.version'.freeze
84
+ RACK_INPUT_KEY = 'rack.input'.freeze
85
+ RACK_ERRORS_KEY = 'rack.errors'.freeze
86
+ RACK_MULTITHREAD_KEY = 'rack.multithread'.freeze
87
+ RACK_MULTIPROCESS_KEY = 'rack.multiprocess'.freeze
88
+ RACK_RUN_ONCE_KEY = 'rack.run_once'.freeze
89
+ RACK_URL_SCHEME_KEY = 'rack.url_scheme'.freeze
90
+
91
+ STATIC_ENV = {
92
+ # Required HTTP environment
93
+ 'SCRIPT_NAME' => EMPTY_STRING,
94
+ 'SERVER_NAME' => LOCALHOST,
95
+
96
+ # Rack internal environment
97
+ 'rack.version' => Rack::VERSION,
98
+ 'rack.errors' => $stderr,
99
+ 'rack.multithread' => true,
100
+ 'rack.multiprocess' => false,
101
+ 'rack.run_once' => false,
102
+ 'rack.url_scheme' => HTTP
103
+ }.freeze
104
+
105
+ def self.install_shutdown_hook!
106
+ java.lang.Runtime.runtime.add_shutdown_hook(java.lang.Thread.new { shutdown })
107
+ end
108
+
109
+ def create_env(request)
110
+ request_body = String.from_java_bytes(request.body_as_bytes)
111
+ rack_input = StringIO.new(request_body)
112
+ rack_input.set_encoding(Encoding::BINARY)
113
+
114
+ path_info, query_string = request.uri.split(QUESTION_MARK)
115
+ query_string ||= EMPTY_STRING
116
+ host, port = request.header(HOST).split(COLON)
117
+ port ||= 80
118
+
119
+ remote_addr, remote_port = request.remote_address.to_s.split(COLON)
120
+ remote_host, remote_ip = remote_addr.split(SLASH)
121
+ remote_host = nil if remote_host.empty?
122
+
123
+ env = STATIC_ENV.merge(
124
+ # Required HTTP environment
125
+ 'REQUEST_METHOD' => request.method,
126
+ 'PATH_INFO' => path_info,
127
+ 'QUERY_STRING' => query_string,
128
+ 'SERVER_PORT' => port,
129
+
130
+ # Optional HTTP environment
131
+ 'CONTENT_TYPE' => request.header(CONTENT_TYPE),
132
+ 'CONTENT_LENGTH' => request.header(CONTENT_LENGTH),
133
+ 'REMOTE_ADDR' => remote_ip,
134
+ 'REMOTE_HOST' => remote_host || remote_ip,
135
+ 'REQUEST_URI' => request.uri,
136
+ 'REQUEST_PATH' => path_info,
137
+
138
+ # Rack internal environment
139
+ 'rack.input' => rack_input
140
+ )
141
+
142
+ request.all_headers.each do |entry|
143
+ header_key_name = entry.key.to_s.upcase.gsub('-', '_')
144
+ env["HTTP_#{header_key_name}"] = entry.value.to_s unless env[header_key_name]
145
+ end
146
+
147
+ env.delete(CONTENT_TYPE_KEY) unless env[CONTENT_TYPE_KEY]
148
+ env.delete(CONTENT_LENGTH_KEY) unless env[CONTENT_LENGTH_KEY]
149
+ env
150
+ end
151
+ end
152
+ end
153
+ end
metadata ADDED
@@ -0,0 +1,70 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: jrack_handlers
3
+ version: !ruby/object:Gem::Version
4
+ prerelease:
5
+ version: 1.0.1
6
+ platform: java
7
+ authors:
8
+ - Theo Hultberg
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+
13
+ date: 2012-01-17 00:00:00 Z
14
+ dependencies:
15
+ - !ruby/object:Gem::Dependency
16
+ name: webbit-jars
17
+ prerelease: false
18
+ requirement: &id001 !ruby/object:Gem::Requirement
19
+ none: false
20
+ requirements:
21
+ - - ">="
22
+ - !ruby/object:Gem::Version
23
+ version: 0.2.17
24
+ type: :runtime
25
+ version_requirements: *id001
26
+ description: Rack handler implementations for Java webservers, such as Webbit
27
+ email:
28
+ - theo@burtcorp.com
29
+ executables: []
30
+
31
+ extensions: []
32
+
33
+ extra_rdoc_files: []
34
+
35
+ files:
36
+ - .gitignore
37
+ - Gemfile
38
+ - README.textile
39
+ - Rakefile
40
+ - jrack_handlers.gemspec
41
+ - lib/rack/handler/webbit.rb
42
+ homepage: http://github.com/burtcorp/jrack_handlers
43
+ licenses: []
44
+
45
+ post_install_message:
46
+ rdoc_options: []
47
+
48
+ require_paths:
49
+ - lib
50
+ required_ruby_version: !ruby/object:Gem::Requirement
51
+ none: false
52
+ requirements:
53
+ - - ">="
54
+ - !ruby/object:Gem::Version
55
+ version: "0"
56
+ required_rubygems_version: !ruby/object:Gem::Requirement
57
+ none: false
58
+ requirements:
59
+ - - ">="
60
+ - !ruby/object:Gem::Version
61
+ version: "0"
62
+ requirements: []
63
+
64
+ rubyforge_project: jrack_handlers
65
+ rubygems_version: 1.8.11
66
+ signing_key:
67
+ specification_version: 3
68
+ summary: Rack handlers for Java webservers
69
+ test_files: []
70
+