2011-07-17 08:05:43 +00:00
|
|
|
'use strict';
|
|
|
|
|
|
2010-10-23 05:46:51 +00:00
|
|
|
/**
|
|
|
|
|
* Here is the problem: http://bugs.jquery.com/ticket/7292
|
|
|
|
|
* basically jQuery treats change event on some browsers (IE) as a
|
2010-12-10 21:55:18 +00:00
|
|
|
* special event and changes it form 'change' to 'click/keydown' and
|
2010-10-23 05:46:51 +00:00
|
|
|
* few others. This horrible hack removes the special treatment
|
|
|
|
|
*/
|
|
|
|
|
_jQuery.event.special.change = undefined;
|
|
|
|
|
|
2011-11-04 19:33:01 +00:00
|
|
|
bindJQuery();
|
2011-10-07 18:27:49 +00:00
|
|
|
beforeEach(function() {
|
2011-11-04 19:33:01 +00:00
|
|
|
publishExternalAPI(angular);
|
2011-09-15 02:54:00 +00:00
|
|
|
|
|
|
|
|
// workaround for IE bug https://plus.google.com/104744871076396904202/posts/Kqjuj6RSbbT
|
|
|
|
|
// IE overwrite window.jQuery with undefined because of empty jQuery var statement, so we have to
|
|
|
|
|
// correct this, but only if we are not running in jqLite mode
|
|
|
|
|
if (!_jqLiteMode && _jQuery !== jQuery) {
|
|
|
|
|
jQuery = _jQuery;
|
|
|
|
|
}
|
|
|
|
|
|
2011-09-08 20:56:29 +00:00
|
|
|
// This resets global id counter;
|
|
|
|
|
uid = ['0', '0', '0'];
|
|
|
|
|
|
2011-02-05 00:42:21 +00:00
|
|
|
// reset to jQuery or default to us.
|
|
|
|
|
bindJQuery();
|
2011-02-07 23:29:56 +00:00
|
|
|
jqLite(document.body).html('');
|
2010-05-11 03:24:20 +00:00
|
|
|
});
|
|
|
|
|
|
2011-11-04 19:33:01 +00:00
|
|
|
afterEach(function() {
|
|
|
|
|
if (this.$injector) {
|
2011-11-12 23:23:30 +00:00
|
|
|
var $rootScope = this.$injector.get('$rootScope');
|
|
|
|
|
var $log = this.$injector.get('$log');
|
2011-11-04 19:33:01 +00:00
|
|
|
// release the injector
|
|
|
|
|
dealoc($rootScope);
|
2011-01-26 04:44:44 +00:00
|
|
|
|
2011-11-04 19:33:01 +00:00
|
|
|
// check $log mock
|
|
|
|
|
$log.assertEmpty && $log.assertEmpty();
|
|
|
|
|
}
|
2010-12-02 04:29:54 +00:00
|
|
|
|
2011-11-04 19:33:01 +00:00
|
|
|
// complain about uncleared jqCache references
|
2010-12-02 04:29:54 +00:00
|
|
|
var count = 0;
|
2012-05-09 23:27:15 +00:00
|
|
|
|
|
|
|
|
// This line should be enabled as soon as this bug is fixed: http://bugs.jquery.com/ticket/11775
|
|
|
|
|
//var cache = jqLite.cache;
|
|
|
|
|
var cache = JQLite.cache;
|
|
|
|
|
|
|
|
|
|
forEachSorted(cache, function(expando, key){
|
|
|
|
|
forEach(expando.data, function(value, key){
|
|
|
|
|
count ++;
|
2011-03-23 16:33:29 +00:00
|
|
|
if (value.$element) {
|
|
|
|
|
dump('LEAK', key, value.$id, sortedHtml(value.$element));
|
|
|
|
|
} else {
|
|
|
|
|
dump('LEAK', key, toJson(value));
|
|
|
|
|
}
|
2010-12-02 04:29:54 +00:00
|
|
|
});
|
|
|
|
|
});
|
|
|
|
|
if (count) {
|
2012-05-04 04:43:55 +00:00
|
|
|
throw new Error('Found jqCache references that were not deallocated! count: ' + count);
|
2010-12-02 04:29:54 +00:00
|
|
|
}
|
2011-11-04 19:33:01 +00:00
|
|
|
});
|
2010-01-06 00:36:58 +00:00
|
|
|
|
2010-03-30 21:55:04 +00:00
|
|
|
|
2010-12-02 04:29:54 +00:00
|
|
|
function dealoc(obj) {
|
2012-05-09 23:27:15 +00:00
|
|
|
var jqCache = jqLite.cache;
|
2011-02-10 19:20:49 +00:00
|
|
|
if (obj) {
|
2011-11-23 05:28:39 +00:00
|
|
|
if (isElement(obj)) {
|
2012-05-09 23:27:15 +00:00
|
|
|
cleanup(jqLite(obj));
|
2011-11-23 05:28:39 +00:00
|
|
|
} else {
|
|
|
|
|
for(var key in jqCache) {
|
|
|
|
|
var value = jqCache[key];
|
2012-05-09 23:27:15 +00:00
|
|
|
if (value.data && value.data.$scope == obj) {
|
2011-11-23 05:28:39 +00:00
|
|
|
delete jqCache[key];
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
2012-05-09 23:27:15 +00:00
|
|
|
}
|
2011-11-23 05:28:39 +00:00
|
|
|
|
2012-05-09 23:27:15 +00:00
|
|
|
function cleanup(element) {
|
|
|
|
|
element.unbind().removeData();
|
2012-12-20 17:27:57 +00:00
|
|
|
for ( var i = 0, children = element.contents() || []; i < children.length; i++) {
|
2012-05-09 23:27:15 +00:00
|
|
|
cleanup(jqLite(children[i]));
|
|
|
|
|
}
|
2011-02-10 19:20:49 +00:00
|
|
|
}
|
2010-12-02 04:29:54 +00:00
|
|
|
}
|
|
|
|
|
|
2011-11-29 20:11:32 +00:00
|
|
|
/**
|
|
|
|
|
* @param {DOMElement} element
|
|
|
|
|
* @param {boolean=} showNgClass
|
|
|
|
|
*/
|
2010-10-27 05:02:24 +00:00
|
|
|
function sortedHtml(element, showNgClass) {
|
2010-01-06 00:36:58 +00:00
|
|
|
var html = "";
|
2011-01-08 06:02:23 +00:00
|
|
|
forEach(jqLite(element), function toString(node) {
|
2012-12-04 17:24:15 +00:00
|
|
|
|
2010-01-06 00:36:58 +00:00
|
|
|
if (node.nodeName == "#text") {
|
2010-10-19 04:20:47 +00:00
|
|
|
html += node.nodeValue.
|
|
|
|
|
replace(/&(\w+[&;\W])?/g, function(match, entity){return entity?match:'&';}).
|
|
|
|
|
replace(/</g, '<').
|
|
|
|
|
replace(/>/g, '>');
|
2012-12-04 17:24:15 +00:00
|
|
|
} else if (node.nodeName == "#comment") {
|
|
|
|
|
html += '<!--' + node.nodeValue + '-->';
|
2010-01-06 00:36:58 +00:00
|
|
|
} else {
|
2011-02-10 19:20:49 +00:00
|
|
|
html += '<' + (node.nodeName || '?NOT_A_NODE?').toLowerCase();
|
2010-01-06 00:36:58 +00:00
|
|
|
var attributes = node.attributes || [];
|
|
|
|
|
var attrs = [];
|
2010-10-27 05:02:24 +00:00
|
|
|
var className = node.className || '';
|
|
|
|
|
if (!showNgClass) {
|
|
|
|
|
className = className.replace(/ng-[\w-]+\s*/g, '');
|
|
|
|
|
}
|
|
|
|
|
className = trim(className);
|
|
|
|
|
if (className) {
|
|
|
|
|
attrs.push(' class="' + className + '"');
|
|
|
|
|
}
|
2010-01-06 00:36:58 +00:00
|
|
|
for(var i=0; i<attributes.length; i++) {
|
2011-04-09 07:16:40 +00:00
|
|
|
if (i>0 && attributes[i] == attributes[i-1])
|
|
|
|
|
continue; //IE9 creates dupes. Ignore them!
|
|
|
|
|
|
2010-01-06 00:36:58 +00:00
|
|
|
var attr = attributes[i];
|
2012-03-09 08:00:05 +00:00
|
|
|
if(attr.name.match(/^ng[\:\-]/) ||
|
2013-02-26 04:43:27 +00:00
|
|
|
(attr.value || attr.value == '') &&
|
2010-01-06 00:36:58 +00:00
|
|
|
attr.value !='null' &&
|
|
|
|
|
attr.value !='auto' &&
|
|
|
|
|
attr.value !='false' &&
|
|
|
|
|
attr.value !='inherit' &&
|
2011-04-19 23:34:49 +00:00
|
|
|
(attr.value !='0' || attr.name =='value') &&
|
2010-01-06 00:36:58 +00:00
|
|
|
attr.name !='loop' &&
|
2010-04-21 19:50:05 +00:00
|
|
|
attr.name !='complete' &&
|
2010-01-06 00:36:58 +00:00
|
|
|
attr.name !='maxLength' &&
|
|
|
|
|
attr.name !='size' &&
|
2010-07-23 20:54:12 +00:00
|
|
|
attr.name !='class' &&
|
2010-01-06 00:36:58 +00:00
|
|
|
attr.name !='start' &&
|
|
|
|
|
attr.name !='tabIndex' &&
|
2010-04-12 21:28:15 +00:00
|
|
|
attr.name !='style' &&
|
2010-01-06 00:36:58 +00:00
|
|
|
attr.name.substr(0, 6) != 'jQuery') {
|
|
|
|
|
// in IE we need to check for all of these.
|
2012-12-04 23:02:29 +00:00
|
|
|
if (/ng-\d+/.exec(attr.name) ||
|
|
|
|
|
attr.name == 'getElementById' ||
|
2011-06-17 20:48:22 +00:00
|
|
|
// IE7 has `selected` in attributes
|
2012-12-04 23:02:29 +00:00
|
|
|
attr.name == 'selected' ||
|
2011-06-17 20:48:22 +00:00
|
|
|
// IE7 adds `value` attribute to all LI tags
|
2012-12-04 23:02:29 +00:00
|
|
|
(node.nodeName == 'LI' && attr.name == 'value') ||
|
|
|
|
|
// IE8 adds bogus rowspan=1 and colspan=1 to TD elements
|
|
|
|
|
(node.nodeName == 'TD' && attr.name == 'rowSpan' && attr.value == '1') ||
|
|
|
|
|
(node.nodeName == 'TD' && attr.name == 'colSpan' && attr.value == '1')) {
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
attrs.push(' ' + attr.name + '="' + attr.value + '"');
|
2010-01-06 00:36:58 +00:00
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
attrs.sort();
|
|
|
|
|
html += attrs.join('');
|
2010-04-15 21:17:33 +00:00
|
|
|
if (node.style) {
|
|
|
|
|
var style = [];
|
|
|
|
|
if (node.style.cssText) {
|
2011-01-08 06:02:23 +00:00
|
|
|
forEach(node.style.cssText.split(';'), function(value){
|
2010-04-15 21:17:33 +00:00
|
|
|
value = trim(value);
|
|
|
|
|
if (value) {
|
2010-04-21 19:50:05 +00:00
|
|
|
style.push(lowercase(value));
|
2010-04-15 21:17:33 +00:00
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
}
|
|
|
|
|
for(var css in node.style){
|
|
|
|
|
var value = node.style[css];
|
|
|
|
|
if (isString(value) && isString(css) && css != 'cssText' && value && (1*css != css)) {
|
2010-04-21 19:50:05 +00:00
|
|
|
var text = lowercase(css + ': ' + value);
|
2010-04-19 21:36:41 +00:00
|
|
|
if (value != 'false' && indexOf(style, text) == -1) {
|
2010-04-15 21:17:33 +00:00
|
|
|
style.push(text);
|
|
|
|
|
}
|
|
|
|
|
}
|
2010-04-19 21:41:36 +00:00
|
|
|
}
|
2010-04-13 02:16:30 +00:00
|
|
|
style.sort();
|
2010-04-22 22:50:20 +00:00
|
|
|
var tmp = style;
|
|
|
|
|
style = [];
|
2011-01-08 06:02:23 +00:00
|
|
|
forEach(tmp, function(value){
|
2010-04-22 22:50:20 +00:00
|
|
|
if (!value.match(/^max[^\-]/))
|
|
|
|
|
style.push(value);
|
|
|
|
|
});
|
2010-04-15 21:17:33 +00:00
|
|
|
if (style.length) {
|
|
|
|
|
html += ' style="' + style.join('; ') + ';"';
|
|
|
|
|
}
|
2010-04-12 21:28:15 +00:00
|
|
|
}
|
2010-01-06 00:36:58 +00:00
|
|
|
html += '>';
|
|
|
|
|
var children = node.childNodes;
|
|
|
|
|
for(var j=0; j<children.length; j++) {
|
2010-03-30 03:25:42 +00:00
|
|
|
toString(children[j]);
|
2010-01-06 00:36:58 +00:00
|
|
|
}
|
|
|
|
|
html += '</' + node.nodeName.toLowerCase() + '>';
|
|
|
|
|
}
|
2010-04-12 21:28:15 +00:00
|
|
|
});
|
2010-01-06 00:36:58 +00:00
|
|
|
return html;
|
2010-04-04 00:04:36 +00:00
|
|
|
}
|
2010-01-06 00:36:58 +00:00
|
|
|
|
2011-07-15 00:50:06 +00:00
|
|
|
|
2011-11-01 00:54:09 +00:00
|
|
|
// TODO(vojta): migrate these helpers into jasmine matchers
|
2011-11-11 02:47:47 +00:00
|
|
|
/**a
|
2011-07-15 00:50:06 +00:00
|
|
|
* This method is a cheap way of testing if css for a given node is not set to 'none'. It doesn't
|
|
|
|
|
* actually test if an element is displayed by the browser. Be aware!!!
|
|
|
|
|
*/
|
2010-04-08 20:43:40 +00:00
|
|
|
function isCssVisible(node) {
|
2010-03-31 20:57:25 +00:00
|
|
|
var display = node.css('display');
|
2010-02-04 21:27:56 +00:00
|
|
|
return display != 'none';
|
|
|
|
|
}
|
|
|
|
|
|
2010-01-06 00:36:58 +00:00
|
|
|
function assertHidden(node) {
|
2012-01-03 04:50:17 +00:00
|
|
|
if (isCssVisible(node)) {
|
|
|
|
|
throw new Error('Node should be hidden but was visible: ' + angular.module.ngMock.dump(node));
|
|
|
|
|
}
|
2010-01-06 00:36:58 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
function assertVisible(node) {
|
2012-01-03 04:50:17 +00:00
|
|
|
if (!isCssVisible(node)) {
|
|
|
|
|
throw new Error('Node should be visible but was hidden: ' + angular.module.ngMock.dump(node));
|
|
|
|
|
}
|
2010-01-06 00:36:58 +00:00
|
|
|
}
|
|
|
|
|
|
2011-12-15 09:10:09 +00:00
|
|
|
function provideLog($provide) {
|
|
|
|
|
$provide.factory('log', function() {
|
|
|
|
|
var messages = [];
|
|
|
|
|
|
|
|
|
|
function log(msg) {
|
|
|
|
|
messages.push(msg);
|
|
|
|
|
return msg;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
log.toString = function() {
|
|
|
|
|
return messages.join('; ');
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
log.toArray = function() {
|
|
|
|
|
return messages;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
log.reset = function() {
|
|
|
|
|
messages = [];
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
log.fn = function(msg) {
|
|
|
|
|
return function() {
|
|
|
|
|
log(msg);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
log.$$log = true;
|
|
|
|
|
|
|
|
|
|
return log;
|
|
|
|
|
});
|
|
|
|
|
}
|
2011-12-20 08:58:26 +00:00
|
|
|
|
|
|
|
|
function pending() {
|
|
|
|
|
dump('PENDING');
|
|
|
|
|
};
|
2012-05-03 04:59:55 +00:00
|
|
|
|
|
|
|
|
function trace(name) {
|
|
|
|
|
dump(new Error(name).stack);
|
|
|
|
|
}
|
2013-07-23 18:00:42 +00:00
|
|
|
|
|
|
|
|
var karmaDump = dump;
|
|
|
|
|
window.dump = function () {
|
|
|
|
|
karmaDump(angular.mock.dump.apply(undefined, arguments));
|
|
|
|
|
};
|