ronin-web 0.1.3 → 0.2.0
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.
- data.tar.gz.sig +0 -0
- data/History.txt +25 -0
- data/Manifest.txt +36 -4
- data/README.txt +67 -64
- data/Rakefile +12 -3
- data/bin/ronin-web +1 -1
- data/lib/ronin/network/helpers/web.rb +221 -0
- data/lib/ronin/web.rb +1 -2
- data/lib/ronin/web/extensions.rb +0 -2
- data/lib/ronin/web/extensions/nokogiri.rb +0 -23
- data/lib/ronin/web/proxy.rb +3 -103
- data/lib/ronin/web/proxy/app.rb +31 -0
- data/lib/ronin/web/proxy/base.rb +41 -0
- data/lib/ronin/web/proxy/web.rb +42 -0
- data/lib/ronin/web/server.rb +3 -530
- data/lib/ronin/web/server/app.rb +31 -0
- data/lib/ronin/web/server/base.rb +334 -0
- data/lib/ronin/web/server/files.rb +92 -0
- data/lib/ronin/web/server/helpers.rb +25 -0
- data/lib/ronin/web/server/helpers/files.rb +126 -0
- data/lib/ronin/web/server/helpers/hosts.rb +72 -0
- data/lib/ronin/web/server/helpers/proxy.rb +153 -0
- data/lib/ronin/web/server/helpers/rendering.rb +36 -0
- data/lib/ronin/web/server/hosts.rb +86 -0
- data/lib/ronin/web/server/proxy.rb +116 -0
- data/lib/ronin/web/server/web.rb +62 -0
- data/lib/ronin/web/spider.rb +53 -26
- data/lib/ronin/web/version.rb +1 -3
- data/lib/ronin/web/web.rb +253 -95
- data/spec/spec_helper.rb +1 -1
- data/spec/web/proxy/base_spec.rb +9 -0
- data/spec/web/server/base_spec.rb +86 -0
- data/spec/web/server/classes/files/dir/file.txt +1 -0
- data/spec/web/server/classes/files/dir/index.html +1 -0
- data/spec/web/server/classes/files/dir2/file2.txt +1 -0
- data/spec/web/server/classes/files/dir3/page.xml +4 -0
- data/spec/web/server/classes/files/file.txt +1 -0
- data/spec/web/server/classes/files_app.rb +27 -0
- data/spec/web/server/classes/hosts_app.rb +40 -0
- data/spec/web/server/classes/proxy_app.rb +45 -0
- data/spec/web/server/classes/public1/static1.txt +1 -0
- data/spec/web/server/classes/public2/static2.txt +1 -0
- data/spec/web/server/classes/sub_app.rb +13 -0
- data/spec/web/server/classes/test_app.rb +20 -0
- data/spec/web/server/files_spec.rb +74 -0
- data/spec/web/server/helpers/server.rb +42 -0
- data/spec/web/server/hosts_spec.rb +55 -0
- data/spec/web/server/proxy_spec.rb +49 -0
- data/tasks/spec.rb +1 -0
- data/tasks/yard.rb +13 -0
- metadata +76 -17
- metadata.gz.sig +0 -0
- data/TODO.txt +0 -7
- data/lib/ronin/sessions/web.rb +0 -80
- data/lib/ronin/web/fingerprint.rb +0 -76
- data/spec/web/server_spec.rb +0 -142
@@ -0,0 +1,25 @@
|
|
1
|
+
#
|
2
|
+
# Ronin Web - A Ruby library for Ronin that provides support for web
|
3
|
+
# scraping and spidering functionality.
|
4
|
+
#
|
5
|
+
# Copyright (c) 2006-2009 Hal Brodigan (postmodern.mod3 at gmail.com)
|
6
|
+
#
|
7
|
+
# This program is free software; you can redistribute it and/or modify
|
8
|
+
# it under the terms of the GNU General Public License as published by
|
9
|
+
# the Free Software Foundation; either version 2 of the License, or
|
10
|
+
# (at your option) any later version.
|
11
|
+
#
|
12
|
+
# This program is distributed in the hope that it will be useful,
|
13
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
14
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
15
|
+
# GNU General Public License for more details.
|
16
|
+
#
|
17
|
+
# You should have received a copy of the GNU General Public License
|
18
|
+
# along with this program; if not, write to the Free Software
|
19
|
+
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
20
|
+
#
|
21
|
+
|
22
|
+
require 'ronin/web/server/helpers/rendering'
|
23
|
+
require 'ronin/web/server/helpers/files'
|
24
|
+
require 'ronin/web/server/helpers/hosts'
|
25
|
+
require 'ronin/web/server/helpers/proxy'
|
@@ -0,0 +1,126 @@
|
|
1
|
+
#
|
2
|
+
# Ronin Web - A Ruby library for Ronin that provides support for web
|
3
|
+
# scraping and spidering functionality.
|
4
|
+
#
|
5
|
+
# Copyright (c) 2006-2009 Hal Brodigan (postmodern.mod3 at gmail.com)
|
6
|
+
#
|
7
|
+
# This program is free software; you can redistribute it and/or modify
|
8
|
+
# it under the terms of the GNU General Public License as published by
|
9
|
+
# the Free Software Foundation; either version 2 of the License, or
|
10
|
+
# (at your option) any later version.
|
11
|
+
#
|
12
|
+
# This program is distributed in the hope that it will be useful,
|
13
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
14
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
15
|
+
# GNU General Public License for more details.
|
16
|
+
#
|
17
|
+
# You should have received a copy of the GNU General Public License
|
18
|
+
# along with this program; if not, write to the Free Software
|
19
|
+
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
20
|
+
#
|
21
|
+
|
22
|
+
module Ronin
|
23
|
+
module Web
|
24
|
+
module Server
|
25
|
+
module Helpers
|
26
|
+
module Files
|
27
|
+
# Directory index files
|
28
|
+
INDICES = ['index.htm', 'index.html']
|
29
|
+
|
30
|
+
#
|
31
|
+
# Sets the content_type based on the extension of a given file.
|
32
|
+
#
|
33
|
+
# @param [String] path
|
34
|
+
# The path to guess the content-type for.
|
35
|
+
#
|
36
|
+
# @return [String]
|
37
|
+
# The MIME content-type of the file.
|
38
|
+
#
|
39
|
+
# @example
|
40
|
+
# content_type_for 'file.html'
|
41
|
+
#
|
42
|
+
# @since 0.2.0
|
43
|
+
#
|
44
|
+
def content_type_for(path)
|
45
|
+
ext = File.extname(path).downcase
|
46
|
+
|
47
|
+
return content_type(ext[1..-1])
|
48
|
+
end
|
49
|
+
|
50
|
+
#
|
51
|
+
# Finds the index file for a given directory.
|
52
|
+
#
|
53
|
+
# @param [String] path
|
54
|
+
# The path of the directory.
|
55
|
+
#
|
56
|
+
# @yield [index_path]
|
57
|
+
# If a block is given, it will be passed the path of the
|
58
|
+
# index file for the given directory.
|
59
|
+
#
|
60
|
+
# @yieldparam [String] index_path
|
61
|
+
# The path to the index file.
|
62
|
+
#
|
63
|
+
# @return [String]
|
64
|
+
# The path to the index file.
|
65
|
+
#
|
66
|
+
# @since 0.2.0
|
67
|
+
#
|
68
|
+
def index_of(path,&block)
|
69
|
+
path = File.expand_path(path)
|
70
|
+
|
71
|
+
Base.indices.each do |name|
|
72
|
+
index = File.join(path,name)
|
73
|
+
|
74
|
+
if File.file?(index)
|
75
|
+
block.call(index) if block
|
76
|
+
return index
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
80
|
+
pass
|
81
|
+
end
|
82
|
+
|
83
|
+
#
|
84
|
+
# Returns a file to the client with the appropriate content-type.
|
85
|
+
#
|
86
|
+
# @param [String] path
|
87
|
+
# The path of the file to return.
|
88
|
+
#
|
89
|
+
# @param [Symbol] custom_content_type
|
90
|
+
# Optional content-type to return the file with.
|
91
|
+
#
|
92
|
+
# @example
|
93
|
+
# return_file 'lol.jpg'
|
94
|
+
#
|
95
|
+
# @example
|
96
|
+
# return_file '/tmp/file', :html
|
97
|
+
#
|
98
|
+
# @since 0.2.0
|
99
|
+
#
|
100
|
+
def return_file(path,custom_content_type=nil)
|
101
|
+
path = File.expand_path(path)
|
102
|
+
|
103
|
+
pass unless File.exists?(path)
|
104
|
+
|
105
|
+
if File.directory?(path)
|
106
|
+
index_of(path) { |index| path = index }
|
107
|
+
end
|
108
|
+
|
109
|
+
if custom_content_type
|
110
|
+
content_type custom_content_type
|
111
|
+
else
|
112
|
+
content_type_for path
|
113
|
+
end
|
114
|
+
|
115
|
+
case request.request_method
|
116
|
+
when 'GET', 'POST'
|
117
|
+
halt 200, File.new(path)
|
118
|
+
else
|
119
|
+
halt 302
|
120
|
+
end
|
121
|
+
end
|
122
|
+
end
|
123
|
+
end
|
124
|
+
end
|
125
|
+
end
|
126
|
+
end
|
@@ -0,0 +1,72 @@
|
|
1
|
+
#
|
2
|
+
# Ronin Web - A Ruby library for Ronin that provides support for web
|
3
|
+
# scraping and spidering functionality.
|
4
|
+
#
|
5
|
+
# Copyright (c) 2006-2009 Hal Brodigan (postmodern.mod3 at gmail.com)
|
6
|
+
#
|
7
|
+
# This program is free software; you can redistribute it and/or modify
|
8
|
+
# it under the terms of the GNU General Public License as published by
|
9
|
+
# the Free Software Foundation; either version 2 of the License, or
|
10
|
+
# (at your option) any later version.
|
11
|
+
#
|
12
|
+
# This program is distributed in the hope that it will be useful,
|
13
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
14
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
15
|
+
# GNU General Public License for more details.
|
16
|
+
#
|
17
|
+
# You should have received a copy of the GNU General Public License
|
18
|
+
# along with this program; if not, write to the Free Software
|
19
|
+
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
20
|
+
#
|
21
|
+
|
22
|
+
module Ronin
|
23
|
+
module Web
|
24
|
+
module Server
|
25
|
+
module Helpers
|
26
|
+
module Hosts
|
27
|
+
#
|
28
|
+
# Calls a given block for requests with matching Host headers.
|
29
|
+
#
|
30
|
+
# @param [Regexp, String] name_or_pattern
|
31
|
+
# The exact name or pattern to match Host headers.
|
32
|
+
#
|
33
|
+
# @yield []
|
34
|
+
# The given block will be called when a request is received
|
35
|
+
# with the matching Host header.
|
36
|
+
#
|
37
|
+
# @example
|
38
|
+
# downloads = 0
|
39
|
+
#
|
40
|
+
# get '/file' do
|
41
|
+
# for_host /^ftp/ do
|
42
|
+
# downloads += 1
|
43
|
+
#
|
44
|
+
# content_type :txt
|
45
|
+
# 'some file'
|
46
|
+
# end
|
47
|
+
#
|
48
|
+
# for_host /^www/ do
|
49
|
+
# downloads += 1
|
50
|
+
#
|
51
|
+
# 'some file'
|
52
|
+
# end
|
53
|
+
#
|
54
|
+
# for_host 'localhost' do
|
55
|
+
# "Total Downloads: #{downloads}"
|
56
|
+
# end
|
57
|
+
# end
|
58
|
+
#
|
59
|
+
# @since 0.2.0
|
60
|
+
#
|
61
|
+
def for_host(name_or_pattern,&block)
|
62
|
+
if name_or_pattern.kind_of?(Regexp)
|
63
|
+
halt(*block.call()) if request.host =~ name_or_pattern
|
64
|
+
else
|
65
|
+
halt(*block.call()) if request.host == name_or_pattern.to_s
|
66
|
+
end
|
67
|
+
end
|
68
|
+
end
|
69
|
+
end
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
@@ -0,0 +1,153 @@
|
|
1
|
+
#
|
2
|
+
# Ronin Web - A Ruby library for Ronin that provides support for web
|
3
|
+
# scraping and spidering functionality.
|
4
|
+
#
|
5
|
+
# Copyright (c) 2006-2009 Hal Brodigan (postmodern.mod3 at gmail.com)
|
6
|
+
#
|
7
|
+
# This program is free software; you can redistribute it and/or modify
|
8
|
+
# it under the terms of the GNU General Public License as published by
|
9
|
+
# the Free Software Foundation; either version 2 of the License, or
|
10
|
+
# (at your option) any later version.
|
11
|
+
#
|
12
|
+
# This program is distributed in the hope that it will be useful,
|
13
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
14
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
15
|
+
# GNU General Public License for more details.
|
16
|
+
#
|
17
|
+
# You should have received a copy of the GNU General Public License
|
18
|
+
# along with this program; if not, write to the Free Software
|
19
|
+
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
20
|
+
#
|
21
|
+
|
22
|
+
require 'ronin/network/http'
|
23
|
+
|
24
|
+
module Ronin
|
25
|
+
module Web
|
26
|
+
module Server
|
27
|
+
module Helpers
|
28
|
+
module Proxy
|
29
|
+
#
|
30
|
+
# Proxies the current request.
|
31
|
+
#
|
32
|
+
# @param [Hash] options
|
33
|
+
# Additional options to use when proxying the request.
|
34
|
+
#
|
35
|
+
# @yield [(response), body]
|
36
|
+
# If a block is given, it will be passed the optional response
|
37
|
+
# of the proxied request and the body received from the
|
38
|
+
# proxied request.
|
39
|
+
#
|
40
|
+
# @yieldparam [Net::HTTP::Response] response
|
41
|
+
# The response of the proxied request.
|
42
|
+
#
|
43
|
+
# @yieldparam [String] body
|
44
|
+
# The body from the proxied request.
|
45
|
+
#
|
46
|
+
# @example
|
47
|
+
# get '/login.php' do
|
48
|
+
# proxy do |body|
|
49
|
+
# body.gsub(/https/,'http')
|
50
|
+
# end
|
51
|
+
# end
|
52
|
+
#
|
53
|
+
# @since 0.2.0
|
54
|
+
#
|
55
|
+
def proxy(options={},&block)
|
56
|
+
default_options = {
|
57
|
+
:host => request.host,
|
58
|
+
:port => request.port,
|
59
|
+
:method => request.request_method,
|
60
|
+
:path => request.path_info,
|
61
|
+
:query => request.query_string,
|
62
|
+
:content_type => request.content_type
|
63
|
+
}
|
64
|
+
|
65
|
+
request.env.each do |name,value|
|
66
|
+
if name =~ /^HTTP/
|
67
|
+
default_options[name.gsub(/^HTTP_/,'').downcase.to_sym] = value
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
71
|
+
options = default_options.merge(options)
|
72
|
+
http_response = Net.http_request(options)
|
73
|
+
|
74
|
+
response = Rack::Response.new(
|
75
|
+
[http_response.body],
|
76
|
+
http_response.code,
|
77
|
+
http_response.to_hash
|
78
|
+
)
|
79
|
+
|
80
|
+
if block
|
81
|
+
old_body = response.body.first
|
82
|
+
|
83
|
+
new_body = if block.arity == 2
|
84
|
+
block.call(response,old_body)
|
85
|
+
else
|
86
|
+
block.call(old_body)
|
87
|
+
end
|
88
|
+
|
89
|
+
response.body[0] = (new_body || old_body)
|
90
|
+
end
|
91
|
+
|
92
|
+
halt(response)
|
93
|
+
end
|
94
|
+
|
95
|
+
#
|
96
|
+
# Proxies the current request.
|
97
|
+
#
|
98
|
+
# @param [Hash] options
|
99
|
+
# Additional options to use when proxying the request.
|
100
|
+
#
|
101
|
+
# @yield [(response), doc]
|
102
|
+
# If a block is given, it will be passed the optional response
|
103
|
+
# of the proxied request and the document representing the
|
104
|
+
# proxied request.
|
105
|
+
#
|
106
|
+
# @yieldparam [Net::HTTP::Response] response
|
107
|
+
# The response of the proxied request.
|
108
|
+
#
|
109
|
+
# @yieldparam [Nokogiri::HTML, Nokogiri::XML] doc
|
110
|
+
# The document representing the proxied request.
|
111
|
+
#
|
112
|
+
# @example
|
113
|
+
# get '/login.php' do
|
114
|
+
# proxy do |doc|
|
115
|
+
# doc.search('form/@action').each do |action|
|
116
|
+
# action.inner_text = action.inner_text.gsub(
|
117
|
+
# /^https/, 'http'
|
118
|
+
# )
|
119
|
+
# end
|
120
|
+
# end
|
121
|
+
# end
|
122
|
+
#
|
123
|
+
# @since 0.2.0
|
124
|
+
#
|
125
|
+
def proxy_doc(options={},&block)
|
126
|
+
proxy(options) do |response,body|
|
127
|
+
case response.content_type
|
128
|
+
when 'text/html'
|
129
|
+
doc = Nokogiri::HTML(body)
|
130
|
+
when 'text/xml'
|
131
|
+
doc = Nokogiri::XML(body)
|
132
|
+
else
|
133
|
+
doc = nil
|
134
|
+
end
|
135
|
+
|
136
|
+
if doc
|
137
|
+
if block
|
138
|
+
if block.arity == 2
|
139
|
+
block.call(response,doc)
|
140
|
+
else
|
141
|
+
block.call(doc)
|
142
|
+
end
|
143
|
+
end
|
144
|
+
|
145
|
+
doc.to_s
|
146
|
+
end
|
147
|
+
end
|
148
|
+
end
|
149
|
+
end
|
150
|
+
end
|
151
|
+
end
|
152
|
+
end
|
153
|
+
end
|
@@ -0,0 +1,36 @@
|
|
1
|
+
#
|
2
|
+
# Ronin Web - A Ruby library for Ronin that provides support for web
|
3
|
+
# scraping and spidering functionality.
|
4
|
+
#
|
5
|
+
# Copyright (c) 2006-2009 Hal Brodigan (postmodern.mod3 at gmail.com)
|
6
|
+
#
|
7
|
+
# This program is free software; you can redistribute it and/or modify
|
8
|
+
# it under the terms of the GNU General Public License as published by
|
9
|
+
# the Free Software Foundation; either version 2 of the License, or
|
10
|
+
# (at your option) any later version.
|
11
|
+
#
|
12
|
+
# This program is distributed in the hope that it will be useful,
|
13
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
14
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
15
|
+
# GNU General Public License for more details.
|
16
|
+
#
|
17
|
+
# You should have received a copy of the GNU General Public License
|
18
|
+
# along with this program; if not, write to the Free Software
|
19
|
+
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
20
|
+
#
|
21
|
+
|
22
|
+
require 'rack/utils'
|
23
|
+
|
24
|
+
module Ronin
|
25
|
+
module Web
|
26
|
+
module Server
|
27
|
+
module Helpers
|
28
|
+
module Rendering
|
29
|
+
include Rack::Utils
|
30
|
+
|
31
|
+
alias h escape_html
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
@@ -0,0 +1,86 @@
|
|
1
|
+
#
|
2
|
+
# Ronin Web - A Ruby library for Ronin that provides support for web
|
3
|
+
# scraping and spidering functionality.
|
4
|
+
#
|
5
|
+
# Copyright (c) 2006-2009 Hal Brodigan (postmodern.mod3 at gmail.com)
|
6
|
+
#
|
7
|
+
# This program is free software; you can redistribute it and/or modify
|
8
|
+
# it under the terms of the GNU General Public License as published by
|
9
|
+
# the Free Software Foundation; either version 2 of the License, or
|
10
|
+
# (at your option) any later version.
|
11
|
+
#
|
12
|
+
# This program is distributed in the hope that it will be useful,
|
13
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
14
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
15
|
+
# GNU General Public License for more details.
|
16
|
+
#
|
17
|
+
# You should have received a copy of the GNU General Public License
|
18
|
+
# along with this program; if not, write to the Free Software
|
19
|
+
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
20
|
+
#
|
21
|
+
|
22
|
+
require 'ronin/web/server/helpers/hosts'
|
23
|
+
|
24
|
+
module Ronin
|
25
|
+
module Web
|
26
|
+
module Server
|
27
|
+
module Hosts
|
28
|
+
def self.included(base)
|
29
|
+
base.module_eval do
|
30
|
+
#
|
31
|
+
# Routes requests with a specific Host header to another
|
32
|
+
# web server.
|
33
|
+
#
|
34
|
+
# @param [String] name
|
35
|
+
# The host-name to route requests for.
|
36
|
+
#
|
37
|
+
# @param [Base, #call] server
|
38
|
+
# The web server to route the requests to.
|
39
|
+
#
|
40
|
+
# @example
|
41
|
+
# MyApp.host 'cdn.evil.com', EvilServer
|
42
|
+
#
|
43
|
+
# @since 0.2.0
|
44
|
+
#
|
45
|
+
def self.host(name,server)
|
46
|
+
name = name.to_s
|
47
|
+
|
48
|
+
before do
|
49
|
+
if request.host == name
|
50
|
+
halt(*server.call(request.env))
|
51
|
+
end
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
#
|
56
|
+
# Routes requests with a matching Host header to another web
|
57
|
+
# server.
|
58
|
+
#
|
59
|
+
# @param [Regexp, String] pattern
|
60
|
+
# The pattern to match Host headers of requests.
|
61
|
+
#
|
62
|
+
# @param [Base, #call] server
|
63
|
+
# The server to route the requests to.
|
64
|
+
#
|
65
|
+
# @example
|
66
|
+
# MyApp.hosts_like /^a[0-9]\./, FileProxy
|
67
|
+
#
|
68
|
+
# @since 0.2.0
|
69
|
+
#
|
70
|
+
def self.hosts_like(pattern,server)
|
71
|
+
before do
|
72
|
+
if request.host.match(pattern)
|
73
|
+
halt(*server.call(request.env))
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
protected
|
79
|
+
|
80
|
+
helpers Ronin::Web::Server::Helpers::Hosts
|
81
|
+
end
|
82
|
+
end
|
83
|
+
end
|
84
|
+
end
|
85
|
+
end
|
86
|
+
end
|