huntr 1.0.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.
Files changed (5) hide show
  1. checksums.yaml +7 -0
  2. data/bin/huntr +4 -0
  3. data/lib/huntr.rb +216 -0
  4. data/lib/huntr/version.rb +3 -0
  5. metadata +188 -0
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: eefda26d1cdf4a3ac01b9e405fd5264ff79d4074
4
+ data.tar.gz: edb3ab836db0ad0dbf47c9aebd90e9d94aaabe58
5
+ SHA512:
6
+ metadata.gz: 26f7591370d316b7d91ce2df46b55c288abdcc5f9030ed3a170b93fdcca97989e09af2f8f43bb77aaaa2611e42d807559dfc74b9a357c245f54b191d472d44c0
7
+ data.tar.gz: cacf78e7031c98b296d0aab071a771297ad133fbc9bb6267c77bd6bf47e964c3880a0682df356c826fd46a7f2009d27c445d295df9bdf0f60a47a39b61175a33
@@ -0,0 +1,4 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'bundler/setup'
4
+ require 'huntr'
@@ -0,0 +1,216 @@
1
+ require "command_lion"
2
+ require "nmapr"
3
+ require "shodan"
4
+ require "yaml"
5
+ require "colorize"
6
+ require "socket"
7
+ require "unirest"
8
+ require "resolv"
9
+ require "ipaddress"
10
+ require "whois-parser"
11
+ require "huntr/version"
12
+
13
+ # The purpose of this libary is provide the tooling required
14
+ # to effectively perform reconnaissance on a given target.
15
+ #
16
+ # A *target* is simply an organization's IP address or domain name.
17
+ #
18
+ module Huntr
19
+
20
+ # Re-usable code to provision different stages of the reconnaissance.
21
+ module Utils
22
+ def self.target_file
23
+ data = {}
24
+ data["domains"] = []
25
+ data["ips"] = []
26
+ data.to_yaml
27
+ end
28
+ end
29
+
30
+ trap("SIGINT") { puts "Stopping huntr!"; exit 0 }
31
+
32
+ CommandLion::App.run do
33
+ if ENV["SHODAN_API_KEY"].nil?
34
+ puts "No shodan API key detected. Will not be able to use shodan!"
35
+ end
36
+ name "Huntr"
37
+ version Huntr::VERSION
38
+ description "A simple reconnaissance command-line application."
39
+
40
+ command :create do
41
+ description "Create a new reconnaissance directory to store relevant information."
42
+ type :string
43
+ before do
44
+ if argument.nil?
45
+ puts "Must provide an argument!"
46
+ exit 1
47
+ end
48
+ if File.directory?(argument)
49
+ puts "Directory already exists!"
50
+ exit 1
51
+ end
52
+ end
53
+ action do
54
+ Dir.mkdir(argument)
55
+ Dir.chdir(argument)
56
+ File.open("target.yaml", "w+") { |f| f.write Utils.target_file }
57
+ end
58
+ after do
59
+ puts "Directory #{argument.colorize(:yellow)} has been created."
60
+ end
61
+ end
62
+
63
+ command :targets do
64
+ description "Add target domains and IP addresses to the target file."
65
+ type :strings
66
+ before do
67
+ if arguments.empty?
68
+ file = YAML.load(File.read("target.yaml"))
69
+ puts "HUNTR TARGETS:"
70
+ file["domains"].each do |domain|
71
+ puts "Domain: #{domain}"
72
+ end
73
+ file["ips"].each do |ip|
74
+ puts "IP: #{ip}"
75
+ end
76
+ exit
77
+ end
78
+ unless File.file?("target.yaml")
79
+ puts "No target file found! Are you in a reconnaissance directory?"
80
+ exit 1
81
+ end
82
+ end
83
+ action do
84
+ file = YAML.load(File.read("target.yaml"))
85
+ arguments.each do |argument|
86
+ if IPAddress.valid?(argument)
87
+ file["ips"] << argument unless file["ips"].include?(argument)
88
+ if names = Resolv.getnames(argument)
89
+ names.each do |name|
90
+ file["domains"] << name unless file["domains"].include?(name)
91
+ end
92
+ end
93
+ elsif ip = IPSocket::getaddress(argument)
94
+ file["domains"] << argument unless file["domains"].include?(argument)
95
+ file["ips"] << ip unless file["ips"].include?(ip)
96
+ end
97
+ File.open("target.yaml", "w") { |f| f.write file.to_yaml }
98
+ end
99
+ end
100
+ end
101
+
102
+ command :delete do
103
+ description "Delete a given reconnaissance directory."
104
+ type :string
105
+ before do
106
+ if argument.nil?
107
+ puts "Must provide an argument!"
108
+ exit 1
109
+ end
110
+ unless File.directory?(argument)
111
+ puts "That directroy doesn't exist, try again!"
112
+ exit 1
113
+ end
114
+ end
115
+ action do
116
+ FileUtils.rm_rf(argument)
117
+ end
118
+ end
119
+
120
+ command :shodan do
121
+ description "Perform shodan query on a given domain or IP address."
122
+ type :string
123
+ before do
124
+ if argument.nil?
125
+ puts "Must provide an argument!"
126
+ exit 1
127
+ end
128
+ unless File.file?("target.yaml")
129
+ puts "No target file found! Are you in a reconnaissance directory?"
130
+ exit 1
131
+ end
132
+ end
133
+ action do
134
+ api = Shodan::Shodan.new(ENV["SHODAN_API_KEY"])
135
+ response = api.host(argument)
136
+ file = YAML.load(File.read("target.yaml"))
137
+ file["shodan"] = {} unless file["shodan"]
138
+ file["shodan"][argument] = response
139
+ File.open("target.yaml", "w") { |f| f.write file.to_yaml }
140
+ puts response.to_yaml
141
+ end
142
+ end
143
+
144
+ command :nmap do
145
+ description "Perform nmap scan on a given domain or IP address."
146
+ type :string
147
+ before do
148
+ if argument.nil?
149
+ puts "Must provide an argument!"
150
+ exit 1
151
+ end
152
+ unless File.file?("target.yaml")
153
+ puts "No target file found! Are you in a reconnaissance directory?"
154
+ exit 1
155
+ end
156
+ end
157
+ action do
158
+ nmap = `nmap #{argument} -vvvv --reason -oN -`
159
+ file = YAML.load(File.read("target.yaml"))
160
+ file["nmap"] = {} unless file["nmap"]
161
+ file["nmap"][argument] = nmap
162
+ File.open("target.yaml", "w") { |f| f.write file.to_yaml }
163
+ puts nmap
164
+ end
165
+ end
166
+
167
+ command :ipinfo do
168
+ description "Get ipinfo.io information on a given domain or IP address."
169
+ type :string
170
+ before do
171
+ if argument.nil?
172
+ puts "Must provide an argument!"
173
+ exit 1
174
+ end
175
+ unless File.file?("target.yaml")
176
+ puts "No target file found! Are you in a reconnaissance directory?"
177
+ exit 1
178
+ end
179
+ end
180
+ action do
181
+ data = Unirest.get('https://ipinfo.io/' + argument).body
182
+ file = YAML.load(File.read("target.yaml"))
183
+ file["ipinfo"] = {} unless file["ipinfo"]
184
+ file["ipinfo"][argument] = data
185
+ File.open("target.yaml", "w") { |f| f.write file.to_yaml }
186
+ puts data.to_yaml
187
+ end
188
+ end
189
+
190
+ command :whois do
191
+ description "Perform nmap scan on a given domain or IP address."
192
+ type :string
193
+ before do
194
+ if argument.nil?
195
+ puts "Must provide an argument!"
196
+ exit 1
197
+ end
198
+ unless File.file?("target.yaml")
199
+ puts "No target file found! Are you in a reconnaissance directory?"
200
+ exit 1
201
+ end
202
+ end
203
+ action do
204
+ data = Whois.whois(argument).to_s
205
+ file = YAML.load(File.read("target.yaml"))
206
+ file["whois"] = {} unless file["whois"]
207
+ file["whois"][argument] = data
208
+ File.open("target.yaml", "w") { |f| f.write file.to_yaml }
209
+ puts data
210
+ end
211
+ end
212
+
213
+
214
+
215
+ end
216
+ end
@@ -0,0 +1,3 @@
1
+ module Huntr
2
+ VERSION = "1.0.0"
3
+ end
metadata ADDED
@@ -0,0 +1,188 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: huntr
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.0
5
+ platform: ruby
6
+ authors:
7
+ - Kent Gruber
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2017-09-21 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: shodan
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: command_lion
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: nmapr
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ">="
46
+ - !ruby/object:Gem::Version
47
+ version: '0'
48
+ type: :runtime
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
55
+ - !ruby/object:Gem::Dependency
56
+ name: colorize
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - ">="
60
+ - !ruby/object:Gem::Version
61
+ version: '0'
62
+ type: :runtime
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - ">="
67
+ - !ruby/object:Gem::Version
68
+ version: '0'
69
+ - !ruby/object:Gem::Dependency
70
+ name: ipaddress
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - ">="
74
+ - !ruby/object:Gem::Version
75
+ version: '0'
76
+ type: :runtime
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - ">="
81
+ - !ruby/object:Gem::Version
82
+ version: '0'
83
+ - !ruby/object:Gem::Dependency
84
+ name: whois-parser
85
+ requirement: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - ">="
88
+ - !ruby/object:Gem::Version
89
+ version: '0'
90
+ type: :runtime
91
+ prerelease: false
92
+ version_requirements: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - ">="
95
+ - !ruby/object:Gem::Version
96
+ version: '0'
97
+ - !ruby/object:Gem::Dependency
98
+ name: unirest
99
+ requirement: !ruby/object:Gem::Requirement
100
+ requirements:
101
+ - - ">="
102
+ - !ruby/object:Gem::Version
103
+ version: '0'
104
+ type: :runtime
105
+ prerelease: false
106
+ version_requirements: !ruby/object:Gem::Requirement
107
+ requirements:
108
+ - - ">="
109
+ - !ruby/object:Gem::Version
110
+ version: '0'
111
+ - !ruby/object:Gem::Dependency
112
+ name: bundler
113
+ requirement: !ruby/object:Gem::Requirement
114
+ requirements:
115
+ - - "~>"
116
+ - !ruby/object:Gem::Version
117
+ version: '1.15'
118
+ type: :development
119
+ prerelease: false
120
+ version_requirements: !ruby/object:Gem::Requirement
121
+ requirements:
122
+ - - "~>"
123
+ - !ruby/object:Gem::Version
124
+ version: '1.15'
125
+ - !ruby/object:Gem::Dependency
126
+ name: rake
127
+ requirement: !ruby/object:Gem::Requirement
128
+ requirements:
129
+ - - "~>"
130
+ - !ruby/object:Gem::Version
131
+ version: '10.0'
132
+ type: :development
133
+ prerelease: false
134
+ version_requirements: !ruby/object:Gem::Requirement
135
+ requirements:
136
+ - - "~>"
137
+ - !ruby/object:Gem::Version
138
+ version: '10.0'
139
+ - !ruby/object:Gem::Dependency
140
+ name: rspec
141
+ requirement: !ruby/object:Gem::Requirement
142
+ requirements:
143
+ - - "~>"
144
+ - !ruby/object:Gem::Version
145
+ version: '3.0'
146
+ type: :development
147
+ prerelease: false
148
+ version_requirements: !ruby/object:Gem::Requirement
149
+ requirements:
150
+ - - "~>"
151
+ - !ruby/object:Gem::Version
152
+ version: '3.0'
153
+ description:
154
+ email:
155
+ - kgruber1@emich.edu
156
+ executables:
157
+ - huntr
158
+ extensions: []
159
+ extra_rdoc_files: []
160
+ files:
161
+ - bin/huntr
162
+ - lib/huntr.rb
163
+ - lib/huntr/version.rb
164
+ homepage: https://github.com/picatz/huntr
165
+ licenses:
166
+ - MIT
167
+ metadata: {}
168
+ post_install_message:
169
+ rdoc_options: []
170
+ require_paths:
171
+ - lib
172
+ required_ruby_version: !ruby/object:Gem::Requirement
173
+ requirements:
174
+ - - ">="
175
+ - !ruby/object:Gem::Version
176
+ version: '0'
177
+ required_rubygems_version: !ruby/object:Gem::Requirement
178
+ requirements:
179
+ - - ">="
180
+ - !ruby/object:Gem::Version
181
+ version: '0'
182
+ requirements: []
183
+ rubyforge_project:
184
+ rubygems_version: 2.6.12
185
+ signing_key:
186
+ specification_version: 4
187
+ summary: A simple reconnaissance command-line application.
188
+ test_files: []