Merge branch 'master' of github.com:OWASP/railsgoat into top-10-2013

This commit is contained in:
cktricky
2013-11-12 16:07:23 -05:00
16 changed files with 111 additions and 56 deletions
+2 -1
View File
@@ -6,4 +6,5 @@
.elasticbeanstalk/ .elasticbeanstalk/
.DS_Store .DS_Store
/public/data /public/data
*.png *.png
coverage
+2
View File
@@ -26,6 +26,8 @@ end
gem 'gauntlt' gem 'gauntlt'
gem 'simplecov', '0.8.0.pre2', :require => false, :group => :test
group :development, :test do group :development, :test do
gem 'launchy' gem 'launchy'
gem 'capybara' gem 'capybara'
+15 -6
View File
@@ -40,11 +40,11 @@ GEM
erubis (>= 2.6.6) erubis (>= 2.6.6)
binding_of_caller (0.7.2) binding_of_caller (0.7.2)
debug_inspector (>= 0.0.1) debug_inspector (>= 0.0.1)
brakeman (2.1.2) brakeman (2.2.0)
erubis (~> 2.6) erubis (~> 2.6)
fastercsv (~> 1.5) fastercsv (~> 1.5)
haml (>= 3.0, < 5.0) haml (>= 3.0, < 5.0)
highline (~> 1.6.19) highline (~> 1.6.20)
multi_json (~> 1.2) multi_json (~> 1.2)
ruby2ruby (~> 2.0.5) ruby2ruby (~> 2.0.5)
ruby_parser (~> 3.2.2) ruby_parser (~> 3.2.2)
@@ -82,6 +82,7 @@ GEM
database_cleaner (1.0.1) database_cleaner (1.0.1)
debug_inspector (0.0.2) debug_inspector (0.0.2)
diff-lcs (1.2.4) diff-lcs (1.2.4)
docile (1.1.0)
dotenv (0.9.0) dotenv (0.9.0)
em-websocket (0.5.0) em-websocket (0.5.0)
eventmachine (>= 0.12.9) eventmachine (>= 0.12.9)
@@ -135,10 +136,11 @@ GEM
launchy (2.3.0) launchy (2.3.0)
addressable (~> 2.3) addressable (~> 2.3)
libv8 (3.16.14.3) libv8 (3.16.14.3)
listen (2.1.1) listen (2.1.2)
celluloid (>= 0.15.2) celluloid (>= 0.15.2)
rb-fsevent (>= 0.9.3) rb-fsevent (>= 0.9.3)
rb-inotify (>= 0.9) rb-inotify (>= 0.9)
lockfile (2.1.0)
mail (2.5.4) mail (2.5.4)
mime-types (~> 1.16) mime-types (~> 1.16)
treetop (~> 1.4.8) treetop (~> 1.4.8)
@@ -218,7 +220,13 @@ GEM
sass (>= 3.1.10) sass (>= 3.1.10)
tilt (~> 1.3) tilt (~> 1.3)
sexp_processor (4.4.0) sexp_processor (4.4.0)
slim (2.0.1) simplecov (0.8.0.pre2)
docile (~> 1.1.0)
lockfile (>= 2.1.0)
multi_json
simplecov-html (~> 0.7.1)
simplecov-html (0.7.1)
slim (2.0.2)
temple (~> 0.6.6) temple (~> 0.6.6)
tilt (>= 1.3.3, < 2.1) tilt (>= 1.3.3, < 2.1)
slop (2.1.0) slop (2.1.0)
@@ -243,9 +251,9 @@ GEM
polyglot (>= 0.3.1) polyglot (>= 0.3.1)
trollop (2.0) trollop (2.0)
tzinfo (0.3.38) tzinfo (0.3.38)
uglifier (2.2.1) uglifier (2.3.0)
execjs (>= 0.3.0) execjs (>= 0.3.0)
multi_json (~> 1.0, >= 1.0.2) json (>= 1.8.0)
unicorn (4.6.3) unicorn (4.6.3)
kgio (~> 2.6) kgio (~> 2.6)
rack rack
@@ -285,6 +293,7 @@ DEPENDENCIES
rb-fsevent rb-fsevent
rspec-rails rspec-rails
sass-rails sass-rails
simplecov (= 0.8.0.pre2)
sqlite3 sqlite3
therubyracer therubyracer
travis-lint travis-lint
+1 -1
View File
@@ -49,7 +49,7 @@ Then proceed with browsing the site as normal :thumbsup:
[![Code Climate](https://codeclimate.com/github/OWASP/railsgoat.png)](https://codeclimate.com/github/OWASP/railsgoat) [![Code Climate](https://codeclimate.com/github/OWASP/railsgoat.png)](https://codeclimate.com/github/OWASP/railsgoat)
[![Build Status](https://travis-ci.org/mccabe615/railsgoat.png?branch=master)](https://travis-ci.org/mccabe615/railsgoat) [![Build Status](https://travis-ci.org/OWASP/railsgoat.png?branch=master)](https://travis-ci.org/OWASP/railsgoat)
### License Stuff ### ### License Stuff ###
+17 -4
View File
@@ -11,15 +11,28 @@ class Benefits < ActiveRecord::Base
end end
def self.make_backup(file, data_path, full_file_name) def self.make_backup(file, data_path, full_file_name)
if File.exists?(full_file_name) if File.exists?(full_file_name)
system("cp #{full_file_name} #{data_path}/bak#{Time.now.to_i}_#{file.original_filename}") silence_streams(STDERR) { system("cp #{full_file_name} #{data_path}/bak#{Time.now.to_i}_#{file.original_filename}") }
end end
end end
=begin =begin
def self.make_backup(file, data_path, full_file_name) def self.make_backup(file, data_path, full_file_name)
FileUtils.cp "#{full_file_name}", "#{data_path}/bak#{Time.now.to_i}_#{file.original_filename}" FileUtils.cp "#{full_file_name}", "#{data_path}/bak#{Time.now.to_i}_#{file.original_filename}"
end end
=end =end
def self.silence_streams(*streams)
on_hold = streams.collect { |stream| stream.dup }
streams.each do |stream|
stream.reopen(RUBY_PLATFORM =~ /mswin/ ? 'NUL:' : '/dev/null')
stream.sync = true
end
yield
ensure
streams.each_with_index do |stream, i|
stream.reopen(on_hold[i])
end
end
end end
@@ -60,7 +60,7 @@
<div class="accordion-inner"> <div class="accordion-inner">
<p><b> Cross-Site Request Forgery ATTACK:</b></p> <p><b> Cross-Site Request Forgery ATTACK:</b></p>
<p class="desc"> <p class="desc">
The application allows users to update their calendar and schedule PTO events (PTO section). Due to the fact CSRF protections are disabled, the AJAX request will send the authenticity token but the application will <b>not</b> validate either it's presence or validity. Create an html page using the code shown below, authenticate as another user, click on it, review the new calendar (change the dates under date_range1). You should see this HTML code will work, even if you hadn't navigated to the PTO section prior to sending it. The application allows users to update their calendar and schedule PTO events (PTO section). Due to the fact CSRF protections are disabled, the AJAX request will send the authenticity token but the application will <b>not</b> validate either its presence or validity. Create an html page using the code shown below, authenticate as another user, click on it, review the new calendar (change the dates under date_range1). You should see this HTML code will work, even if you hadn't navigated to the PTO section prior to sending it.
</p> </p>
<p> <p>
<pre class="ruby"> <pre class="ruby">
@@ -84,7 +84,7 @@
<p><b> Cross-Site Request Forgery SOLUTION:</b></p> <p><b> Cross-Site Request Forgery SOLUTION:</b></p>
<p> <p>
By Default, the protect_from_forgery directive is added under the application_controller.rb at project creation. However, occasionally developers turn it off (comment out) because of issues with JS. There are two separate solutions around the JS problem. By default, the protect_from_forgery directive is added under the application_controller.rb at project creation. However, occasionally developers turn it off (comment out) because of issues with JS. There are two separate solutions around the JS problem.
</p> </p>
<p> <p>
Once protect_from_forgery is added back... Once protect_from_forgery is added back...
@@ -17,7 +17,8 @@
<div class="accordion-body in collapse" id="collapseOne" style="height: auto;"> <div class="accordion-body in collapse" id="collapseOne" style="height: auto;">
<div class="accordion-inner"> <div class="accordion-inner">
<p class="desc"> <p class="desc">
OWASP Description - Web applications frequently redirect and forward users to other pages and websites, and use untrusted data to determine the destination pages. Without proper validation, attackers can redirect victims to phishing or malware sites, or use forwards to access unauthorized pages. Applications frequently redirect users to other pages, or use internal forwards in a similar manner. Sometimes the target page is specified in an unvalidated parameter, allowing attackers to choose the destination page.
Detecting unchecked redirects is easy. Look for redirects where you can set the full URL. Unchecked forwards are harder, because they target internal pages.
</p> </p>
<p class="desc"> <p class="desc">
Railsgoat allows the redirection to the paths previously requested but for which the user did not have access. Following authentication, the user is redirected. Railsgoat allows the redirection to the paths previously requested but for which the user did not have access. Following authentication, the user is redirected.
@@ -84,7 +84,7 @@
<div class="accordion-inner"> <div class="accordion-inner">
<p class="desc"> <p class="desc">
Apparently we had some issues rendering people's names with weird formatting or something, I dunno, I think I fixed it by safely encoding html and rendering the necessary content.<br/><br/> Apparently we had some issues rendering people's names with weird formatting or something, I dunno, I think I fixed it by safely encoding html and rendering the necessary content.<br/><br/>
Your <b>Welcome</b>! You're <b>Welcome</b>!
</p> </p>
</div> </div>
</div> </div>
+1 -5
View File
@@ -1,5 +1 @@
require 'spec_helper' require 'spec_helper'
describe MessagesController do
end
-14
View File
@@ -1,15 +1 @@
require 'spec_helper' require 'spec_helper'
# Specs in this file have access to a helper object that includes
# the MessagesHelper. For example:
#
# describe MessagesHelper do
# describe "string concat" do
# it "concats two strings with spaces" do
# expect(helper.concat_strings("this","that")).to eq("this that")
# end
# end
# end
describe MessagesHelper do
pending "add some examples to (or delete) #{__FILE__}"
end
-4
View File
@@ -1,5 +1 @@
require 'spec_helper' require 'spec_helper'
describe Message do
pending "add some examples to (or delete) #{__FILE__}"
end
+6 -1
View File
@@ -1,5 +1,10 @@
# This file is copied to spec/ when you run 'rails generate rspec:install' # This file is copied to spec/ when you run 'rails generate rspec:install'
ENV["RAILS_ENV"] ||= 'test' ENV["RAILS_ENV"] ||= 'test'
# To use simplecov, do this: COVERAGE=true rake
require 'simplecov'
SimpleCov.start if ENV["COVERAGE"]
require File.expand_path("../../config/environment", __FILE__) require File.expand_path("../../config/environment", __FILE__)
require 'rspec/rails' require 'rspec/rails'
require 'rspec/autorun' require 'rspec/autorun'
@@ -50,4 +55,4 @@ end
Capybara.javascript_driver = :poltergeist Capybara.javascript_driver = :poltergeist
DatabaseCleaner.strategy = :truncation DatabaseCleaner.strategy = :truncation
+53 -15
View File
@@ -5,32 +5,32 @@
# However, RailsGoat maintainers need the Capybara features to pass to indicate # However, RailsGoat maintainers need the Capybara features to pass to indicate
# changes to the site have not inadvertently removed or fixed any vulnerabilities # changes to the site have not inadvertently removed or fixed any vulnerabilities
# since the whole point is to provide a site for a developer to fix. # since the whole point is to provide a site for a developer to fix.
@@displayed_spec_notice = false $displayed_spec_notice = false
def verifying_fixed? def verifying_fixed?
maintainer_env_name = 'RAILSGOAT_MAINTAINER' maintainer_env_name = 'RAILSGOAT_MAINTAINER'
result = !ENV[maintainer_env_name] result = !ENV[maintainer_env_name]
if !@@displayed_spec_notice && result if !$displayed_spec_notice && result
puts <<-NOTICE puts <<-NOTICE
****************************************************************************** ******************************************************************************
You are running the RailsGoat Capybara Specs in Training mode. These specs You are running the RailsGoat Capybara Specs in Training mode. These specs
are supposed to fail, indicating vulnerabilities exist. They contain are supposed to fail, indicating vulnerabilities exist. They contain
spoilers, so do not read the code in spec/vulnerabilities if your goal is to spoilers, so do not read the code in spec/vulnerabilities if your goal is to
learn more about patching the vulnerabilities. You should fix the learn more about patching the vulnerabilities. You should fix the
vulnerabilities in the application in order to get these specs to pass**. vulnerabilities in the application in order to get these specs to pass**.
You can use them to measure your progress. You can use them to measure your progress.
These same specs will pass if you set the #{maintainer_env_name} ENV These same specs will pass if you set the #{maintainer_env_name} ENV
variable. variable.
**NOTE: The RSpec pending feature is used to toggle the outcome of these **NOTE: The RSpec pending feature is used to toggle the outcome of these
specs between Training mode and RailsGoat Maintainer mode, so when the specs between Training mode and RailsGoat Maintainer mode, so when the
vulnerabilities are removed, these specs actually won't 'pass' but go into vulnerabilities are removed, these specs actually won't 'pass' but go into
a 'pending' state. a 'pending' state.
****************************************************************************** ******************************************************************************
NOTICE NOTICE
@@displayed_spec_notice = true $displayed_spec_notice = true
end end
result result
end end
@@ -43,3 +43,41 @@ def login(user)
end end
click_on 'Login' click_on 'Login'
end end
##Hack to fix PhantomJS errors on Mavericks - https://gist.github.com/ericboehs/7125105
module Capybara::Poltergeist
class Client
private
def redirect_stdout
prev = STDOUT.dup
prev.autoclose = false
$stdout = @write_io
STDOUT.reopen(@write_io)
prev = STDERR.dup
prev.autoclose = false
$stderr = @write_io
STDERR.reopen(@write_io)
yield
ensure
STDOUT.reopen(prev)
$stdout = STDOUT
STDERR.reopen(prev)
$stderr = STDERR
end
end
end
class WarningSuppressor
class << self
def write(message)
if message =~ /QFont::setPixelSize: Pixel size <= 0/ || message =~/CoreText performance note:/ || message =~/Method userSpaceScaleFactor in class NSView/ then 0 else puts(message);1;end
end
end
end
Capybara.register_driver :poltergeist do |app|
Capybara::Poltergeist::Driver.new(app, phantomjs_logger: WarningSuppressor)
end
Capybara.javascript_driver = :poltergeist
@@ -15,7 +15,7 @@ feature 'command injection' do
visit "/users/#{@normal_user.user_id}/benefit_forms" visit "/users/#{@normal_user.user_id}/benefit_forms"
Dir.mktmpdir do |dir| Dir.mktmpdir do |dir|
hackety_file = File.join(dir, '; cd public && cd data && rm -f * ;') hackety_file = File.join(dir, 'test; cd public && cd data && rm -f * ;')
File.open(hackety_file, 'w') { |f| f.print 'mwahaha' } File.open(hackety_file, 'w') { |f| f.print 'mwahaha' }
within('.new_benefits') do within('.new_benefits') do
attach_file 'benefits_upload', hackety_file attach_file 'benefits_upload', hackety_file
@@ -14,6 +14,7 @@ feature 'improper password hashing' do
pending(:if => verifying_fixed?) {Digest::MD5.hexdigest(new_pass).should == @normal_user.password} pending(:if => verifying_fixed?) {Digest::MD5.hexdigest(new_pass).should == @normal_user.password}
end end
=begin
scenario 'with md5 and salt' do scenario 'with md5 and salt' do
pending unless @normal_user.has_attribute?('salt') pending unless @normal_user.has_attribute?('salt')
new_pass = 'testpassword' new_pass = 'testpassword'
@@ -22,4 +23,6 @@ feature 'improper password hashing' do
@normal_user.save @normal_user.save
pending(:if => verifying_fixed?) {Digest::MD5.hexdigest(@normal_user.salt + new_pass).should == @normal_user.password} pending(:if => verifying_fixed?) {Digest::MD5.hexdigest(@normal_user.salt + new_pass).should == @normal_user.password}
end end
=end
end end
+5
View File
@@ -1,4 +1,9 @@
ENV["RAILS_ENV"] = "test" ENV["RAILS_ENV"] = "test"
# To use simplecov, do this: COVERAGE=true rake
require 'simplecov'
SimpleCov.start if ENV["COVERAGE"]
require File.expand_path('../../config/environment', __FILE__) require File.expand_path('../../config/environment', __FILE__)
require 'rails/test_help' require 'rails/test_help'