chemistrykit 3.8.1 → 3.9.0.rc1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (59) hide show
  1. data/.gitignore +1 -0
  2. data/CHANGELOG.md +15 -5
  3. data/Gemfile +4 -0
  4. data/README.md +13 -1
  5. data/Rakefile +3 -3
  6. data/chemistrykit.gemspec +7 -3
  7. data/features/brew.feature +1 -1
  8. data/features/chemists.feature +56 -1
  9. data/features/concurrency.feature +2 -2
  10. data/features/exit_status.feature +1 -0
  11. data/features/logging.feature +88 -85
  12. data/features/reporting.feature +105 -0
  13. data/features/step_definitions/steps.rb +4 -4
  14. data/features/support/env.rb +1 -1
  15. data/features/tags.feature +1 -0
  16. data/lib/chemistrykit/chemist.rb +6 -1
  17. data/lib/chemistrykit/chemist/repository/csv_chemist_repository.rb +1 -1
  18. data/lib/chemistrykit/cli/cli.rb +33 -12
  19. data/lib/chemistrykit/configuration.rb +2 -2
  20. data/lib/chemistrykit/formula/formula_lab.rb +13 -0
  21. data/lib/chemistrykit/{parallel_tests_mods.rb → parallel_tests/rspec/runner.rb} +5 -5
  22. data/lib/chemistrykit/reporting/html_report_assembler.rb +170 -0
  23. data/lib/chemistrykit/rspec/html_formatter.rb +241 -0
  24. data/lib/chemistrykit/rspec/j_unit_formatter.rb +124 -0
  25. data/report/config.rb +28 -0
  26. data/report/index.html +213 -0
  27. data/report/javascripts/foundation/foundation.abide.js +194 -0
  28. data/report/javascripts/foundation/foundation.alerts.js +52 -0
  29. data/report/javascripts/foundation/foundation.clearing.js +516 -0
  30. data/report/javascripts/foundation/foundation.cookie.js +74 -0
  31. data/report/javascripts/foundation/foundation.dropdown.js +177 -0
  32. data/report/javascripts/foundation/foundation.forms.js +533 -0
  33. data/report/javascripts/foundation/foundation.interchange.js +280 -0
  34. data/report/javascripts/foundation/foundation.joyride.js +850 -0
  35. data/report/javascripts/foundation/foundation.js +440 -0
  36. data/report/javascripts/foundation/foundation.magellan.js +135 -0
  37. data/report/javascripts/foundation/foundation.orbit.js +412 -0
  38. data/report/javascripts/foundation/foundation.placeholder.js +179 -0
  39. data/report/javascripts/foundation/foundation.reveal.js +330 -0
  40. data/report/javascripts/foundation/foundation.section.js +400 -0
  41. data/report/javascripts/foundation/foundation.tooltips.js +208 -0
  42. data/report/javascripts/foundation/foundation.topbar.js +300 -0
  43. data/report/javascripts/vendor/custom.modernizr.js +4 -0
  44. data/report/javascripts/vendor/jquery.js +9789 -0
  45. data/report/sass/_normalize.scss +402 -0
  46. data/report/sass/_settings.scss +1301 -0
  47. data/report/sass/app.scss +571 -0
  48. data/report/stylesheets/app.css +3636 -0
  49. data/spec/integration/lib/chemistrykit/formula/formula_lab_spec.rb +26 -2
  50. data/spec/integration/lib/chemistrykit/reporting/html_reporting_assembler_spec.rb +18 -0
  51. data/spec/support/evidence/results_0.html +30 -0
  52. data/spec/support/evidence/results_1.html +27 -0
  53. data/spec/unit/lib/chemistrykit/chemist/repository/csv_chemist_repository_spec.rb +15 -2
  54. data/spec/unit/lib/chemistrykit/chemist_spec.rb +17 -1
  55. data/spec/unit/lib/chemistrykit/configuration_spec.rb +2 -2
  56. data/spec/unit/lib/chemistrykit/formula/formula_lab_spec.rb +7 -0
  57. data/spec/unit/lib/chemistrykit/reporting/html_reporting_assembler_spec.rb +22 -0
  58. metadata +94 -13
  59. data/lib/chemistrykit/j_unit.rb +0 -121
@@ -0,0 +1,208 @@
1
+ /*jslint unparam: true, browser: true, indent: 2 */
2
+
3
+ ;(function ($, window, document, undefined) {
4
+ 'use strict';
5
+
6
+ Foundation.libs.tooltips = {
7
+ name : 'tooltips',
8
+
9
+ version : '4.2.2',
10
+
11
+ settings : {
12
+ selector : '.has-tip',
13
+ additionalInheritableClasses : [],
14
+ tooltipClass : '.tooltip',
15
+ appendTo: 'body',
16
+ 'disable-for-touch': false,
17
+ tipTemplate : function (selector, content) {
18
+ return '<span data-selector="' + selector + '" class="'
19
+ + Foundation.libs.tooltips.settings.tooltipClass.substring(1)
20
+ + '">' + content + '<span class="nub"></span></span>';
21
+ }
22
+ },
23
+
24
+ cache : {},
25
+
26
+ init : function (scope, method, options) {
27
+ Foundation.inherit(this, 'data_options');
28
+ var self = this;
29
+
30
+ if (typeof method === 'object') {
31
+ $.extend(true, this.settings, method);
32
+ } else if (typeof options !== 'undefined') {
33
+ $.extend(true, this.settings, options);
34
+ }
35
+
36
+ if (typeof method !== 'string') {
37
+ if (Modernizr.touch) {
38
+ $(this.scope)
39
+ .on('click.fndtn.tooltip touchstart.fndtn.tooltip touchend.fndtn.tooltip',
40
+ '[data-tooltip]', function (e) {
41
+ var settings = $.extend({}, self.settings, self.data_options($(this)));
42
+ if (!settings['disable-for-touch']) {
43
+ e.preventDefault();
44
+ $(settings.tooltipClass).hide();
45
+ self.showOrCreateTip($(this));
46
+ }
47
+ })
48
+ .on('click.fndtn.tooltip touchstart.fndtn.tooltip touchend.fndtn.tooltip',
49
+ this.settings.tooltipClass, function (e) {
50
+ e.preventDefault();
51
+ $(this).fadeOut(150);
52
+ });
53
+ } else {
54
+ $(this.scope)
55
+ .on('mouseenter.fndtn.tooltip mouseleave.fndtn.tooltip',
56
+ '[data-tooltip]', function (e) {
57
+ var $this = $(this);
58
+
59
+ if (/enter|over/i.test(e.type)) {
60
+ self.showOrCreateTip($this);
61
+ } else if (e.type === 'mouseout' || e.type === 'mouseleave') {
62
+ self.hide($this);
63
+ }
64
+ });
65
+ }
66
+
67
+ // $(this.scope).data('fndtn-tooltips', true);
68
+ } else {
69
+ return this[method].call(this, options);
70
+ }
71
+
72
+ },
73
+
74
+ showOrCreateTip : function ($target) {
75
+ var $tip = this.getTip($target);
76
+
77
+ if ($tip && $tip.length > 0) {
78
+ return this.show($target);
79
+ }
80
+
81
+ return this.create($target);
82
+ },
83
+
84
+ getTip : function ($target) {
85
+ var selector = this.selector($target),
86
+ tip = null;
87
+
88
+ if (selector) {
89
+ tip = $('span[data-selector="' + selector + '"]' + this.settings.tooltipClass);
90
+ }
91
+
92
+ return (typeof tip === 'object') ? tip : false;
93
+ },
94
+
95
+ selector : function ($target) {
96
+ var id = $target.attr('id'),
97
+ dataSelector = $target.attr('data-tooltip') || $target.attr('data-selector');
98
+
99
+ if ((id && id.length < 1 || !id) && typeof dataSelector != 'string') {
100
+ dataSelector = 'tooltip' + Math.random().toString(36).substring(7);
101
+ $target.attr('data-selector', dataSelector);
102
+ }
103
+
104
+ return (id && id.length > 0) ? id : dataSelector;
105
+ },
106
+
107
+ create : function ($target) {
108
+ var $tip = $(this.settings.tipTemplate(this.selector($target), $('<div></div>').html($target.attr('title')).html())),
109
+ classes = this.inheritable_classes($target);
110
+
111
+ $tip.addClass(classes).appendTo(this.settings.appendTo);
112
+ if (Modernizr.touch) {
113
+ $tip.append('<span class="tap-to-close">tap to close </span>');
114
+ }
115
+ $target.removeAttr('title').attr('title','');
116
+ this.show($target);
117
+ },
118
+
119
+ reposition : function (target, tip, classes) {
120
+ var width, nub, nubHeight, nubWidth, column, objPos;
121
+
122
+ tip.css('visibility', 'hidden').show();
123
+
124
+ width = target.data('width');
125
+ nub = tip.children('.nub');
126
+ nubHeight = this.outerHeight(nub);
127
+ nubWidth = this.outerHeight(nub);
128
+
129
+ objPos = function (obj, top, right, bottom, left, width) {
130
+ return obj.css({
131
+ 'top' : (top) ? top : 'auto',
132
+ 'bottom' : (bottom) ? bottom : 'auto',
133
+ 'left' : (left) ? left : 'auto',
134
+ 'right' : (right) ? right : 'auto',
135
+ 'width' : (width) ? width : 'auto'
136
+ }).end();
137
+ };
138
+
139
+ objPos(tip, (target.offset().top + this.outerHeight(target) + 10), 'auto', 'auto', target.offset().left, width);
140
+
141
+ if ($(window).width() < 767) {
142
+ objPos(tip, (target.offset().top + this.outerHeight(target) + 10), 'auto', 'auto', 12.5, $(this.scope).width());
143
+ tip.addClass('tip-override');
144
+ objPos(nub, -nubHeight, 'auto', 'auto', target.offset().left);
145
+ } else {
146
+ var left = target.offset().left;
147
+ if (Foundation.rtl) {
148
+ left = target.offset().left + target.offset().width - this.outerWidth(tip);
149
+ }
150
+ objPos(tip, (target.offset().top + this.outerHeight(target) + 10), 'auto', 'auto', left, width);
151
+ tip.removeClass('tip-override');
152
+ if (classes && classes.indexOf('tip-top') > -1) {
153
+ objPos(tip, (target.offset().top - this.outerHeight(tip)), 'auto', 'auto', left, width)
154
+ .removeClass('tip-override');
155
+ } else if (classes && classes.indexOf('tip-left') > -1) {
156
+ objPos(tip, (target.offset().top + (this.outerHeight(target) / 2) - nubHeight*2.5), 'auto', 'auto', (target.offset().left - this.outerWidth(tip) - nubHeight), width)
157
+ .removeClass('tip-override');
158
+ } else if (classes && classes.indexOf('tip-right') > -1) {
159
+ objPos(tip, (target.offset().top + (this.outerHeight(target) / 2) - nubHeight*2.5), 'auto', 'auto', (target.offset().left + this.outerWidth(target) + nubHeight), width)
160
+ .removeClass('tip-override');
161
+ }
162
+ }
163
+
164
+ tip.css('visibility', 'visible').hide();
165
+ },
166
+
167
+ inheritable_classes : function (target) {
168
+ var inheritables = ['tip-top', 'tip-left', 'tip-bottom', 'tip-right', 'noradius'].concat(this.settings.additionalInheritableClasses),
169
+ classes = target.attr('class'),
170
+ filtered = classes ? $.map(classes.split(' '), function (el, i) {
171
+ if ($.inArray(el, inheritables) !== -1) {
172
+ return el;
173
+ }
174
+ }).join(' ') : '';
175
+
176
+ return $.trim(filtered);
177
+ },
178
+
179
+ show : function ($target) {
180
+ var $tip = this.getTip($target);
181
+
182
+ this.reposition($target, $tip, $target.attr('class'));
183
+ $tip.fadeIn(150);
184
+ },
185
+
186
+ hide : function ($target) {
187
+ var $tip = this.getTip($target);
188
+
189
+ $tip.fadeOut(150);
190
+ },
191
+
192
+ // deprecate reload
193
+ reload : function () {
194
+ var $self = $(this);
195
+
196
+ return ($self.data('fndtn-tooltips')) ? $self.foundationTooltips('destroy').foundationTooltips('init') : $self.foundationTooltips('init');
197
+ },
198
+
199
+ off : function () {
200
+ $(this.scope).off('.fndtn.tooltip');
201
+ $(this.settings.tooltipClass).each(function (i) {
202
+ $('[data-tooltip]').get(i).attr('title', $(this).text());
203
+ }).remove();
204
+ },
205
+
206
+ reflow : function () {}
207
+ };
208
+ }(Foundation.zj, this, this.document));
@@ -0,0 +1,300 @@
1
+ /*jslint unparam: true, browser: true, indent: 2 */
2
+
3
+ ;(function ($, window, document, undefined) {
4
+ 'use strict';
5
+
6
+ Foundation.libs.topbar = {
7
+ name : 'topbar',
8
+
9
+ version: '4.3.1',
10
+
11
+ settings : {
12
+ index : 0,
13
+ stickyClass : 'sticky',
14
+ custom_back_text: true,
15
+ back_text: 'Back',
16
+ is_hover: true,
17
+ mobile_show_parent_link: true,
18
+ scrolltop : true, // jump to top when sticky nav menu toggle is clicked
19
+ init : false
20
+ },
21
+
22
+ init : function (section, method, options) {
23
+ Foundation.inherit(this, 'data_options');
24
+ var self = this;
25
+
26
+ if (typeof method === 'object') {
27
+ $.extend(true, this.settings, method);
28
+ } else if (typeof options !== 'undefined') {
29
+ $.extend(true, this.settings, options);
30
+ }
31
+
32
+ if (typeof method !== 'string') {
33
+
34
+ $('.top-bar, [data-topbar]').each(function () {
35
+ $.extend(true, self.settings, self.data_options($(this)));
36
+ self.settings.$w = $(window);
37
+ self.settings.$topbar = $(this);
38
+ self.settings.$section = self.settings.$topbar.find('section');
39
+ self.settings.$titlebar = self.settings.$topbar.children('ul').first();
40
+ self.settings.$topbar.data('index', 0);
41
+
42
+ var breakpoint = $("<div class='top-bar-js-breakpoint'/>").insertAfter(self.settings.$topbar);
43
+ self.settings.breakPoint = breakpoint.width();
44
+ breakpoint.remove();
45
+
46
+ self.assemble();
47
+
48
+ if (self.settings.is_hover) {
49
+ self.settings.$topbar.find('.has-dropdown').addClass('not-click');
50
+ }
51
+
52
+ if (self.settings.$topbar.parent().hasClass('fixed')) {
53
+ $('body').css('padding-top', self.outerHeight(self.settings.$topbar));
54
+ }
55
+ });
56
+
57
+ if (!self.settings.init) {
58
+ this.events();
59
+ }
60
+
61
+ return this.settings.init;
62
+ } else {
63
+ // fire method
64
+ return this[method].call(this, options);
65
+ }
66
+ },
67
+
68
+ timer : null,
69
+
70
+ events : function () {
71
+ var self = this;
72
+ var offst = this.outerHeight($('.top-bar, [data-topbar]'));
73
+ $(this.scope)
74
+ .off('.fndtn.topbar')
75
+ .on('click.fndtn.topbar', '.top-bar .toggle-topbar, [data-topbar] .toggle-topbar', function (e) {
76
+ var topbar = $(this).closest('.top-bar, [data-topbar]'),
77
+ section = topbar.find('section, .section'),
78
+ titlebar = topbar.children('ul').first();
79
+
80
+ e.preventDefault();
81
+
82
+ if (self.breakpoint()) {
83
+ if (!self.rtl) {
84
+ section.css({left: '0%'});
85
+ section.find('>.name').css({left: '100%'});
86
+ } else {
87
+ section.css({right: '0%'});
88
+ section.find('>.name').css({right: '100%'});
89
+ }
90
+
91
+ section.find('li.moved').removeClass('moved');
92
+ topbar.data('index', 0);
93
+
94
+ topbar
95
+ .toggleClass('expanded')
96
+ .css('height', '');
97
+ }
98
+
99
+ if (!topbar.hasClass('expanded')) {
100
+ if (topbar.hasClass('fixed')) {
101
+ topbar.parent().addClass('fixed');
102
+ topbar.removeClass('fixed');
103
+ $('body').css('padding-top',offst);
104
+ }
105
+ } else if (topbar.parent().hasClass('fixed')) {
106
+ topbar.parent().removeClass('fixed');
107
+ topbar.addClass('fixed');
108
+ $('body').css('padding-top','0');
109
+
110
+ if (self.settings.scrolltop) {
111
+ window.scrollTo(0,0);
112
+ }
113
+ }
114
+ })
115
+
116
+ .on('click.fndtn.topbar', '.top-bar li.has-dropdown', function (e) {
117
+ if (self.breakpoint()) return;
118
+
119
+ var li = $(this),
120
+ target = $(e.target),
121
+ topbar = li.closest('[data-topbar], .top-bar'),
122
+ is_hover = topbar.data('topbar');
123
+
124
+ if (self.settings.is_hover && !Modernizr.touch) return;
125
+
126
+ e.stopImmediatePropagation();
127
+
128
+ if (target[0].nodeName === 'A' && target.parent().hasClass('has-dropdown')) {
129
+ e.preventDefault();
130
+ }
131
+
132
+ if (li.hasClass('hover')) {
133
+ li
134
+ .removeClass('hover')
135
+ .find('li')
136
+ .removeClass('hover');
137
+ } else {
138
+ li.addClass('hover');
139
+ }
140
+ })
141
+
142
+ .on('click.fndtn.topbar', '.top-bar .has-dropdown>a, [data-topbar] .has-dropdown>a', function (e) {
143
+ if (self.breakpoint()) {
144
+ e.preventDefault();
145
+
146
+ var $this = $(this),
147
+ topbar = $this.closest('.top-bar, [data-topbar]'),
148
+ section = topbar.find('section, .section'),
149
+ titlebar = topbar.children('ul').first(),
150
+ dropdownHeight = $this.next('.dropdown').outerHeight(),
151
+ $selectedLi = $this.closest('li');
152
+
153
+ topbar.data('index', topbar.data('index') + 1);
154
+ $selectedLi.addClass('moved');
155
+
156
+ if (!self.rtl) {
157
+ section.css({left: -(100 * topbar.data('index')) + '%'});
158
+ section.find('>.name').css({left: 100 * topbar.data('index') + '%'});
159
+ } else {
160
+ section.css({right: -(100 * topbar.data('index')) + '%'});
161
+ section.find('>.name').css({right: 100 * topbar.data('index') + '%'});
162
+ }
163
+
164
+ topbar.css('height', self.outerHeight($this.siblings('ul'), true) + self.height(titlebar));
165
+ }
166
+ });
167
+
168
+ $(window).on('resize.fndtn.topbar', function () {
169
+ if (!self.breakpoint()) {
170
+ $('.top-bar, [data-topbar]')
171
+ .css('height', '')
172
+ .removeClass('expanded')
173
+ .find('li')
174
+ .removeClass('hover');
175
+ }
176
+ }.bind(this));
177
+
178
+ $('body').on('click.fndtn.topbar', function (e) {
179
+ var parent = $(e.target).closest('[data-topbar], .top-bar');
180
+
181
+ if (parent.length > 0) {
182
+ return;
183
+ }
184
+
185
+ $('.top-bar li, [data-topbar] li').removeClass('hover');
186
+ });
187
+
188
+ // Go up a level on Click
189
+ $(this.scope).on('click.fndtn', '.top-bar .has-dropdown .back, [data-topbar] .has-dropdown .back', function (e) {
190
+ e.preventDefault();
191
+
192
+ var $this = $(this),
193
+ topbar = $this.closest('.top-bar, [data-topbar]'),
194
+ titlebar = topbar.children('ul').first(),
195
+ section = topbar.find('section, .section'),
196
+ $movedLi = $this.closest('li.moved'),
197
+ $previousLevelUl = $movedLi.parent();
198
+
199
+ topbar.data('index', topbar.data('index') - 1);
200
+
201
+ if (!self.rtl) {
202
+ section.css({left: -(100 * topbar.data('index')) + '%'});
203
+ section.find('>.name').css({left: 100 * topbar.data('index') + '%'});
204
+ } else {
205
+ section.css({right: -(100 * topbar.data('index')) + '%'});
206
+ section.find('>.name').css({right: 100 * topbar.data('index') + '%'});
207
+ }
208
+
209
+ if (topbar.data('index') === 0) {
210
+ topbar.css('height', '');
211
+ } else {
212
+ topbar.css('height', self.outerHeight($previousLevelUl, true) + self.height(titlebar));
213
+ }
214
+
215
+ setTimeout(function () {
216
+ $movedLi.removeClass('moved');
217
+ }, 300);
218
+ });
219
+ },
220
+
221
+ breakpoint : function () {
222
+ return $(document).width() <= this.settings.breakPoint || $('html').hasClass('lt-ie9');
223
+ },
224
+
225
+ assemble : function () {
226
+ var self = this;
227
+ // Pull element out of the DOM for manipulation
228
+ this.settings.$section.detach();
229
+
230
+ this.settings.$section.find('.has-dropdown>a').each(function () {
231
+ var $link = $(this),
232
+ $dropdown = $link.siblings('.dropdown'),
233
+ url = $link.attr('href');
234
+
235
+ if (self.settings.mobile_show_parent_link && url && url.length > 1) {
236
+ var $titleLi = $('<li class="title back js-generated"><h5><a href="#"></a></h5></li><li><a class="parent-link js-generated" href="' + url + '">' + $link.text() +'</a></li>');
237
+ } else {
238
+ var $titleLi = $('<li class="title back js-generated"><h5><a href="#"></a></h5></li>');
239
+ }
240
+
241
+ // Copy link to subnav
242
+ if (self.settings.custom_back_text == true) {
243
+ $titleLi.find('h5>a').html('&laquo; ' + self.settings.back_text);
244
+ } else {
245
+ $titleLi.find('h5>a').html('&laquo; ' + $link.html());
246
+ }
247
+ $dropdown.prepend($titleLi);
248
+ });
249
+
250
+ // Put element back in the DOM
251
+ this.settings.$section.appendTo(this.settings.$topbar);
252
+
253
+ // check for sticky
254
+ this.sticky();
255
+ },
256
+
257
+ height : function (ul) {
258
+ var total = 0,
259
+ self = this;
260
+
261
+ ul.find('> li').each(function () { total += self.outerHeight($(this), true); });
262
+
263
+ return total;
264
+ },
265
+
266
+ sticky : function () {
267
+ var klass = '.' + this.settings.stickyClass;
268
+ if ($(klass).length > 0) {
269
+ var distance = $(klass).length ? $(klass).offset().top: 0,
270
+ $window = $(window),
271
+ offst = this.outerHeight($('.top-bar')),
272
+ t_top;
273
+
274
+ //Whe resize elements of the page on windows resize. Must recalculate distance
275
+ $(window).resize(function() {
276
+ clearTimeout(t_top);
277
+ t_top = setTimeout (function() {
278
+ distance = $(klass).offset().top;
279
+ },105);
280
+ });
281
+ $window.scroll(function() {
282
+ if ($window.scrollTop() > (distance)) {
283
+ $(klass).addClass("fixed");
284
+ $('body').css('padding-top',offst);
285
+ } else if ($window.scrollTop() <= distance) {
286
+ $(klass).removeClass("fixed");
287
+ $('body').css('padding-top','0');
288
+ }
289
+ });
290
+ }
291
+ },
292
+
293
+ off : function () {
294
+ $(this.scope).off('.fndtn.topbar');
295
+ $(window).off('.fndtn.topbar');
296
+ },
297
+
298
+ reflow : function () {}
299
+ };
300
+ }(Foundation.zj, this, this.document));