qlive 0.1.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.
@@ -0,0 +1,4 @@
1
+ *.gem
2
+ .bundle
3
+ Gemfile.lock
4
+ pkg/*
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source "http://rubygems.org"
2
+
3
+ # Specify your gem's dependencies in qlive.gemspec
4
+ gemspec
@@ -0,0 +1,44 @@
1
+ # Qlive
2
+
3
+ Qlive is rack middleware for running qunit javascript tests against a live server.
4
+ It is mainly intended to be used for testing javascript-heavy, single-page web applications
5
+ (like those built using backbone, angularjs, emberjs, etc.)
6
+
7
+ Qlive inserts the qunit framework and your test sources into the page's response.
8
+ Qlive provides hooks for setting server state before the request is processed by your app, so you can
9
+ do things like popuplate content with your favorite fixtures library (like factory_girl) and log in a user for the qunit test page.
10
+
11
+
12
+ ## Benefits:
13
+
14
+ * Precisely set fixture content and user login state for your qunit tests
15
+ * Insert qunit tests and any custom html into live pages generated by your server
16
+ * Run the same qunit tests in a browser or headlessly, alongside your normal integration test suite. (When used with Ruby on Rails and the [qlive-headless](https://github.com/proxv/qlive-headless) gem.)
17
+
18
+
19
+ ## Installation
20
+
21
+ ### Ruby on Rails
22
+
23
+ If you are using Ruby on Rails, you should use one of these gems:
24
+
25
+ * [qlive-rails](https://github.com/proxv/qlive-rails). Configures most of qlive for you and provides an index page linking to your test suites.
26
+ * [qlive-headless](https://github.com/proxv/qlive-headless). Run your qunit tests headlessly as part of your rspec or test suite. (Builds on qlive-rails.)
27
+
28
+
29
+ ### Non-rails:
30
+
31
+ * Configure base path, the top of the directory tree that contains your qlive suites. (See suites section below)
32
+ <pre>Qlive.setup[:base_path] = /absolute/path/to/qunit/tests/tree</pre>
33
+ * Configure url prefix for serving your test sources in this tree.
34
+ * The default is /qlive/sources.
35
+ * So a request to /qlive/sources/my_suite/test-stuff.js would need to resolve to #{base_path}/my_suite/test-stuff.js
36
+ * Mount Qlive::Rack late enough for it to access the database or whatever else the suite needs for preparing page state
37
+
38
+ todo: improve/complete non-rails instructions should anyone want to use it.
39
+
40
+
41
+ ## Usage
42
+
43
+ See [suites wiki page](https://github.com/proxv/qlive/wiki/qlive-suites).
44
+
@@ -0,0 +1 @@
1
+ require "bundler/gem_tasks"
@@ -0,0 +1,8 @@
1
+ require "qlive/version"
2
+ require "qlive/setup"
3
+ require "qlive/registry"
4
+ require "qlive/suite"
5
+ require "qlive/rack"
6
+
7
+ module Qlive
8
+ end
Binary file
@@ -0,0 +1,21 @@
1
+ module Qlive
2
+ class DevReload
3
+
4
+ def initialize(app, opts={})
5
+ @app = app
6
+ end
7
+
8
+ def call(env)
9
+ self.class.reload_main if env['QUERY_STRING'].include?('qlive=')
10
+ @app.call(env)
11
+ end
12
+
13
+
14
+ def self.reload_main
15
+ load "#{File.expand_path('../rack.rb', __FILE__)}"
16
+ load "#{File.expand_path('../qunit_assets.rb', __FILE__)}"
17
+ load "#{File.expand_path('../suite.rb', __FILE__)}"
18
+ load "#{File.expand_path('../registry.rb', __FILE__)}"
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,75 @@
1
+ module Qlive
2
+ module QunitAssets
3
+
4
+ # default is to serve assets for qlive-rails. Override if your qunit assets are elsewhere.
5
+ def prepare_assets
6
+ before_body_close.concat(
7
+ qunit_html_structure |
8
+ qunit_support_assets |
9
+ qunit_framework |
10
+ qunit_disable_autostart |
11
+ qunit_javascript_test_sources |
12
+ qunit_finalize
13
+ )
14
+ end
15
+
16
+ def qunit_framework
17
+ [
18
+ '<link rel="stylesheet" href="/qlive/qunit-1.9.0/qunit.css" type="text/css" media="screen" />',
19
+ '<script type="text/javascript" src="/qlive/qunit-1.9.0/qunit.js"></script>'
20
+ ]
21
+ end
22
+
23
+ def qunit_support_assets
24
+ support_relpath = Qlive.setup[:js_support_relpath]
25
+ path = "#{Qlive.setup[:base_path]}#{support_relpath}"
26
+ if (File.exist?(path))
27
+ glob_script_tags(path, "#{Qlive.setup[:url_prefix] || ''}#{support_relpath}")
28
+ else
29
+ []
30
+ end
31
+ end
32
+
33
+ def qunit_javascript_test_sources
34
+ test_path = File.expand_path('..', self.meta_data[:path])
35
+ url_prefix = "#{Qlive.setup[:url_prefix] || ''}/#{suite_name}"
36
+ glob_script_tags(test_path, url_prefix)
37
+ end
38
+
39
+ def qunit_html_structure
40
+ [
41
+ '<div class="qlive-structure">',
42
+ "<h1 id='qunit-header'>Qlive Suite: #{suite_name}</h1>",
43
+ '<h2 id="qunit-banner"></h2>',
44
+ '<div id="qunit-testrunner-toolbar"></div>',
45
+ '<h2 id="qunit-userAgent"></h2>',
46
+ '<ol id="qunit-tests"></ol>',
47
+ '<div id="qunit-fixture">test markup, will be hidden</div>',
48
+ '<div id="display-proxified-tests"></div>',
49
+ '</div>'
50
+ ]
51
+ end
52
+
53
+ def qunit_disable_autostart
54
+ [
55
+ '<script>QUnit.config.autostart = false;</script>'
56
+ ]
57
+ end
58
+
59
+ def qunit_finalize
60
+ [
61
+ '<script>QUnit.done = function(failed, passed, total, runtime) { window.qunitComplete = true; };</script>'
62
+ ]
63
+ end
64
+
65
+ def glob_script_tags(src_base_path, url_prefix)
66
+ sources = Dir.glob("#{src_base_path}#{src_base_path.end_with?('/') ? '' : '/'}**/*.js").sort.flatten
67
+ sources.map do |src|
68
+ src = src.to_s
69
+ href = "#{url_prefix}#{src.sub(src_base_path, '')}"
70
+ "<script type='text/javascript' src='#{href}'></script>"
71
+ end
72
+ end
73
+
74
+ end
75
+ end
@@ -0,0 +1,76 @@
1
+ require 'qlive/setup'
2
+ require 'qlive/registry'
3
+
4
+ module Qlive
5
+ class Rack
6
+
7
+ def initialize(app, opts)
8
+ Qlive.setup.merge!(opts)
9
+ @app = app
10
+ @regex_qs = /#{opts[:magic_param] || 'qlive'}=([^&\?]+)/i
11
+ Registry.find_suites
12
+ end
13
+
14
+ def call(env)
15
+ suite = nil
16
+ if env["REQUEST_METHOD"].upcase == 'GET'
17
+ m = @regex_qs.match(env['QUERY_STRING'])
18
+ if m && m.length > 0
19
+ request = ::Rack::Request.new(env)
20
+ suite = Registry.build_suite(m[1])
21
+ suite.prepare({
22
+ :request => request,
23
+ :session => env["rack.session"]
24
+ })
25
+ suite.before_each_request(request)
26
+ end
27
+ end
28
+
29
+ status, headers, body = @app.call(env)
30
+
31
+ if suite
32
+ inject_html(:after_open, :head, suite.html_after_head_open, body, headers)
33
+ inject_html(:before_close, :head, suite.html_before_head_close, body, headers)
34
+ inject_html(:after_open, :body, suite.html_after_body_open, body, headers)
35
+ inject_html(:before_close, :body, suite.html_before_body_close, body, headers)
36
+ end
37
+
38
+ [status, headers, body]
39
+ end
40
+
41
+
42
+ protected
43
+
44
+
45
+ private
46
+
47
+ def inject_html(place, tag_type, html, body, headers)
48
+ return if !html || html.length == 0
49
+ html = html.join("\n") if html.kind_of?(Array)
50
+
51
+ if place == :before_close
52
+ regex = /<\/#{tag_type}>/i
53
+ substitution = "\n#{html}\n</#{tag_type}>"
54
+ else # :after_open
55
+ regex = /<#{tag_type}[^>]*>/i
56
+ substitution = "\\0\n#{html}\n"
57
+ end
58
+
59
+ body.each do |part|
60
+ if part =~ regex
61
+ part.sub!(regex, substitution)
62
+ fix_content_length(headers, html)
63
+ break
64
+ end
65
+ end
66
+ end
67
+
68
+ def fix_content_length(headers, inserted_text)
69
+ if headers['Content-Length'] && inserted_text && inserted_text.length > 0
70
+ headers['Content-Length'] = (headers['Content-Length'].to_i + inserted_text.length).to_s
71
+ end
72
+ end
73
+
74
+
75
+ end
76
+ end
@@ -0,0 +1,72 @@
1
+ require 'qlive/setup'
2
+ require 'qlive/suite'
3
+
4
+ module Qlive
5
+ module Registry
6
+
7
+ unless String.public_method_defined?(:underscore)
8
+ String.class_eval do
9
+ def underscore
10
+ self.gsub(/(.)([A-Z])/,'\1_\2').downcase
11
+ end
12
+ end
13
+ end
14
+
15
+
16
+ $qlive_all_suites ||= {}
17
+ #@all_suites ||= {} # use module instance variable
18
+
19
+ def self.suites
20
+ $qlive_all_suites
21
+ end
22
+
23
+
24
+ def self.find_suites
25
+ suites = {}
26
+ base_path = Qlive.setup[:base_path]
27
+ sources = Dir.glob("#{base_path}#{base_path.end_with?('/') ? '' : '/'}**/*_qlive.rb").sort.flatten
28
+ sources.each do |path|
29
+ path = path.to_s
30
+ name = self.extract_suite_name_from_path(path)
31
+ suites[name] ||= {}
32
+ suites[name][:path] = path
33
+ end
34
+
35
+ $qlive_all_suites = suites
36
+ end
37
+
38
+ def self.build_suite(suite_name)
39
+ meta = Registry.suites[suite_name]
40
+ unless meta || Qlive.setup[:skip_suite_reloader]
41
+ Registry.find_suites
42
+ meta = Registry.suites[suite_name]
43
+ end
44
+ raise "Qlive Suite not found: #{suite_name}" unless meta
45
+ load meta[:path]
46
+ klass = meta[:klass]
47
+ raise "Qlive could not find class for suite: #{suite_name}" unless klass
48
+ klass.new
49
+ end
50
+
51
+ def self.register_class(klass)
52
+ name = self.extract_suite_name_from_class(klass)
53
+ meta = Registry.suites[name] || {}
54
+ meta.merge!(:name => name,
55
+ :klass => klass)
56
+ meta
57
+ end
58
+
59
+
60
+ def self.extract_suite_name_from_path(path)
61
+ res = path.split('/')[-1]
62
+ res = res.split('.')[0]
63
+ res = res.downcase.sub(/_qlive$/, '')
64
+ res
65
+ end
66
+
67
+ def self.extract_suite_name_from_class(klass)
68
+ klass.name.underscore.sub(/_qlive$/, '')
69
+ end
70
+
71
+ end
72
+ end
@@ -0,0 +1,14 @@
1
+ module Qlive
2
+ @qlive_config = {
3
+ :base_path => nil, # required. qlive-rails sets this to "#{Rails.root}/spec/qunits"
4
+ :url_prefix => '/qlive/sources',
5
+ :magic_param => 'qlive',
6
+ :js_support_relpath => '/qunit_support', # gets loaded before all of the qunit js tests
7
+ :skip_suite_reloader => false, # when true, does not re-crawl base_path looking for suites whenever a suite_name is missing
8
+ :gem_dev_mode => true
9
+ }
10
+
11
+ def self.setup
12
+ @qlive_config
13
+ end
14
+ end
@@ -0,0 +1,67 @@
1
+ require 'qlive/setup'
2
+ require 'qlive/qunit_assets'
3
+
4
+ module Qlive
5
+ module Suite
6
+ include QunitAssets
7
+
8
+ attr_reader :request, :session
9
+
10
+ InsertionPoints ||= [ 'after_head_open', 'before_head_close', 'after_body_open', 'before_body_close']
11
+
12
+ def self.included(base)
13
+ meta = Registry.register_class(base)
14
+ base.class_eval do
15
+ class << self
16
+ attr_reader :suite_meta_data
17
+ end
18
+ end
19
+ base.instance_variable_set(:@suite_meta_data, meta)
20
+
21
+ InsertionPoints.each do |place|
22
+ attr_accessor place
23
+
24
+ define_method "html_#{place}" do
25
+ htmls = instance_variable_get("@#{place}")
26
+ has_content = htmls.length > 0
27
+ htmls.unshift "\n<!-- Begin Qlive Insertions (#{place}) -->" if has_content
28
+ htmls << "<!-- End Qlive Insertions (#{place}) -->\n" if has_content
29
+ htmls.join("\n")
30
+ end
31
+ end
32
+ end
33
+
34
+
35
+
36
+ def prepare(args={})
37
+ @session = args[:session]
38
+ @request = args[:request]
39
+ InsertionPoints.each do |place|
40
+ instance_variable_set("@#{place}", [ ])
41
+ end
42
+ prepare_assets
43
+ end
44
+
45
+
46
+ def name
47
+ self.meta_data[:name]
48
+ end
49
+
50
+ def meta_data
51
+ self.class.suite_meta_data
52
+ end
53
+
54
+
55
+ def suite_name
56
+ self.name
57
+ end
58
+
59
+
60
+ protected
61
+
62
+ def before_each_request(rack_request)
63
+ # override to create server-side fixtures here for the qlive request
64
+ end
65
+
66
+ end
67
+ end
@@ -0,0 +1,3 @@
1
+ module Qlive
2
+ VERSION = "0.1.0"
3
+ end
@@ -0,0 +1,23 @@
1
+ # -*- encoding: utf-8 -*-
2
+ $:.push File.expand_path("../lib", __FILE__)
3
+ require "qlive/version"
4
+
5
+ Gem::Specification.new do |s|
6
+ s.name = "qlive"
7
+ s.version = Qlive::VERSION
8
+ s.authors = ["ProxV"]
9
+ s.email = ["support@proxv.com"]
10
+ s.homepage = "https://github.com/proxv/qlive/"
11
+ s.summary = "run qunit tests against actual back-end server with prepared test fixtures"
12
+ s.description = s.summary
13
+
14
+ s.rubyforge_project = "qlive"
15
+
16
+ s.files = `git ls-files`.split("\n")
17
+ s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
18
+ s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
19
+ s.require_paths = ["lib"]
20
+
21
+ s.add_dependency 'rack', '~> 1.4'
22
+ s.add_development_dependency "rspec", '~> 2.8.0'
23
+ end
Binary file
@@ -0,0 +1,5 @@
1
+ $(document).ready(function() {
2
+ nextTick(function() {
3
+ QUnit.start();
4
+ });
5
+ });
@@ -0,0 +1,9 @@
1
+ class FancyWorkflowQlive
2
+ include Qlive::Suite
3
+ # include QliveHelper
4
+
5
+ def before_each_request(rack_request)
6
+ # login_as Factory(:user)
7
+ end
8
+
9
+ end
@@ -0,0 +1,5 @@
1
+ $(document).ready(function() {
2
+ module("post-new-recipe.js");
3
+
4
+ test("creation pages", 26, window.ns.goodQunitTestFunction);
5
+ });
@@ -0,0 +1,5 @@
1
+ $(document).ready(function() {
2
+ module("verify-creds.js");
3
+
4
+ test("permissions", 3, window.ns.permissionCheckB);
5
+ });
@@ -0,0 +1,51 @@
1
+ require File.expand_path("../../spec_helper.rb", __FILE__)
2
+
3
+ describe Qlive::Rack do
4
+ class HappyGoLuckyQlive
5
+ include Qlive::Suite
6
+
7
+ def before_each_request(rack_request)
8
+ rack_request.session[:logged_in_as] = 1255
9
+ end
10
+ end
11
+
12
+ before(:each) do
13
+ suite = HappyGoLuckyQlive.new
14
+ Qlive::Registry.stub!(:build_suite).and_return suite
15
+ end
16
+
17
+ let(:environment) { Rack::MockRequest.env_for('/webapp/tinfoiled?qlive=happy_go_lucky#frontpage') }
18
+ let(:application) { lambda{|env| [200, {'Content-Type' => 'text/html'}, [ html_page ]]} }
19
+ let(:middleware) do
20
+ Qlive::Rack.new(application, { :base_path => fixtures_base_path })
21
+ end
22
+
23
+ it "should insert qunit test resources when magic_param is present in query string" do
24
+ body = middleware.call(environment)[2].join('')
25
+ body.should match(/qunit\.js/)
26
+ end
27
+
28
+ it "should allow suite to modify session data" do
29
+ middleware.call(environment)
30
+ environment['rack.session'].should == {:logged_in_as => 1255} # see before_each_request
31
+ end
32
+
33
+ #todo: describe "magic param" do
34
+ # it "should do nothing when magic param is missing"
35
+ # it "should permit configuration of magic_param to use a query param other than 'qlive'"
36
+ #end
37
+
38
+
39
+ def html_page
40
+ <<-END.gsub(/^\s+/, '')
41
+ <html><head>
42
+ <title>Why Jasmine Is Annoying</title>
43
+ <script src='/app-ui.js'></script>
44
+ </head>
45
+ <body class="webapp">
46
+ <div class="app-content-holder"></div>
47
+ </body></html>
48
+ END
49
+ end
50
+
51
+ end
@@ -0,0 +1,18 @@
1
+ require File.expand_path("../../spec_helper.rb", __FILE__)
2
+
3
+ describe Qlive::Registry, "find_suites" do
4
+ it "should find qlive suites" do
5
+ suites = Qlive::Registry.find_suites
6
+ suites.length.should > 0
7
+ suites['fancy_workflow'].should_not be_nil
8
+ end
9
+ end
10
+
11
+ describe Qlive::Registry, "build_suite" do
12
+
13
+ it "should instantiate suite and add class to meta data registry" do
14
+ suite = Qlive::Registry.build_suite('fancy_workflow')
15
+ suite.class.name.should == 'FancyWorkflowQlive'
16
+
17
+ end
18
+ end
@@ -0,0 +1,60 @@
1
+ require File.expand_path("../../spec_helper.rb", __FILE__)
2
+
3
+ describe Qlive::Suite do
4
+ class BlueSuite
5
+ include Qlive::Suite
6
+
7
+ def before_each_request(rack_request)
8
+ @pretend_factory_girl = true
9
+ @pretend_devise_user_login = true
10
+ end
11
+ end
12
+
13
+ let(:suite) do
14
+ suite = BlueSuite.new
15
+ suite.prepare
16
+ suite.after_head_open << '<script> doSomethingEarly();</script>'
17
+ suite
18
+ end
19
+
20
+ it "should provide array of desired html at all insertion points" do
21
+ suite.after_head_open.length.should == 1
22
+ suite.html_after_head_open.should match(/doSomethingEarly/) # it also adds before & after comments
23
+ suite.html_before_body_close.should match(/qunit\.js/)
24
+ end
25
+
26
+ end
27
+
28
+
29
+ describe Qlive::Suite, "qunit source" do
30
+ before(:each) do
31
+ @suite = Qlive::Registry.build_suite('fancy_workflow')
32
+ @suite.prepare
33
+ end
34
+
35
+ it "should insert qunit resources and all js files in the same directory as the suite" do
36
+ source_tags = @suite.qunit_javascript_test_sources
37
+ source_tags.length.should == 2
38
+ source_tags.join("\n").should match(/#{Regexp.escape("/qlive/sources/fancy_workflow/post-new-recipe.js")}/)
39
+ end
40
+
41
+ end
42
+
43
+
44
+ describe Qlive::Suite, "insertion helper methods" do
45
+ class GreenSuite
46
+ include Qlive::Suite
47
+ end
48
+
49
+ let(:suite) { GreenSuite.new }
50
+
51
+ it "should not mess up metacoding too much" do
52
+ a = GreenSuite.new
53
+ b = GreenSuite.new
54
+ a.after_head_open = [ 8 ]
55
+ b.after_head_open = [ 9 ]
56
+ a.after_head_open[0].should == 8
57
+ b.after_head_open[0].should == 9
58
+ end
59
+ end
60
+
@@ -0,0 +1,2 @@
1
+ --color
2
+ --backtrace
@@ -0,0 +1,14 @@
1
+ QliveHome = File.expand_path('../..', __FILE__)
2
+ require 'rack/mock'
3
+ require "#{QliveHome}/lib/qlive"
4
+
5
+ def fixtures_base_path
6
+ "#{QliveHome}/spec/fixtures"
7
+ end
8
+
9
+
10
+ RSpec.configure do |config|
11
+ Qlive.setup[:base_path] = fixtures_base_path
12
+
13
+ end
14
+
metadata ADDED
@@ -0,0 +1,100 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: qlive
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - ProxV
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2012-07-26 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: rack
16
+ requirement: &2152313360 !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ~>
20
+ - !ruby/object:Gem::Version
21
+ version: '1.4'
22
+ type: :runtime
23
+ prerelease: false
24
+ version_requirements: *2152313360
25
+ - !ruby/object:Gem::Dependency
26
+ name: rspec
27
+ requirement: &2152310660 !ruby/object:Gem::Requirement
28
+ none: false
29
+ requirements:
30
+ - - ~>
31
+ - !ruby/object:Gem::Version
32
+ version: 2.8.0
33
+ type: :development
34
+ prerelease: false
35
+ version_requirements: *2152310660
36
+ description: run qunit tests against actual back-end server with prepared test fixtures
37
+ email:
38
+ - support@proxv.com
39
+ executables: []
40
+ extensions: []
41
+ extra_rdoc_files: []
42
+ files:
43
+ - .gitignore
44
+ - Gemfile
45
+ - README.md
46
+ - Rakefile
47
+ - lib/qlive.rb
48
+ - lib/qlive/.DS_Store
49
+ - lib/qlive/dev_reload.rb
50
+ - lib/qlive/qunit_assets.rb
51
+ - lib/qlive/rack.rb
52
+ - lib/qlive/registry.rb
53
+ - lib/qlive/setup.rb
54
+ - lib/qlive/suite.rb
55
+ - lib/qlive/version.rb
56
+ - qlive.gemspec
57
+ - spec/.DS_Store
58
+ - spec/fixtures/qunit_support/start-qunit.js
59
+ - spec/fixtures/suites/fancy_workflow/fancy_workflow_qlive.rb
60
+ - spec/fixtures/suites/fancy_workflow/post-new-recipe.js
61
+ - spec/fixtures/suites/fancy_workflow/verify-creds.js
62
+ - spec/qlive/rack_spec.rb
63
+ - spec/qlive/registry_spec.rb
64
+ - spec/qlive/suite_spec.rb
65
+ - spec/spec.opts
66
+ - spec/spec_helper.rb
67
+ homepage: https://github.com/proxv/qlive/
68
+ licenses: []
69
+ post_install_message:
70
+ rdoc_options: []
71
+ require_paths:
72
+ - lib
73
+ required_ruby_version: !ruby/object:Gem::Requirement
74
+ none: false
75
+ requirements:
76
+ - - ! '>='
77
+ - !ruby/object:Gem::Version
78
+ version: '0'
79
+ required_rubygems_version: !ruby/object:Gem::Requirement
80
+ none: false
81
+ requirements:
82
+ - - ! '>='
83
+ - !ruby/object:Gem::Version
84
+ version: '0'
85
+ requirements: []
86
+ rubyforge_project: qlive
87
+ rubygems_version: 1.8.10
88
+ signing_key:
89
+ specification_version: 3
90
+ summary: run qunit tests against actual back-end server with prepared test fixtures
91
+ test_files:
92
+ - spec/fixtures/qunit_support/start-qunit.js
93
+ - spec/fixtures/suites/fancy_workflow/fancy_workflow_qlive.rb
94
+ - spec/fixtures/suites/fancy_workflow/post-new-recipe.js
95
+ - spec/fixtures/suites/fancy_workflow/verify-creds.js
96
+ - spec/qlive/rack_spec.rb
97
+ - spec/qlive/registry_spec.rb
98
+ - spec/qlive/suite_spec.rb
99
+ - spec/spec.opts
100
+ - spec/spec_helper.rb