Skip to content

Commit

Permalink
refactored unit tests quite a bit. Added JS and CSS fixtures.
Browse files Browse the repository at this point in the history
  • Loading branch information
tobie committed Sep 3, 2008
1 parent 81de0e3 commit cf5d180
Show file tree
Hide file tree
Showing 19 changed files with 886 additions and 844 deletions.
25 changes: 11 additions & 14 deletions Rakefile
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ PROTOTYPE_VERSION = '1.6.0.2'

task :default => [:dist, :dist_helper, :package, :clean_package_source]

desc "Builds the distribution"
desc "Builds the distribution."
task :dist do
$:.unshift File.join(PROTOTYPE_ROOT, 'lib')
require 'protodoc'
Expand All @@ -21,7 +21,7 @@ task :dist do
end
end

desc "Builds the updating helper"
desc "Builds the updating helper."
task :dist_helper do
$:.unshift File.join(PROTOTYPE_ROOT, 'lib')
require 'protodoc'
Expand All @@ -45,8 +45,8 @@ Rake::PackageTask.new('prototype', PROTOTYPE_VERSION) do |package|
)
end

desc "Builds the distribution, runs the JavaScript unit tests and collects their results."
task :test => [:build_tests, :dist, :test_units]
desc "Builds the distribution and the test suite, runs the tests and collects their results."
task :test => [:dist, :test_units]

require 'test/lib/jstest'
desc "Runs all the JavaScript unit tests and collects the results"
Expand All @@ -58,19 +58,16 @@ JavaScriptTestTask.new(:test_units) do |t|
t.mount("/dist")
t.mount("/test")

Dir["test/unit/tmp/*_test.html"].sort.each do |test_file|
tests = testcases ? { :url => "/#{test_file}", :testcases => testcases } : "/#{test_file}"
test_filename = test_file[/.*\/(.+?)_test\.html/, 1]
t.run(tests) unless tests_to_run && !tests_to_run.include?(test_filename)
Dir["test/unit/*_test.js"].each do |file|
TestBuilder.new(file).render
test_file = File.basename(file, ".js")
test_name = test_file.sub("_test", "")
unless tests_to_run && !tests_to_run.include?(test_name)
t.run("/test/unit/tmp/#{test_file}.html", testcases)
end
end

%w( safari firefox ie konqueror opera ).each do |browser|
t.browser(browser.to_sym) unless browsers_to_test && !browsers_to_test.include?(browser)
end
end

task :build_tests do
Dir["test/unit/*_test.js"].each do |test_file|
TestBuilder.new(test_file).render
end
end
155 changes: 102 additions & 53 deletions test/lib/jstest.rb
Original file line number Diff line number Diff line change
Expand Up @@ -278,12 +278,7 @@ def initialize(name=:test)

@server = WEBrick::HTTPServer.new(:Port => 4711) # TODO: make port configurable
@server.mount_proc("/results") do |req, res|
@queue.push({
:tests => req.query['tests'].to_i,
:assertions => req.query['assertions'].to_i,
:failures => req.query['failures'].to_i,
:errors => req.query['errors'].to_i
})
@queue.push(req)
res.body = "OK"
end
@server.mount("/response", BasicServlet)
Expand All @@ -303,62 +298,49 @@ def define
@browsers.each do |browser|
if browser.supported?
t0 = Time.now
results = {:tests => 0, :assertions => 0, :failures => 0, :errors => 0}
errors = []
failures = []
test_suite_results = TestSuiteResults.new

browser.setup
puts "\nStarted tests in #{browser}"
puts "\nStarted tests in #{browser}."

@tests.each do |test|
params = "resultsURL=http://localhost:4711/results&t=" + ("%.6f" % Time.now.to_f)
if test.is_a?(Hash)
params << "&tests=#{test[:testcases]}" if test[:testcases]
test = test[:url]
end
browser.visit("http://localhost:4711#{test}?#{params}")

result = @queue.pop
result.each { |k, v| results[k] += v }
value = "."

if result[:failures] > 0
value = "F"
failures.push(test)
end

if result[:errors] > 0
value = "E"
errors.push(test)
end

print value
browser.visit(get_url(test))
results = TestResults.new(@queue.pop.query)
print results
test_suite_results.add(results, test[:url])
end

puts "\nFinished in #{(Time.now - t0).round.to_s} seconds."
puts " Failures: #{failures.join(', ')}" unless failures.empty?
puts " Errors: #{errors.join(', ')}" unless errors.empty?
puts "#{results[:tests]} tests, #{results[:assertions]} assertions, #{results[:failures]} failures, #{results[:errors]} errors"
print "\nFinished in #{Time.now - t0} seconds."
print test_suite_results
browser.teardown
else
puts "\nSkipping #{browser}, not supported on this OS"
puts "\nSkipping #{browser}, not supported on this OS."
end
end

@server.shutdown
t.join
end
end


def get_url(test)
params = "resultsURL=http://localhost:4711/results&t=" + ("%.6f" % Time.now.to_f)
params << "&tests=#{test[:testcases]}" unless test[:testcases] == :all
"http://localhost:4711#{test[:url]}?#{params}"
end

def mount(path, dir=nil)
dir = Dir.pwd + path unless dir

# don't cache anything in our tests
@server.mount(path, NonCachingFileHandler, dir)
end

# test should be specified as a url or as a hash of the form
# {:url => "url", :testcases => "testFoo,testBar"}
def run(test)
@tests<<test
# test should be specified as a hash of the form
# {:url => "url", :testcases => "testFoo,testBar"}.
# specifying :testcases is optional
def run(url, testcases = :all)
@tests << { :url => url, :testcases => testcases }
end

def browser(browser)
Expand All @@ -382,37 +364,104 @@ def browser(browser)
end
end
class TestResults
attr_reader :tests, :assertions, :failures, :errors
def initialize(query)
@tests = query['tests'].to_i
@assertions = query['assertions'].to_i
@failures = query['failures'].to_i
@errors = query['errors'].to_i
end
def error?
@errors > 0
end
def failure?
@failures > 0
end
def to_s
return "E" if error?
return "F" if failure?
"."
end
end
class TestSuiteResults
def initialize
@tests = 0
@assertions = 0
@failures = 0
@errors = 0
@error_files = []
@failure_files = []
end
def add(result, file)
@tests += result.tests
@assertions += result.assertions
@failures += result.failures
@errors += result.errors
@error_files.push(file) if result.error?
@failure_files.push(file) if result.failure?
end
def error?
@errors > 0
end
def failure?
@failures > 0
end
def to_s
str = ""
str << "\n Failures: #{@failure_files.join(', ')}" if failure?
str << "\n Errors: #{@error_files.join(', ')}" if error?
"#{str}\n#{summary}\n\n"
end
def summary
"#{@tests} tests, #{@assertions} assertions, #{@failures} failures, #{@errors} errors."
end
end
class TestBuilder
UNITTEST_DIR = File.expand_path('test')
TEMPLATE = File.join(UNITTEST_DIR, 'lib', 'template.erb')
FIXTURES_EXTENSION = "html"
FIXTURES_DIR = File.join(UNITTEST_DIR, 'unit', 'fixtures')
def initialize(filename)
@filename = filename
@js_filename = File.basename(@filename)
@basename = @js_filename.sub("_test.js", "")
@fixtures_filename = "#{@basename}.#{FIXTURES_EXTENSION}"
@title = @basename.gsub("_", " ").strip.capitalize
@html_fixtures = html_fixtures
@js_fixtures_filename = external_fixtures("js")
@css_fixtures_filename = external_fixtures("css")
end
def find_fixtures
@fixtures = ""
file = File.join(FIXTURES_DIR, @fixtures_filename)
if File.exists?(file)
File.open(file).each { |line| @fixtures << line }
end
def html_fixtures
content = ""
file = File.join(FIXTURES_DIR, "#{@basename}.html")
File.open(file).each { |l| content << l } if File.exists?(file)
content
end
def external_fixtures(type)
filename = "#{@basename}.#{type}"
File.exists?(File.join(FIXTURES_DIR, filename)) ? filename : nil
end
def render
find_fixtures
File.open(destination, "w+") do |file|
file << ERB.new(IO.read(TEMPLATE), nil, "%").result(binding)
end
end
def destination
basename = File.basename(@filename, ".js")
File.join(UNITTEST_DIR, 'unit', 'tmp', "#{basename}.html")
filename = File.basename(@filename, ".js")
File.join(UNITTEST_DIR, 'unit', 'tmp', "#{filename}.html")
end
end
23 changes: 16 additions & 7 deletions test/lib/template.erb
Original file line number Diff line number Diff line change
Expand Up @@ -6,26 +6,35 @@
<meta http-equiv="content-type" content="text/html; charset=utf-8" />
<script type="text/javascript" charset="utf-8">
var eventResults = {};
var originalElement = Element;
var originalElement = window.Element;
</script>
<script src="../../../dist/prototype.js" type="text/javascript"></script>
<script src="../../lib/unittest.js" type="text/javascript"></script>
<script src="../<%= @js_filename %>" type="text/javascript"></script>

<link rel="stylesheet" href="../../test.css" type="text/css" />

<% if @css_fixtures_filename %>
<link rel="stylesheet" href="../fixtures/<%= @css_fixtures_filename %>" type="text/css" charset="utf-8" />
<% end %>
<% if @js_fixtures_filename %>
<script src="../fixtures/<%= @js_fixtures_filename %>" type="text/javascript" charset="utf-8"></script>
<% end %>

<script src="../<%= @js_filename %>" type="text/javascript"></script>
</head>
<body>
<h1>Prototype Unit test file</h1>
<h2><%= @title %></h2>

<!-- This file is programmatically generated. Do not attempt to modify it. Instead, modify <%= @fixtures_filename %> -->

<!-- Log output -->
<!-- Log output start -->
<div id="testlog"></div>
<!-- Log output end -->

<!-- Fixtures start -->
<%= @fixtures %>
<!-- Fixtures end -->
<!-- HTML Fixtures start -->
<%= @html_fixtures %>
<!-- HTML Fixtures end -->
</body>
</html>
<script type="text/javascript" charset="utf-8">
Expand Down
43 changes: 0 additions & 43 deletions test/unit/ajax_test.js
Original file line number Diff line number Diff line change
@@ -1,38 +1,3 @@
var Fixtures = {
js: {
responseBody: '$("content").update("<H2>Hello world!</H2>");',
'Content-Type': ' text/javascript '
},

html: {
responseBody: "Pack my box with <em>five dozen</em> liquor jugs! " +
"Oh, how <strong>quickly</strong> daft jumping zebras vex..."
},

xml: {
responseBody: '<?xml version="1.0" encoding="UTF-8" ?><name attr="foo">bar</name>',
'Content-Type': 'application/xml'
},

json: {
responseBody: '{\n\r"test": 123}',
'Content-Type': 'application/json'
},

jsonWithoutContentType: {
responseBody: '{"test": 123}'
},

invalidJson: {
responseBody: '{});window.attacked = true;({}',
'Content-Type': 'application/json'
},

headerJson: {
'X-JSON': '{"test": "hello #éà"}'
}
};

var extendDefault = function(options) {
return Object.extend({
asynchronous: false,
Expand All @@ -41,14 +6,6 @@ var extendDefault = function(options) {
}, options);
};

var responderCounter = 0;

// lowercase comparison because of MSIE which presents HTML tags in uppercase
var sentence = ("Pack my box with <em>five dozen</em> liquor jugs! " +
"Oh, how <strong>quickly</strong> daft jumping zebras vex...").toLowerCase();

var message = 'You must be running your tests from rake to test this feature.';

new Test.Unit.Runner({
setup: function() {
$('content').update('');
Expand Down
Loading

0 comments on commit cf5d180

Please sign in to comment.