1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/changeset/4bdb9214efd6/
changeset: 4bdb9214efd6
user: jgoecks
date: 2012-10-02 04:53:21
summary: Fix some UI framework issues.
affected #: 3 files
diff -r 55e7d7008efee2c5622f2505612265a9593ae992 -r 4bdb9214efd6ec510f2cc6e00224a467d36ba721 static/scripts/libs/underscore.js
--- a/static/scripts/libs/underscore.js
+++ b/static/scripts/libs/underscore.js
@@ -1,7 +1,10 @@
-// Underscore.js 1.4.0
-// http://underscorejs.org
+// Underscore.js 1.3.1
// (c) 2009-2012 Jeremy Ashkenas, DocumentCloud Inc.
-// Underscore may be freely distributed under the MIT license.
+// Underscore is freely distributable under the MIT license.
+// Portions of Underscore are inspired or borrowed from Prototype,
+// Oliver Steele's Functional, and John Resig's Micro-Templating.
+// For all details and documentation:
+// http://documentcloud.github.com/underscore
(function() {
@@ -21,9 +24,7 @@
var ArrayProto = Array.prototype, ObjProto = Object.prototype, FuncProto = Function.prototype;
// Create quick reference variables for speed access to core prototypes.
- var push = ArrayProto.push,
- slice = ArrayProto.slice,
- concat = ArrayProto.concat,
+ var slice = ArrayProto.slice,
unshift = ArrayProto.unshift,
toString = ObjProto.toString,
hasOwnProperty = ObjProto.hasOwnProperty;
@@ -45,11 +46,7 @@
nativeBind = FuncProto.bind;
// Create a safe reference to the Underscore object for use below.
- var _ = function(obj) {
- if (obj instanceof _) return obj;
- if (!(this instanceof _)) return new _(obj);
- this._wrapped = obj;
- };
+ var _ = function(obj) { return new wrapper(obj); };
// Export the Underscore object for **Node.js**, with
// backwards-compatibility for the old `require()` API. If we're in
@@ -65,7 +62,7 @@
}
// Current version.
- _.VERSION = '1.4.0';
+ _.VERSION = '1.3.1';
// Collection Functions
// --------------------
@@ -74,11 +71,12 @@
// Handles objects with the built-in `forEach`, arrays, and raw objects.
// Delegates to **ECMAScript 5**'s native `forEach` if available.
var each = _.each = _.forEach = function(obj, iterator, context) {
+ if (obj == null) return;
if (nativeForEach && obj.forEach === nativeForEach) {
obj.forEach(iterator, context);
} else if (obj.length === +obj.length) {
for (var i = 0, l = obj.length; i < l; i++) {
- if (iterator.call(context, obj[i], i, obj) === breaker) return;
+ if (i in obj && iterator.call(context, obj[i], i, obj) === breaker) return;
}
} else {
for (var key in obj) {
@@ -93,10 +91,12 @@
// Delegates to **ECMAScript 5**'s native `map` if available.
_.map = _.collect = function(obj, iterator, context) {
var results = [];
+ if (obj == null) return results;
if (nativeMap && obj.map === nativeMap) return obj.map(iterator, context);
each(obj, function(value, index, list) {
results[results.length] = iterator.call(context, value, index, list);
});
+ if (obj.length === +obj.length) results.length = obj.length;
return results;
};
@@ -104,6 +104,7 @@
// or `foldl`. Delegates to **ECMAScript 5**'s native `reduce` if available.
_.reduce = _.foldl = _.inject = function(obj, iterator, memo, context) {
var initial = arguments.length > 2;
+ if (obj == null) obj = [];
if (nativeReduce && obj.reduce === nativeReduce) {
if (context) iterator = _.bind(iterator, context);
return initial ? obj.reduce(iterator, memo) : obj.reduce(iterator);
@@ -124,26 +125,14 @@
// Delegates to **ECMAScript 5**'s native `reduceRight` if available.
_.reduceRight = _.foldr = function(obj, iterator, memo, context) {
var initial = arguments.length > 2;
+ if (obj == null) obj = [];
if (nativeReduceRight && obj.reduceRight === nativeReduceRight) {
if (context) iterator = _.bind(iterator, context);
- return arguments.length > 2 ? obj.reduceRight(iterator, memo) : obj.reduceRight(iterator);
+ return initial ? obj.reduceRight(iterator, memo) : obj.reduceRight(iterator);
}
- var length = obj.length;
- if (length !== +length) {
- var keys = _.keys(obj);
- length = keys.length;
- }
- each(obj, function(value, index, list) {
- index = keys ? keys[--length] : --length;
- if (!initial) {
- memo = obj[index];
- initial = true;
- } else {
- memo = iterator.call(context, memo, obj[index], index, list);
- }
- });
- if (!initial) throw new TypeError('Reduce of empty array with no initial value');
- return memo;
+ var reversed = _.toArray(obj).reverse();
+ if (context && !initial) iterator = _.bind(iterator, context);
+ return initial ? _.reduce(reversed, iterator, memo, context) : _.reduce(reversed, iterator);
};
// Return the first value which passes a truth test. Aliased as `detect`.
@@ -163,6 +152,7 @@
// Aliased as `select`.
_.filter = _.select = function(obj, iterator, context) {
var results = [];
+ if (obj == null) return results;
if (nativeFilter && obj.filter === nativeFilter) return obj.filter(iterator, context);
each(obj, function(value, index, list) {
if (iterator.call(context, value, index, list)) results[results.length] = value;
@@ -173,6 +163,7 @@
// Return all the elements for which a truth test fails.
_.reject = function(obj, iterator, context) {
var results = [];
+ if (obj == null) return results;
each(obj, function(value, index, list) {
if (!iterator.call(context, value, index, list)) results[results.length] = value;
});
@@ -183,13 +174,13 @@
// Delegates to **ECMAScript 5**'s native `every` if available.
// Aliased as `all`.
_.every = _.all = function(obj, iterator, context) {
- iterator || (iterator = _.identity);
var result = true;
+ if (obj == null) return result;
if (nativeEvery && obj.every === nativeEvery) return obj.every(iterator, context);
each(obj, function(value, index, list) {
if (!(result = result && iterator.call(context, value, index, list))) return breaker;
});
- return !!result;
+ return result;
};
// Determine if at least one element in the object matches a truth test.
@@ -198,6 +189,7 @@
var any = _.some = _.any = function(obj, iterator, context) {
iterator || (iterator = _.identity);
var result = false;
+ if (obj == null) return result;
if (nativeSome && obj.some === nativeSome) return obj.some(iterator, context);
each(obj, function(value, index, list) {
if (result || (result = iterator.call(context, value, index, list))) return breaker;
@@ -205,10 +197,11 @@
return !!result;
};
- // Determine if the array or object contains a given value (using `===`).
- // Aliased as `include`.
- _.contains = _.include = function(obj, target) {
+ // Determine if a given value is included in the array or object using `===`.
+ // Aliased as `contains`.
+ _.include = _.contains = function(obj, target) {
var found = false;
+ if (obj == null) return found;
if (nativeIndexOf && obj.indexOf === nativeIndexOf) return obj.indexOf(target) != -1;
found = any(obj, function(value) {
return value === target;
@@ -220,7 +213,7 @@
_.invoke = function(obj, method) {
var args = slice.call(arguments, 2);
return _.map(obj, function(value) {
- return (_.isFunction(method) ? method : value[method]).apply(value, args);
+ return (_.isFunction(method) ? method || value : value[method]).apply(value, args);
});
};
@@ -229,25 +222,9 @@
return _.map(obj, function(value){ return value[key]; });
};
- // Convenience version of a common use case of `filter`: selecting only objects
- // with specific `key:value` pairs.
- _.where = function(obj, attrs) {
- if (_.isEmpty(attrs)) return [];
- return _.filter(obj, function(value) {
- for (var key in attrs) {
- if (attrs[key] !== value[key]) return false;
- }
- return true;
- });
- };
-
// Return the maximum element or (element-based computation).
- // Can't optimize arrays of integers longer than 65,535 elements.
- // See: https://bugs.webkit.org/show_bug.cgi?id=80797
_.max = function(obj, iterator, context) {
- if (!iterator && _.isArray(obj) && obj[0] === +obj[0] && obj.length < 65535) {
- return Math.max.apply(Math, obj);
- }
+ if (!iterator && _.isArray(obj)) return Math.max.apply(Math, obj);
if (!iterator && _.isEmpty(obj)) return -Infinity;
var result = {computed : -Infinity};
each(obj, function(value, index, list) {
@@ -259,9 +236,7 @@
// Return the minimum element (or element-based computation).
_.min = function(obj, iterator, context) {
- if (!iterator && _.isArray(obj) && obj[0] === +obj[0] && obj.length < 65535) {
- return Math.min.apply(Math, obj);
- }
+ if (!iterator && _.isArray(obj)) return Math.min.apply(Math, obj);
if (!iterator && _.isEmpty(obj)) return Infinity;
var result = {computed : Infinity};
each(obj, function(value, index, list) {
@@ -273,107 +248,81 @@
// Shuffle an array.
_.shuffle = function(obj) {
- var rand;
- var index = 0;
- var shuffled = [];
- each(obj, function(value) {
- rand = _.random(index++);
- shuffled[index - 1] = shuffled[rand];
- shuffled[rand] = value;
+ var shuffled = [], rand;
+ each(obj, function(value, index, list) {
+ if (index == 0) {
+ shuffled[0] = value;
+ } else {
+ rand = Math.floor(Math.random() * (index + 1));
+ shuffled[index] = shuffled[rand];
+ shuffled[rand] = value;
+ }
});
return shuffled;
};
- // An internal function to generate lookup iterators.
- var lookupIterator = function(value) {
- return _.isFunction(value) ? value : function(obj){ return obj[value]; };
- };
-
// Sort the object's values by a criterion produced by an iterator.
- _.sortBy = function(obj, value, context) {
- var iterator = lookupIterator(value);
+ _.sortBy = function(obj, iterator, context) {
return _.pluck(_.map(obj, function(value, index, list) {
return {
value : value,
- index : index,
criteria : iterator.call(context, value, index, list)
};
}).sort(function(left, right) {
- var a = left.criteria;
- var b = right.criteria;
- if (a !== b) {
- if (a > b || a === void 0) return 1;
- if (a < b || b === void 0) return -1;
- }
- return left.index < right.index ? -1 : 1;
+ var a = left.criteria, b = right.criteria;
+ return a < b ? -1 : a > b ? 1 : 0;
}), 'value');
};
- // An internal function used for aggregate "group by" operations.
- var group = function(obj, value, context, behavior) {
+ // Groups the object's values by a criterion. Pass either a string attribute
+ // to group by, or a function that returns the criterion.
+ _.groupBy = function(obj, val) {
var result = {};
- var iterator = lookupIterator(value);
+ var iterator = _.isFunction(val) ? val : function(obj) { return obj[val]; };
each(obj, function(value, index) {
- var key = iterator.call(context, value, index, obj);
- behavior(result, key, value);
+ var key = iterator(value, index);
+ (result[key] || (result[key] = [])).push(value);
});
return result;
};
- // Groups the object's values by a criterion. Pass either a string attribute
- // to group by, or a function that returns the criterion.
- _.groupBy = function(obj, value, context) {
- return group(obj, value, context, function(result, key, value) {
- (_.has(result, key) ? result[key] : (result[key] = [])).push(value);
- });
- };
-
- // Counts instances of an object that group by a certain criterion. Pass
- // either a string attribute to count by, or a function that returns the
- // criterion.
- _.countBy = function(obj, value, context) {
- return group(obj, value, context, function(result, key, value) {
- if (!_.has(result, key)) result[key] = 0;
- result[key]++;
- });
- };
-
- // Use a comparator function to figure out the smallest index at which
- // an object should be inserted so as to maintain order. Uses binary search.
- _.sortedIndex = function(array, obj, iterator, context) {
- iterator = iterator == null ? _.identity : lookupIterator(iterator);
- var value = iterator.call(context, obj);
+ // Use a comparator function to figure out at what index an object should
+ // be inserted so as to maintain order. Uses binary search.
+ _.sortedIndex = function(array, obj, iterator) {
+ iterator || (iterator = _.identity);
var low = 0, high = array.length;
while (low < high) {
- var mid = (low + high) >>> 1;
- iterator.call(context, array[mid]) < value ? low = mid + 1 : high = mid;
+ var mid = (low + high) >> 1;
+ iterator(array[mid]) < iterator(obj) ? low = mid + 1 : high = mid;
}
return low;
};
// Safely convert anything iterable into a real, live array.
- _.toArray = function(obj) {
- if (!obj) return [];
- if (obj.length === +obj.length) return slice.call(obj);
- return _.values(obj);
+ _.toArray = function(iterable) {
+ if (!iterable) return [];
+ if (iterable.toArray) return iterable.toArray();
+ if (_.isArray(iterable)) return slice.call(iterable);
+ if (_.isArguments(iterable)) return slice.call(iterable);
+ return _.values(iterable);
};
// Return the number of elements in an object.
_.size = function(obj) {
- return (obj.length === +obj.length) ? obj.length : _.keys(obj).length;
+ return _.toArray(obj).length;
};
// Array Functions
// ---------------
// Get the first element of an array. Passing **n** will return the first N
- // values in the array. Aliased as `head` and `take`. The **guard** check
- // allows it to work with `_.map`.
- _.first = _.head = _.take = function(array, n, guard) {
+ // values in the array. Aliased as `head`. The **guard** check allows it to work
+ // with `_.map`.
+ _.first = _.head = function(array, n, guard) {
return (n != null) && !guard ? slice.call(array, 0, n) : array[0];
};
- // Returns everything but the last entry of the array. Especially useful on
+ // Returns everything but the last entry of the array. Especcialy useful on
// the arguments object. Passing **n** will return all the values in
// the array, excluding the last N. The **guard** check allows it to work with
// `_.map`.
@@ -391,12 +340,12 @@
}
};
- // Returns everything but the first entry of the array. Aliased as `tail` and `drop`.
- // Especially useful on the arguments object. Passing an **n** will return
- // the rest N values in the array. The **guard**
+ // Returns everything but the first entry of the array. Aliased as `tail`.
+ // Especially useful on the arguments object. Passing an **index** will return
+ // the rest of the values in the array from that index onward. The **guard**
// check allows it to work with `_.map`.
- _.rest = _.tail = _.drop = function(array, n, guard) {
- return slice.call(array, (n == null) || guard ? 1 : n);
+ _.rest = _.tail = function(array, index, guard) {
+ return slice.call(array, (index == null) || guard ? 1 : index);
};
// Trim out all falsy values from an array.
@@ -404,21 +353,13 @@
return _.filter(array, function(value){ return !!value; });
};
- // Internal implementation of a recursive `flatten` function.
- var flatten = function(input, shallow, output) {
- each(input, function(value) {
- if (_.isArray(value)) {
- shallow ? push.apply(output, value) : flatten(value, shallow, output);
- } else {
- output.push(value);
- }
- });
- return output;
- };
-
// Return a completely flattened version of an array.
_.flatten = function(array, shallow) {
- return flatten(array, shallow, []);
+ return _.reduce(array, function(memo, value) {
+ if (_.isArray(value)) return memo.concat(shallow ? value : _.flatten(value));
+ memo[memo.length] = value;
+ return memo;
+ }, []);
};
// Return a version of the array that does not contain the specified value(s).
@@ -429,28 +370,28 @@
// Produce a duplicate-free version of the array. If the array has already
// been sorted, you have the option of using a faster algorithm.
// Aliased as `unique`.
- _.uniq = _.unique = function(array, isSorted, iterator, context) {
- var initial = iterator ? _.map(array, iterator, context) : array;
- var results = [];
- var seen = [];
- each(initial, function(value, index) {
- if (isSorted ? (!index || seen[seen.length - 1] !== value) : !_.contains(seen, value)) {
- seen.push(value);
- results.push(array[index]);
+ _.uniq = _.unique = function(array, isSorted, iterator) {
+ var initial = iterator ? _.map(array, iterator) : array;
+ var result = [];
+ _.reduce(initial, function(memo, el, i) {
+ if (0 == i || (isSorted === true ? _.last(memo) != el : !_.include(memo, el))) {
+ memo[memo.length] = el;
+ result[result.length] = array[i];
}
- });
- return results;
+ return memo;
+ }, []);
+ return result;
};
// Produce an array that contains the union: each distinct element from all of
// the passed-in arrays.
_.union = function() {
- return _.uniq(concat.apply(ArrayProto, arguments));
+ return _.uniq(_.flatten(arguments, true));
};
// Produce an array that contains every item shared between all the
- // passed-in arrays.
- _.intersection = function(array) {
+ // passed-in arrays. (Aliased as "intersect" for back-compat.)
+ _.intersection = _.intersect = function(array) {
var rest = slice.call(arguments, 1);
return _.filter(_.uniq(array), function(item) {
return _.every(rest, function(other) {
@@ -462,8 +403,8 @@
// Take the difference between one array and a number of other arrays.
// Only the elements present in just the first array will remain.
_.difference = function(array) {
- var rest = concat.apply(ArrayProto, slice.call(arguments, 1));
- return _.filter(array, function(value){ return !_.contains(rest, value); });
+ var rest = _.flatten(slice.call(arguments, 1));
+ return _.filter(array, function(value){ return !_.include(rest, value); });
};
// Zip together multiple lists into a single array -- elements that share
@@ -472,27 +413,10 @@
var args = slice.call(arguments);
var length = _.max(_.pluck(args, 'length'));
var results = new Array(length);
- for (var i = 0; i < length; i++) {
- results[i] = _.pluck(args, "" + i);
- }
+ for (var i = 0; i < length; i++) results[i] = _.pluck(args, "" + i);
return results;
};
- // Converts lists into objects. Pass either a single array of `[key, value]`
- // pairs, or two parallel arrays of the same length -- one of keys, and one of
- // the corresponding values.
- _.object = function(list, values) {
- var result = {};
- for (var i = 0, l = list.length; i < l; i++) {
- if (values) {
- result[list[i]] = values[i];
- } else {
- result[list[i][0]] = list[i][1];
- }
- }
- return result;
- };
-
// If the browser doesn't supply us with indexOf (I'm looking at you, **MSIE**),
// we need this function. Return the position of the first occurrence of an
// item in an array, or -1 if the item is not included in the array.
@@ -500,25 +424,23 @@
// If the array is large and already in sort order, pass `true`
// for **isSorted** to use binary search.
_.indexOf = function(array, item, isSorted) {
- var i = 0, l = array.length;
+ if (array == null) return -1;
+ var i, l;
if (isSorted) {
- if (typeof isSorted == 'number') {
- i = (isSorted < 0 ? Math.max(0, l + isSorted) : isSorted);
- } else {
- i = _.sortedIndex(array, item);
- return array[i] === item ? i : -1;
- }
+ i = _.sortedIndex(array, item);
+ return array[i] === item ? i : -1;
}
- if (nativeIndexOf && array.indexOf === nativeIndexOf) return array.indexOf(item, isSorted);
- for (; i < l; i++) if (array[i] === item) return i;
+ if (nativeIndexOf && array.indexOf === nativeIndexOf) return array.indexOf(item);
+ for (i = 0, l = array.length; i < l; i++) if (i in array && array[i] === item) return i;
return -1;
};
// Delegates to **ECMAScript 5**'s native `lastIndexOf` if available.
- _.lastIndexOf = function(array, item, fromIndex) {
- if (nativeLastIndexOf && array.lastIndexOf === nativeLastIndexOf) return array.lastIndexOf(item, fromIndex);
- var i = (fromIndex != null ? fromIndex : array.length);
- while (i--) if (array[i] === item) return i;
+ _.lastIndexOf = function(array, item) {
+ if (array == null) return -1;
+ if (nativeLastIndexOf && array.lastIndexOf === nativeLastIndexOf) return array.lastIndexOf(item);
+ var i = array.length;
+ while (i--) if (i in array && array[i] === item) return i;
return -1;
};
@@ -592,7 +514,7 @@
// it with the arguments supplied.
_.delay = function(func, wait) {
var args = slice.call(arguments, 2);
- return setTimeout(function(){ return func.apply(null, args); }, wait);
+ return setTimeout(function(){ return func.apply(func, args); }, wait);
};
// Defers a function, scheduling it to run after the current call stack has
@@ -604,46 +526,39 @@
// Returns a function, that, when invoked, will only be triggered at most once
// during a given window of time.
_.throttle = function(func, wait) {
- var context, args, timeout, throttling, more, result;
+ var context, args, timeout, throttling, more;
var whenDone = _.debounce(function(){ more = throttling = false; }, wait);
return function() {
context = this; args = arguments;
var later = function() {
timeout = null;
- if (more) {
- result = func.apply(context, args);
- }
+ if (more) func.apply(context, args);
whenDone();
};
if (!timeout) timeout = setTimeout(later, wait);
if (throttling) {
more = true;
} else {
- throttling = true;
- result = func.apply(context, args);
+ func.apply(context, args);
}
whenDone();
- return result;
+ throttling = true;
};
};
// Returns a function, that, as long as it continues to be invoked, will not
// be triggered. The function will be called after it stops being called for
- // N milliseconds. If `immediate` is passed, trigger the function on the
- // leading edge, instead of the trailing.
- _.debounce = function(func, wait, immediate) {
- var timeout, result;
+ // N milliseconds.
+ _.debounce = function(func, wait) {
+ var timeout;
return function() {
var context = this, args = arguments;
var later = function() {
timeout = null;
- if (!immediate) result = func.apply(context, args);
+ func.apply(context, args);
};
- var callNow = immediate && !timeout;
clearTimeout(timeout);
timeout = setTimeout(later, wait);
- if (callNow) result = func.apply(context, args);
- return result;
};
};
@@ -654,9 +569,7 @@
return function() {
if (ran) return memo;
ran = true;
- memo = func.apply(this, arguments);
- func = null;
- return memo;
+ return memo = func.apply(this, arguments);
};
};
@@ -665,8 +578,7 @@
// conditionally execute the original function.
_.wrap = function(func, wrapper) {
return function() {
- var args = [func];
- push.apply(args, arguments);
+ var args = [func].concat(slice.call(arguments, 0));
return wrapper.apply(this, args);
};
};
@@ -688,9 +600,7 @@
_.after = function(times, func) {
if (times <= 0) return func();
return function() {
- if (--times < 1) {
- return func.apply(this, arguments);
- }
+ if (--times < 1) { return func.apply(this, arguments); }
};
};
@@ -708,23 +618,7 @@
// Retrieve the values of an object's properties.
_.values = function(obj) {
- var values = [];
- for (var key in obj) if (_.has(obj, key)) values.push(obj[key]);
- return values;
- };
-
- // Convert an object into a list of `[key, value]` pairs.
- _.pairs = function(obj) {
- var pairs = [];
- for (var key in obj) if (_.has(obj, key)) pairs.push([key, obj[key]]);
- return pairs;
- };
-
- // Invert the keys and values of an object. The values must be serializable.
- _.invert = function(obj) {
- var result = {};
- for (var key in obj) if (_.has(obj, key)) result[obj[key]] = key;
- return result;
+ return _.map(obj, _.identity);
};
// Return a sorted list of the function names available on the object.
@@ -747,26 +641,6 @@
return obj;
};
- // Return a copy of the object only containing the whitelisted properties.
- _.pick = function(obj) {
- var copy = {};
- var keys = concat.apply(ArrayProto, slice.call(arguments, 1));
- each(keys, function(key) {
- if (key in obj) copy[key] = obj[key];
- });
- return copy;
- };
-
- // Return a copy of the object without the blacklisted properties.
- _.omit = function(obj) {
- var copy = {};
- var keys = concat.apply(ArrayProto, slice.call(arguments, 1));
- for (var key in obj) {
- if (!_.contains(keys, key)) copy[key] = obj[key];
- }
- return copy;
- };
-
// Fill in a given object with default properties.
_.defaults = function(obj) {
each(slice.call(arguments, 1), function(source) {
@@ -791,16 +665,19 @@
return obj;
};
- // Internal recursive comparison function for `isEqual`.
- var eq = function(a, b, aStack, bStack) {
+ // Internal recursive comparison function.
+ function eq(a, b, stack) {
// Identical objects are equal. `0 === -0`, but they aren't identical.
// See the Harmony `egal` proposal: http://wiki.ecmascript.org/doku.php?id=harmony:egal.
if (a === b) return a !== 0 || 1 / a == 1 / b;
// A strict comparison is necessary because `null == undefined`.
if (a == null || b == null) return a === b;
// Unwrap any wrapped objects.
- if (a instanceof _) a = a._wrapped;
- if (b instanceof _) b = b._wrapped;
+ if (a._chain) a = a._wrapped;
+ if (b._chain) b = b._wrapped;
+ // Invoke a custom `isEqual` method if one is provided.
+ if (a.isEqual && _.isFunction(a.isEqual)) return a.isEqual(b);
+ if (b.isEqual && _.isFunction(b.isEqual)) return b.isEqual(a);
// Compare `[[Class]]` names.
var className = toString.call(a);
if (className != toString.call(b)) return false;
@@ -830,15 +707,14 @@
if (typeof a != 'object' || typeof b != 'object') return false;
// Assume equality for cyclic structures. The algorithm for detecting cyclic
// structures is adapted from ES 5.1 section 15.12.3, abstract operation `JO`.
- var length = aStack.length;
+ var length = stack.length;
while (length--) {
// Linear search. Performance is inversely proportional to the number of
// unique nested structures.
- if (aStack[length] == a) return bStack[length] == b;
+ if (stack[length] == a) return true;
}
// Add the first object to the stack of traversed objects.
- aStack.push(a);
- bStack.push(b);
+ stack.push(a);
var size = 0, result = true;
// Recursively compare objects and arrays.
if (className == '[object Array]') {
@@ -848,24 +724,20 @@
if (result) {
// Deep compare the contents, ignoring non-numeric properties.
while (size--) {
- if (!(result = eq(a[size], b[size], aStack, bStack))) break;
+ // Ensure commutative equality for sparse arrays.
+ if (!(result = size in a == size in b && eq(a[size], b[size], stack))) break;
}
}
} else {
- // Objects with different constructors are not equivalent, but `Object`s
- // from different frames are.
- var aCtor = a.constructor, bCtor = b.constructor;
- if (aCtor !== bCtor && !(_.isFunction(aCtor) && (aCtor instanceof aCtor) &&
- _.isFunction(bCtor) && (bCtor instanceof bCtor))) {
- return false;
- }
+ // Objects with different constructors are not equivalent.
+ if ('constructor' in a != 'constructor' in b || a.constructor != b.constructor) return false;
// Deep compare objects.
for (var key in a) {
if (_.has(a, key)) {
// Count the expected number of properties.
size++;
// Deep compare each member.
- if (!(result = _.has(b, key) && eq(a[key], b[key], aStack, bStack))) break;
+ if (!(result = _.has(b, key) && eq(a[key], b[key], stack))) break;
}
}
// Ensure that both objects contain the same number of properties.
@@ -877,20 +749,18 @@
}
}
// Remove the first object from the stack of traversed objects.
- aStack.pop();
- bStack.pop();
+ stack.pop();
return result;
- };
+ }
// Perform a deep comparison to check if two objects are equal.
_.isEqual = function(a, b) {
- return eq(a, b, [], []);
+ return eq(a, b, []);
};
// Is a given array, string, or object empty?
// An "empty" object has no enumerable own-properties.
_.isEmpty = function(obj) {
- if (obj == null) return true;
if (_.isArray(obj) || _.isString(obj)) return obj.length === 0;
for (var key in obj) if (_.has(obj, key)) return false;
return true;
@@ -898,7 +768,7 @@
// Is a given value a DOM element?
_.isElement = function(obj) {
- return !!(obj && obj.nodeType === 1);
+ return !!(obj && obj.nodeType == 1);
};
// Is a given value an array?
@@ -912,36 +782,35 @@
return obj === Object(obj);
};
- // Add some isType methods: isArguments, isFunction, isString, isNumber, isDate, isRegExp.
- each(['Arguments', 'Function', 'String', 'Number', 'Date', 'RegExp'], function(name) {
- _['is' + name] = function(obj) {
- return toString.call(obj) == '[object ' + name + ']';
- };
- });
-
- // Define a fallback version of the method in browsers (ahem, IE), where
- // there isn't any inspectable "Arguments" type.
+ // Is a given variable an arguments object?
+ _.isArguments = function(obj) {
+ return toString.call(obj) == '[object Arguments]';
+ };
if (!_.isArguments(arguments)) {
_.isArguments = function(obj) {
return !!(obj && _.has(obj, 'callee'));
};
}
- // Optimize `isFunction` if appropriate.
- if (typeof (/./) !== 'function') {
- _.isFunction = function(obj) {
- return typeof obj === 'function';
- };
- }
-
- // Is a given object a finite number?
- _.isFinite = function(obj) {
- return _.isNumber(obj) && isFinite(obj);
+ // Is a given value a function?
+ _.isFunction = function(obj) {
+ return toString.call(obj) == '[object Function]';
};
- // Is the given value `NaN`? (NaN is the only number which does not equal itself).
+ // Is a given value a string?
+ _.isString = function(obj) {
+ return toString.call(obj) == '[object String]';
+ };
+
+ // Is a given value a number?
+ _.isNumber = function(obj) {
+ return toString.call(obj) == '[object Number]';
+ };
+
+ // Is the given value `NaN`?
_.isNaN = function(obj) {
- return _.isNumber(obj) && obj != +obj;
+ // `NaN` is the only value for which `===` is not reflexive.
+ return obj !== obj;
};
// Is a given value a boolean?
@@ -949,6 +818,16 @@
return obj === true || obj === false || toString.call(obj) == '[object Boolean]';
};
+ // Is a given value a date?
+ _.isDate = function(obj) {
+ return toString.call(obj) == '[object Date]';
+ };
+
+ // Is the given value a regular expression?
+ _.isRegExp = function(obj) {
+ return toString.call(obj) == '[object RegExp]';
+ };
+
// Is a given value equal to null?
_.isNull = function(obj) {
return obj === null;
@@ -959,8 +838,7 @@
return obj === void 0;
};
- // Shortcut function for checking if an object has a given property directly
- // on itself (in other words, not on a prototype).
+ // Has own property?
_.has = function(obj, key) {
return hasOwnProperty.call(obj, key);
};
@@ -981,65 +859,20 @@
};
// Run a function **n** times.
- _.times = function(n, iterator, context) {
+ _.times = function (n, iterator, context) {
for (var i = 0; i < n; i++) iterator.call(context, i);
};
- // Return a random integer between min and max (inclusive).
- _.random = function(min, max) {
- if (max == null) {
- max = min;
- min = 0;
- }
- return min + (0 | Math.random() * (max - min + 1));
+ // Escape a string for HTML interpolation.
+ _.escape = function(string) {
+ return (''+string).replace(/&/g, '&').replace(/</g, '<').replace(/>/g, '>').replace(/"/g, '"').replace(/'/g, ''').replace(/\//g,'/');
};
- // List of HTML entities for escaping.
- var entityMap = {
- escape: {
- '&': '&',
- '<': '<',
- '>': '>',
- '"': '"',
- "'": ''',
- '/': '/'
- }
- };
- entityMap.unescape = _.invert(entityMap.escape);
-
- // Regexes containing the keys and values listed immediately above.
- var entityRegexes = {
- escape: new RegExp('[' + _.keys(entityMap.escape).join('') + ']', 'g'),
- unescape: new RegExp('(' + _.keys(entityMap.unescape).join('|') + ')', 'g')
- };
-
- // Functions for escaping and unescaping strings to/from HTML interpolation.
- _.each(['escape', 'unescape'], function(method) {
- _[method] = function(string) {
- if (string == null) return '';
- return ('' + string).replace(entityRegexes[method], function(match) {
- return entityMap[method][match];
- });
- };
- });
-
- // If the value of the named property is a function then invoke it;
- // otherwise, return it.
- _.result = function(object, property) {
- if (object == null) return null;
- var value = object[property];
- return _.isFunction(value) ? value.call(object) : value;
- };
-
- // Add your own custom functions to the Underscore object.
+ // Add your own custom functions to the Underscore object, ensuring that
+ // they're correctly added to the OOP wrapper as well.
_.mixin = function(obj) {
each(_.functions(obj), function(name){
- var func = _[name] = obj[name];
- _.prototype[name] = function() {
- var args = [this._wrapped];
- push.apply(args, arguments);
- return result.call(this, func.apply(_, args));
- };
+ addToWrapper(name, _[name] = obj[name]);
});
};
@@ -1062,72 +895,41 @@
// When customizing `templateSettings`, if you don't want to define an
// interpolation, evaluation or escaping regex, we need one that is
// guaranteed not to match.
- var noMatch = /(.)^/;
+ var noMatch = /.^/;
- // Certain characters need to be escaped so that they can be put into a
- // string literal.
- var escapes = {
- "'": "'",
- '\\': '\\',
- '\r': 'r',
- '\n': 'n',
- '\t': 't',
- '\u2028': 'u2028',
- '\u2029': 'u2029'
+ // Within an interpolation, evaluation, or escaping, remove HTML escaping
+ // that had been previously added.
+ var unescape = function(code) {
+ return code.replace(/\\\\/g, '\\').replace(/\\'/g, "'");
};
- var escaper = /\\|'|\r|\n|\t|\u2028|\u2029/g;
-
// JavaScript micro-templating, similar to John Resig's implementation.
// Underscore templating handles arbitrary delimiters, preserves whitespace,
// and correctly escapes quotes within interpolated code.
- _.template = function(text, data, settings) {
- settings = _.defaults({}, settings, _.templateSettings);
-
- // Combine delimiters into one regular expression via alternation.
- var matcher = new RegExp([
- (settings.escape || noMatch).source,
- (settings.interpolate || noMatch).source,
- (settings.evaluate || noMatch).source
- ].join('|') + '|$', 'g');
-
- // Compile the template source, escaping string literals appropriately.
- var index = 0;
- var source = "__p+='";
- text.replace(matcher, function(match, escape, interpolate, evaluate, offset) {
- source += text.slice(index, offset)
- .replace(escaper, function(match) { return '\\' + escapes[match]; });
- source +=
- escape ? "'+\n((__t=(" + escape + "))==null?'':_.escape(__t))+\n'" :
- interpolate ? "'+\n((__t=(" + interpolate + "))==null?'':__t)+\n'" :
- evaluate ? "';\n" + evaluate + "\n__p+='" : '';
- index = offset + match.length;
- });
- source += "';\n";
-
- // If a variable is not specified, place data values in local scope.
- if (!settings.variable) source = 'with(obj||{}){\n' + source + '}\n';
-
- source = "var __t,__p='',__j=Array.prototype.join," +
- "print=function(){__p+=__j.call(arguments,'');};\n" +
- source + "return __p;\n";
-
- try {
- var render = new Function(settings.variable || 'obj', '_', source);
- } catch (e) {
- e.source = source;
- throw e;
- }
-
- if (data) return render(data, _);
- var template = function(data) {
- return render.call(this, data, _);
+ _.template = function(str, data) {
+ var c = _.templateSettings;
+ var tmpl = 'var __p=[],print=function(){__p.push.apply(__p,arguments);};' +
+ 'with(obj||{}){__p.push(\'' +
+ str.replace(/\\/g, '\\\\')
+ .replace(/'/g, "\\'")
+ .replace(c.escape || noMatch, function(match, code) {
+ return "',_.escape(" + unescape(code) + "),'";
+ })
+ .replace(c.interpolate || noMatch, function(match, code) {
+ return "'," + unescape(code) + ",'";
+ })
+ .replace(c.evaluate || noMatch, function(match, code) {
+ return "');" + unescape(code).replace(/[\r\n\t]/g, ' ') + ";__p.push('";
+ })
+ .replace(/\r/g, '\\r')
+ .replace(/\n/g, '\\n')
+ .replace(/\t/g, '\\t')
+ + "');}return __p.join('');";
+ var func = new Function('obj', '_', tmpl);
+ if (data) return func(data, _);
+ return function(data) {
+ return func.call(this, data, _);
};
-
- // Provide the compiled function source as a convenience for precompilation.
- template.source = 'function(' + (settings.variable || 'obj') + '){\n' + source + '}';
-
- return template;
};
// Add a "chain" function, which will delegate to the wrapper.
@@ -1135,15 +937,29 @@
return _(obj).chain();
};
- // OOP
+ // The OOP Wrapper
// ---------------
+
// If Underscore is called as a function, it returns a wrapped object that
// can be used OO-style. This wrapper holds altered versions of all the
// underscore functions. Wrapped objects may be chained.
+ var wrapper = function(obj) { this._wrapped = obj; };
+
+ // Expose `wrapper.prototype` as `_.prototype`
+ _.prototype = wrapper.prototype;
// Helper function to continue chaining intermediate results.
- var result = function(obj) {
- return this._chain ? _(obj).chain() : obj;
+ var result = function(obj, chain) {
+ return chain ? _(obj).chain() : obj;
+ };
+
+ // A method to easily add functions to the OOP wrapper.
+ var addToWrapper = function(name, func) {
+ wrapper.prototype[name] = function() {
+ var args = slice.call(arguments);
+ unshift.call(args, this._wrapped);
+ return result(func.apply(_, args), this._chain);
+ };
};
// Add all of the Underscore functions to the wrapper object.
@@ -1152,35 +968,32 @@
// Add all mutator Array functions to the wrapper.
each(['pop', 'push', 'reverse', 'shift', 'sort', 'splice', 'unshift'], function(name) {
var method = ArrayProto[name];
- _.prototype[name] = function() {
- var obj = this._wrapped;
- method.apply(obj, arguments);
- if ((name == 'shift' || name == 'splice') && obj.length === 0) delete obj[0];
- return result.call(this, obj);
+ wrapper.prototype[name] = function() {
+ var wrapped = this._wrapped;
+ method.apply(wrapped, arguments);
+ var length = wrapped.length;
+ if ((name == 'shift' || name == 'splice') && length === 0) delete wrapped[0];
+ return result(wrapped, this._chain);
};
});
// Add all accessor Array functions to the wrapper.
each(['concat', 'join', 'slice'], function(name) {
var method = ArrayProto[name];
- _.prototype[name] = function() {
- return result.call(this, method.apply(this._wrapped, arguments));
+ wrapper.prototype[name] = function() {
+ return result(method.apply(this._wrapped, arguments), this._chain);
};
});
- _.extend(_.prototype, {
+ // Start chaining a wrapped Underscore object.
+ wrapper.prototype.chain = function() {
+ this._chain = true;
+ return this;
+ };
- // Start chaining a wrapped Underscore object.
- chain: function() {
- this._chain = true;
- return this;
- },
-
- // Extracts the result from a wrapped and chained object.
- value: function() {
- return this._wrapped;
- }
-
- });
+ // Extracts the result from a wrapped and chained object.
+ wrapper.prototype.value = function() {
+ return this._wrapped;
+ };
}).call(this);
diff -r 55e7d7008efee2c5622f2505612265a9593ae992 -r 4bdb9214efd6ec510f2cc6e00224a467d36ba721 static/scripts/viz/sweepster.js
--- a/static/scripts/viz/sweepster.js
+++ b/static/scripts/viz/sweepster.js
@@ -3,8 +3,8 @@
* genomic visualization.
*/
-define(["libs/d3", "viz/trackster/util", "viz/visualization", "viz/trackster/tracks", "mvc/tools", "mvc/data"],
- function(d3, util, visualization, tracks, tools, data) {
+define(["libs/underscore", "libs/d3", "viz/trackster/util", "viz/visualization", "viz/trackster/tracks", "mvc/tools", "mvc/data"],
+ function(_, d3, util, visualization, tracks, tools, data) {
/**
* A collection of tool input settings. Object is useful for keeping a list of settings
diff -r 55e7d7008efee2c5622f2505612265a9593ae992 -r 4bdb9214efd6ec510f2cc6e00224a467d36ba721 static/scripts/viz/trackster/tracks.js
--- a/static/scripts/viz/trackster/tracks.js
+++ b/static/scripts/viz/trackster/tracks.js
@@ -1,7 +1,7 @@
define( ["libs/underscore", "viz/visualization", "viz/trackster/util",
"viz/trackster/slotting", "viz/trackster/painters", "mvc/data",
- "viz/trackster/filters", "viz/trackster_ui" ],
- function( _, visualization, util, slotting, painters, data, filters_mod, trackster_ui_mod ) {
+ "viz/trackster/filters" ],
+ function( _, visualization, util, slotting, painters, data, filters_mod ) {
var extend = _.extend;
var get_random_color = util.get_random_color;
Repository URL: https://bitbucket.org/galaxy/galaxy-central/
--
This is a commit notification from bitbucket.org. You are receiving
this because you have the service enabled, addressing the recipient of
this email.
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/changeset/78f37cb76a5f/
changeset: 78f37cb76a5f
user: james_taylor
date: 2012-10-01 22:55:29
summary: admin: another import fix
affected #: 1 file
diff -r 3c8f65f7e1a4f4217499f2369907a75a8dbcb4e9 -r 78f37cb76a5f981febf36b8119278c59d2319e91 lib/galaxy/web/base/controllers/admin.py
--- a/lib/galaxy/web/base/controllers/admin.py
+++ b/lib/galaxy/web/base/controllers/admin.py
@@ -4,6 +4,7 @@
from galaxy.model.orm import *
from galaxy.util import inflector
+from galaxy.web.form_builder import CheckboxField
class Admin( object ):
# Override these
Repository URL: https://bitbucket.org/galaxy/galaxy-central/
--
This is a commit notification from bitbucket.org. You are receiving
this because you have the service enabled, addressing the recipient of
this email.
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/changeset/cda0af45c3d3/
changeset: cda0af45c3d3
user: greg
date: 2012-10-01 21:04:52
summary: Handle unavailable main Galaxy tool shed when checking for migrated tools.
affected #: 2 files
diff -r 4ccb8691639233bb99b4f3e3ebb9b9eacf4c9461 -r cda0af45c3d3bd4fa9e62b37b5cc91f5272a0178 lib/galaxy/tool_shed/migrate/check.py
--- a/lib/galaxy/tool_shed/migrate/check.py
+++ b/lib/galaxy/tool_shed/migrate/check.py
@@ -43,6 +43,8 @@
db_schema = schema.ControlledSchema( engine, migrate_repository )
latest_tool_migration_script_number = migrate_repository.versions.latest
if latest_tool_migration_script_number != db_schema.version:
+ # The default behavior is that the tool shed is down.
+ tool_shed_accessible = False
if app.new_installation:
# New installations will not be missing tools, so we don't need to worry about them.
missing_tool_configs_dict = odict()
@@ -51,8 +53,12 @@
if tool_panel_configs:
# The missing_tool_configs_dict contents are something like:
# {'emboss_antigenic.xml': [('emboss', '5.0.0', 'package', '\nreadme blah blah blah\n')]}
- missing_tool_configs_dict = check_for_missing_tools( app, tool_panel_configs, latest_tool_migration_script_number )
+ tool_shed_accessible, missing_tool_configs_dict = check_for_missing_tools( app, tool_panel_configs, latest_tool_migration_script_number )
else:
+ # It doesn't matter if the tool shed is accessible since there are no migrated tools defined in the local Galaxy instance, but
+ # we have to set the value of tool_shed_accessible to True so that the value of migrate_tools.version can be correctly set in
+ # the database.
+ tool_shed_accessible = True
missing_tool_configs_dict = odict()
have_tool_dependencies = False
for k, v in missing_tool_configs_dict.items():
@@ -63,79 +69,82 @@
if os.path.abspath( os.path.join( os.getcwd(), 'universe_wsgi.ini' ) ) != galaxy_config_file:
config_arg = ' -c %s' % galaxy_config_file.replace( os.path.abspath( os.getcwd() ), '.' )
if not app.config.running_functional_tests:
- # Automatically update the value of the migrate_tools.version database table column.
- cmd = 'sh manage_tools.sh%s upgrade' % config_arg
- proc = subprocess.Popen( args=cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT )
- return_code = proc.wait()
- output = proc.stdout.read( 32768 )
- if return_code != 0:
- raise Exception( "Error attempting to update the value of migrate_tools.version: %s" % output )
- elif missing_tool_configs_dict:
- if len( tool_panel_configs ) == 1:
- plural = ''
- tool_panel_config_file_names = tool_panel_configs[ 0 ]
- else:
- plural = 's'
- tool_panel_config_file_names = ', '.join( tool_panel_configs )
- msg = "\n>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>"
- msg += "\n\nThe list of files at the end of this message refers to tools that are configured to load into the tool panel for\n"
- msg += "this Galaxy instance, but have been removed from the Galaxy distribution. These tools and their dependencies can be\n"
- msg += "automatically installed from the Galaxy tool shed at http://toolshed.g2.bx.psu.edu.\n\n"
- msg += "To skip this process, attempt to start your Galaxy server again (e.g., sh run.sh or whatever you use). If you do this,\n"
- msg += "be aware that these tools will no longer be available in your Galaxy tool panel, and entries for each of them should\n"
- msg += "be removed from your file%s named %s.\n\n" % ( plural, tool_panel_config_file_names )
- msg += "CRITICAL NOTE IF YOU PLAN TO INSTALL\n"
- msg += "The location in which the tool repositories will be installed is the value of the 'tool_path' attribute in the <tool>\n"
- msg += 'tag of the file named ./migrated_tool_conf.xml (i.e., <toolbox tool_path="../shed_tools">). The default location\n'
- msg += "setting is '../shed_tools', which may be problematic for some cluster environments, so make sure to change it before\n"
- msg += "you execute the installation process if appropriate. The configured location must be outside of the Galaxy installation\n"
- msg += "directory or it must be in a sub-directory protected by a properly configured .hgignore file if the directory is within\n"
- msg += "the Galaxy installation directory hierarchy. This is because tool shed repositories will be installed using mercurial's\n"
- msg += "clone feature, which creates .hg directories and associated mercurial repository files. Not having .hgignore properly\n"
- msg += "configured could result in undesired behavior when modifying or updating your local Galaxy instance or the tool shed\n"
- msg += "repositories if they are in directories that pose conflicts. See mercurial's .hgignore documentation at the following\n"
- msg += "URL for details.\n\nhttp://mercurial.selenic.com/wiki/.hgignore\n\n"
- if have_tool_dependencies:
- msg += "The following tool dependencies can also optionally be installed (see the option flag in the command below). If you\n"
- msg += "choose to install them (recommended), they will be installed within the location specified by the 'tool_dependency_dir'\n"
- msg += "setting in your main Galaxy configuration file (e.g., uninverse_wsgi.ini).\n"
- processed_tool_dependencies = []
+ if tool_shed_accessible:
+ # Automatically update the value of the migrate_tools.version database table column.
+ cmd = 'sh manage_tools.sh%s upgrade' % config_arg
+ proc = subprocess.Popen( args=cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT )
+ return_code = proc.wait()
+ output = proc.stdout.read( 32768 )
+ if return_code != 0:
+ raise Exception( "Error attempting to update the value of migrate_tools.version: %s" % output )
+ elif missing_tool_configs_dict:
+ if len( tool_panel_configs ) == 1:
+ plural = ''
+ tool_panel_config_file_names = tool_panel_configs[ 0 ]
+ else:
+ plural = 's'
+ tool_panel_config_file_names = ', '.join( tool_panel_configs )
+ msg = "\n>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>"
+ msg += "\n\nThe list of files at the end of this message refers to tools that are configured to load into the tool panel for\n"
+ msg += "this Galaxy instance, but have been removed from the Galaxy distribution. These tools and their dependencies can be\n"
+ msg += "automatically installed from the Galaxy tool shed at http://toolshed.g2.bx.psu.edu.\n\n"
+ msg += "To skip this process, attempt to start your Galaxy server again (e.g., sh run.sh or whatever you use). If you do this,\n"
+ msg += "be aware that these tools will no longer be available in your Galaxy tool panel, and entries for each of them should\n"
+ msg += "be removed from your file%s named %s.\n\n" % ( plural, tool_panel_config_file_names )
+ msg += "CRITICAL NOTE IF YOU PLAN TO INSTALL\n"
+ msg += "The location in which the tool repositories will be installed is the value of the 'tool_path' attribute in the <tool>\n"
+ msg += 'tag of the file named ./migrated_tool_conf.xml (i.e., <toolbox tool_path="../shed_tools">). The default location\n'
+ msg += "setting is '../shed_tools', which may be problematic for some cluster environments, so make sure to change it before\n"
+ msg += "you execute the installation process if appropriate. The configured location must be outside of the Galaxy installation\n"
+ msg += "directory or it must be in a sub-directory protected by a properly configured .hgignore file if the directory is within\n"
+ msg += "the Galaxy installation directory hierarchy. This is because tool shed repositories will be installed using mercurial's\n"
+ msg += "clone feature, which creates .hg directories and associated mercurial repository files. Not having .hgignore properly\n"
+ msg += "configured could result in undesired behavior when modifying or updating your local Galaxy instance or the tool shed\n"
+ msg += "repositories if they are in directories that pose conflicts. See mercurial's .hgignore documentation at the following\n"
+ msg += "URL for details.\n\nhttp://mercurial.selenic.com/wiki/.hgignore\n\n"
+ if have_tool_dependencies:
+ msg += "The following tool dependencies can also optionally be installed (see the option flag in the command below). If you\n"
+ msg += "choose to install them (recommended), they will be installed within the location specified by the 'tool_dependency_dir'\n"
+ msg += "setting in your main Galaxy configuration file (e.g., uninverse_wsgi.ini).\n"
+ processed_tool_dependencies = []
+ for missing_tool_config, tool_dependencies in missing_tool_configs_dict.items():
+ for tool_dependencies_tup in tool_dependencies:
+ if tool_dependencies_tup not in processed_tool_dependencies:
+ msg += "------------------------------------\n"
+ msg += "Tool Dependency\n"
+ msg += "------------------------------------\n"
+ msg += "Name: %s, Version: %s, Type: %s\n" % ( tool_dependencies_tup[ 0 ],
+ tool_dependencies_tup[ 1 ],
+ tool_dependencies_tup[ 2 ] )
+ if tool_dependencies_tup[ 3 ]:
+ msg += "Requirements and installation information:\n"
+ msg += "%s\n" % tool_dependencies_tup[ 3 ]
+ else:
+ msg += "\n"
+ msg += "------------------------------------\n"
+ processed_tool_dependencies.append( tool_dependencies_tup )
+ msg += "\n"
+ msg += "%s" % output.replace( 'done', '' )
+ msg += "vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n"
+ msg += "sh ./scripts/migrate_tools/%04d_tools.sh\n" % latest_tool_migration_script_number
+ msg += "^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n\n"
+ if have_tool_dependencies:
+ msg += "The tool dependencies listed above will be installed along with the repositories if you add the 'install_dependencies'\n"
+ msg += "option to the above command like this:\n\n"
+ msg += "vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n"
+ msg += "sh ./scripts/migrate_tools/%04d_tools.sh install_dependencies\n" % latest_tool_migration_script_number
+ msg += "^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n\n"
+ msg += "Tool dependencies can be installed after the repositories have been installed as well.\n\n"
+ msg += "After the installation process finishes, you can start your Galaxy server. As part of this installation process,\n"
+ msg += "entries for each of the following tool config files will be added to the file named ./migrated_tool_conf.xml, so these\n"
+ msg += "tools will continue to be loaded into your tool panel. Because of this, existing entries for these files should be\n"
+ msg += "removed from your file%s named %s, but only after the installation process finishes.\n\n" % ( plural, tool_panel_config_file_names )
for missing_tool_config, tool_dependencies in missing_tool_configs_dict.items():
- for tool_dependencies_tup in tool_dependencies:
- if tool_dependencies_tup not in processed_tool_dependencies:
- msg += "------------------------------------\n"
- msg += "Tool Dependency\n"
- msg += "------------------------------------\n"
- msg += "Name: %s, Version: %s, Type: %s\n" % ( tool_dependencies_tup[ 0 ],
- tool_dependencies_tup[ 1 ],
- tool_dependencies_tup[ 2 ] )
- if tool_dependencies_tup[ 3 ]:
- msg += "Requirements and installation information:\n"
- msg += "%s\n" % tool_dependencies_tup[ 3 ]
- else:
- msg += "\n"
- msg += "------------------------------------\n"
- processed_tool_dependencies.append( tool_dependencies_tup )
- msg += "\n"
- msg += "%s" % output.replace( 'done', '' )
- msg += "vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n"
- msg += "sh ./scripts/migrate_tools/%04d_tools.sh\n" % latest_tool_migration_script_number
- msg += "^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n\n"
- if have_tool_dependencies:
- msg += "The tool dependencies listed above will be installed along with the repositories if you add the 'install_dependencies'\n"
- msg += "option to the above command like this:\n\n"
- msg += "vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv\n"
- msg += "sh ./scripts/migrate_tools/%04d_tools.sh install_dependencies\n" % latest_tool_migration_script_number
- msg += "^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n\n"
- msg += "Tool dependencies can be installed after the repositories have been installed as well.\n\n"
- msg += "After the installation process finishes, you can start your Galaxy server. As part of this installation process,\n"
- msg += "entries for each of the following tool config files will be added to the file named ./migrated_tool_conf.xml, so these\n"
- msg += "tools will continue to be loaded into your tool panel. Because of this, existing entries for these files should be\n"
- msg += "removed from your file%s named %s, but only after the installation process finishes.\n\n" % ( plural, tool_panel_config_file_names )
- for missing_tool_config, tool_dependencies in missing_tool_configs_dict.items():
- msg += "%s\n" % missing_tool_config
- msg += "<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\n"
- raise Exception( msg )
+ msg += "%s\n" % missing_tool_config
+ msg += "<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\n"
+ raise Exception( msg )
+ else:
+ log.debug( "The main Galaxy tool shed is not currently available, so skipped tool migration %s until next server startup" % db_schema.version )
else:
log.info( "At migrate_tools version %d" % db_schema.version )
diff -r 4ccb8691639233bb99b4f3e3ebb9b9eacf4c9461 -r cda0af45c3d3bd4fa9e62b37b5cc91f5272a0178 lib/galaxy/tool_shed/migrate/common.py
--- a/lib/galaxy/tool_shed/migrate/common.py
+++ b/lib/galaxy/tool_shed/migrate/common.py
@@ -21,6 +21,8 @@
root = tree.getroot()
tool_shed = root.get( 'name' )
tool_shed_url = get_tool_shed_url_from_tools_xml_file_path( app, tool_shed )
+ # The default behavior is that the tool shed is down.
+ tool_shed_accessible = False
if tool_shed_url:
for elem in root:
if elem.tag == 'repository':
@@ -30,36 +32,44 @@
changeset_revision = elem.get( 'changeset_revision' )
url = '%s/repository/get_tool_dependencies?name=%s&owner=%s&changeset_revision=%s&webapp=install_manager' % \
( tool_shed_url, repository_name, REPOSITORY_OWNER, changeset_revision )
- response = urllib2.urlopen( url )
- text = response.read()
- response.close()
- if text:
- tool_dependencies_dict = tool_shed_decode( text )
- for dependency_key, requirements_dict in tool_dependencies_dict.items():
- tool_dependency_name = requirements_dict[ 'name' ]
- tool_dependency_version = requirements_dict[ 'version' ]
- tool_dependency_type = requirements_dict[ 'type' ]
- tool_dependency_readme = requirements_dict.get( 'readme', '' )
- tool_dependencies.append( ( tool_dependency_name, tool_dependency_version, tool_dependency_type, tool_dependency_readme ) )
- for tool_elem in elem.findall( 'tool' ):
- migrated_tool_configs_dict[ tool_elem.get( 'file' ) ] = tool_dependencies
- # Parse the proprietary tool_panel_configs (the default is tool_conf.xml) and generate the list of missing tool config file names.
- missing_tool_configs_dict = odict()
- for tool_panel_config in tool_panel_configs:
- tree = util.parse_xml( tool_panel_config )
- root = tree.getroot()
- for elem in root:
- if elem.tag == 'tool':
- missing_tool_configs_dict = check_tool_tag_set( elem, migrated_tool_configs_dict, missing_tool_configs_dict )
- elif elem.tag == 'section':
- for section_elem in elem:
- if section_elem.tag == 'tool':
- missing_tool_configs_dict = check_tool_tag_set( section_elem, migrated_tool_configs_dict, missing_tool_configs_dict )
+ try:
+ response = urllib2.urlopen( url )
+ text = response.read()
+ response.close()
+ tool_shed_accessible = True
+ except Exception, e:
+ # Tool shed may be unavailable - we have to set tool_shed_accessible since we're looping.
+ tool_shed_accessible = False
+ print "The URL\n%s\nraised the exception:\n%s\n" % ( url, str( e ) )
+ if tool_shed_accessible:
+ if text:
+ tool_dependencies_dict = tool_shed_decode( text )
+ for dependency_key, requirements_dict in tool_dependencies_dict.items():
+ tool_dependency_name = requirements_dict[ 'name' ]
+ tool_dependency_version = requirements_dict[ 'version' ]
+ tool_dependency_type = requirements_dict[ 'type' ]
+ tool_dependency_readme = requirements_dict.get( 'readme', '' )
+ tool_dependencies.append( ( tool_dependency_name, tool_dependency_version, tool_dependency_type, tool_dependency_readme ) )
+ for tool_elem in elem.findall( 'tool' ):
+ migrated_tool_configs_dict[ tool_elem.get( 'file' ) ] = tool_dependencies
+ if tool_shed_accessible:
+ # Parse the proprietary tool_panel_configs (the default is tool_conf.xml) and generate the list of missing tool config file names.
+ missing_tool_configs_dict = odict()
+ for tool_panel_config in tool_panel_configs:
+ tree = util.parse_xml( tool_panel_config )
+ root = tree.getroot()
+ for elem in root:
+ if elem.tag == 'tool':
+ missing_tool_configs_dict = check_tool_tag_set( elem, migrated_tool_configs_dict, missing_tool_configs_dict )
+ elif elem.tag == 'section':
+ for section_elem in elem:
+ if section_elem.tag == 'tool':
+ missing_tool_configs_dict = check_tool_tag_set( section_elem, migrated_tool_configs_dict, missing_tool_configs_dict )
else:
exception_msg = '\n\nThe entry for the main Galaxy tool shed at %s is missing from the %s file. ' % ( tool_shed, app.config.tool_sheds_config )
exception_msg += 'The entry for this tool shed must always be available in this file, so re-add it before attempting to start your Galaxy server.\n'
raise Exception( exception_msg )
- return missing_tool_configs_dict
+ return tool_shed_accessible, missing_tool_configs_dict
def check_tool_tag_set( elem, migrated_tool_configs_dict, missing_tool_configs_dict ):
file_path = elem.get( 'file', None )
if file_path:
Repository URL: https://bitbucket.org/galaxy/galaxy-central/
--
This is a commit notification from bitbucket.org. You are receiving
this because you have the service enabled, addressing the recipient of
this email.
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/changeset/4ccb86916392/
changeset: 4ccb86916392
user: natefoo
date: 2012-10-01 19:45:37
summary: pgcleanup: Print a useful message if no options are given.
affected #: 1 file
diff -r 844e566f36acc3d94856a55c0d4d4dcf291f8b81 -r 4ccb8691639233bb99b4f3e3ebb9b9eacf4c9461 scripts/cleanup_datasets/pgcleanup.py
--- a/scripts/cleanup_datasets/pgcleanup.py
+++ b/scripts/cleanup_datasets/pgcleanup.py
@@ -76,6 +76,11 @@
self.options.sequence = [ x.strip() for x in self.options.sequence.split(',') ]
+ if self.options.sequence == ['']:
+ print "Error: At least one action must be specified in the action sequence\n"
+ parser.print_help()
+ sys.exit(0)
+
def __setup_logging(self):
format = "%(funcName)s %(levelname)s %(asctime)s %(message)s"
if self.options.debug:
Repository URL: https://bitbucket.org/galaxy/galaxy-central/
--
This is a commit notification from bitbucket.org. You are receiving
this because you have the service enabled, addressing the recipient of
this email.
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/changeset/844e566f36ac/
changeset: 844e566f36ac
user: greg
date: 2012-10-01 18:24:53
summary: Handle the case where a tool dependency definition changed in a tool shed repository and the new definition was pulled to a Galaxy installed repository when the Galaxy admin got updates for the repository.
affected #: 5 files
diff -r de2c99ce5f749582c3ce3bfb02422588c70b1a06 -r 844e566f36acc3d94856a55c0d4d4dcf291f8b81 lib/galaxy/model/__init__.py
--- a/lib/galaxy/model/__init__.py
+++ b/lib/galaxy/model/__init__.py
@@ -3077,10 +3077,16 @@
self.error_message = error_message
@property
def can_install( self ):
- return self.status in [ self.installation_status.NEVER_INSTALLED, self.installation_status.UNINSTALLED ]
+ return self.status in [ self.installation_status.NEVER_INSTALLED, self.installation_status.UNINSTALLED ]
@property
def can_uninstall( self ):
- return self.status in [ self.installation_status.ERROR, self.installation_status.INSTALLED ]
+ return self.status in [ self.installation_status.ERROR, self.installation_status.INSTALLED ]
+ @property
+ def can_update( self ):
+ return self.status in [ self.installation_status.NEVER_INSTALLED,
+ self.installation_status.INSTALLED,
+ self.installation_status.ERROR,
+ self.installation_status.UNINSTALLED ]
@property
def in_error_state( self ):
return self.status == self.installation_status.ERROR
diff -r de2c99ce5f749582c3ce3bfb02422588c70b1a06 -r 844e566f36acc3d94856a55c0d4d4dcf291f8b81 lib/galaxy/tool_shed/install_manager.py
--- a/lib/galaxy/tool_shed/install_manager.py
+++ b/lib/galaxy/tool_shed/install_manager.py
@@ -138,6 +138,7 @@
relative_install_dir=relative_install_dir,
repository_files_dir=None,
resetting_all_metadata_on_repository=False,
+ updating_installed_repository=False,
webapp='galaxy' )
tool_shed_repository.metadata = metadata_dict
self.app.sa_session.add( tool_shed_repository )
diff -r de2c99ce5f749582c3ce3bfb02422588c70b1a06 -r 844e566f36acc3d94856a55c0d4d4dcf291f8b81 lib/galaxy/util/shed_util.py
--- a/lib/galaxy/util/shed_util.py
+++ b/lib/galaxy/util/shed_util.py
@@ -528,7 +528,6 @@
status=app.model.ToolDependency.installation_status.NEVER_INSTALLED,
set_status=set_status )
tool_dependency_objects.append( tool_dependency )
-
elif tool_dependency_type == 'set_environment':
for env_elem in elem:
# <environment_variable name="R_SCRIPT_PATH" action="set_to">$REPOSITORY_INSTALL_DIR</environment_variable>
@@ -603,13 +602,19 @@
tool_dependencies_dict[ 'set_environment' ] = [ requirements_dict ]
return tool_dependencies_dict
def generate_metadata_for_changeset_revision( app, repository, repository_clone_url, relative_install_dir=None, repository_files_dir=None,
- resetting_all_metadata_on_repository=False, webapp='galaxy' ):
+ resetting_all_metadata_on_repository=False, updating_installed_repository=False, webapp='galaxy' ):
"""
Generate metadata for a repository using it's files on disk. To generate metadata for changeset revisions older than the repository tip,
the repository will have been cloned to a temporary location and updated to a specified changeset revision to access that changeset revision's
disk files, so the value of repository_files_dir will not always be repository.repo_path (it could be an absolute path to a temporary directory
containing a clone). If it is an absolute path, the value of relative_install_dir must contain repository.repo_path.
"""
+ if updating_installed_repository:
+ # Keep the original tool shed repository metadata if setting metadata on a repository installed into a local Galaxy instance for which
+ # we have pulled updates.
+ original_repository_metadata = repository.metadata
+ else:
+ original_repository_metadata = None
readme_file_names = get_readme_file_names( repository.name )
metadata_dict = {}
invalid_file_tups = []
@@ -724,7 +729,11 @@
# This step must be done after metadata for tools has been defined.
tool_dependencies_config = get_config_from_disk( 'tool_dependencies.xml', files_dir )
if tool_dependencies_config:
- metadata_dict = generate_tool_dependency_metadata( tool_dependencies_config, metadata_dict )
+ metadata_dict = generate_tool_dependency_metadata( app,
+ repository,
+ tool_dependencies_config,
+ metadata_dict,
+ original_repository_metadata=original_repository_metadata )
if invalid_tool_configs:
metadata_dict [ 'invalid_tools' ] = invalid_tool_configs
# Reset the value of the app's tool_data_path and tool_data_table_config_path to their respective original values.
@@ -747,11 +756,16 @@
if requirements_dict:
tool_dependencies_dict[ dependency_key ] = requirements_dict
return tool_dependencies_dict
-def generate_tool_dependency_metadata( tool_dependencies_config, metadata_dict ):
+def generate_tool_dependency_metadata( app, repository, tool_dependencies_config, metadata_dict, original_repository_metadata=None ):
"""
If the combination of name, version and type of each element is defined in the <requirement> tag for at least one tool in the repository,
then update the received metadata_dict with information from the parsed tool_dependencies_config.
"""
+ if original_repository_metadata:
+ # Keep a copy of the original tool dependencies dictionary in the metadata.
+ original_tool_dependencies_dict = original_repository_metadata.get( 'tool_dependencies', None )
+ else:
+ original_tool_dependencies_dict = None
try:
tree = ElementTree.parse( tool_dependencies_config )
except Exception, e:
@@ -770,6 +784,10 @@
if tool_dependencies_dict:
metadata_dict[ 'tool_dependencies' ] = tool_dependencies_dict
if tool_dependencies_dict:
+ if original_tool_dependencies_dict:
+ # We're generating metadata on an update pulled to a tool shed repository installed into a Galaxy instance, so handle changes to
+ # tool dependencies appropriately.
+ handle_existing_tool_dependencies_that_changed_in_update( app, repository, original_tool_dependencies_dict, tool_dependencies_dict )
metadata_dict[ 'tool_dependencies' ] = tool_dependencies_dict
return metadata_dict
def generate_tool_guid( repository_clone_url, tool ):
@@ -1470,6 +1488,24 @@
# Reset the tool_data_tables by loading the empty tool_data_table_conf.xml file.
reset_tool_data_tables( app )
return repository_tools_tups
+def handle_existing_tool_dependencies_that_changed_in_update( app, repository, original_dependency_dict, new_dependency_dict ):
+ """
+ This method is called when a Galaxy admin is getting updates for an installed tool shed repository in order to cover the case where an
+ existing tool dependency was changed (e.g., the version of the dependency was changed) but the tool version for which it is a dependency
+ was not changed. In this case, we only want to determine if any of the dependency information defined in original_dependency_dict was
+ changed in new_dependency_dict. We don't care if new dependencies were added in new_dependency_dict since they will just be treated as
+ missing dependencies for the tool.
+ """
+ updated_tool_dependency_names = []
+ deleted_tool_dependency_names = []
+ for original_dependency_key, original_dependency_val_dict in original_dependency_dict.items():
+ if original_dependency_key not in new_dependency_dict:
+ updated_tool_dependency = update_existing_tool_dependency( app, repository, original_dependency_val_dict, new_dependency_dict )
+ if updated_tool_dependency:
+ updated_tool_dependency_names.append( updated_tool_dependency.name )
+ else:
+ deleted_tool_dependency_names.append( original_dependency_val_dict[ 'name' ] )
+ return updated_tool_dependency_names, deleted_tool_dependency_names
def handle_missing_index_file( app, tool_path, sample_files, repository_tools_tups, sample_files_copied ):
"""
Inspect each tool to see if it has any input parameters that are dynamically generated select lists that depend on a .loc file.
@@ -1862,21 +1898,28 @@
trans.app.toolbox.write_integrated_tool_panel_config_file()
def remove_tool_dependency( trans, tool_dependency ):
dependency_install_dir = tool_dependency.installation_directory( trans.app )
- try:
- shutil.rmtree( dependency_install_dir )
- removed = True
- error_message = ''
- log.debug( "Removed tool dependency installation directory: %s" % str( dependency_install_dir ) )
- except Exception, e:
- removed = False
- error_message = "Error removing tool dependency installation directory %s: %s" % ( str( dependency_install_dir ), str( e ) )
- log.debug( error_message )
+ removed, error_message = remove_tool_dependency_installation_directory( dependency_install_dir )
if removed:
tool_dependency.status = trans.model.ToolDependency.installation_status.UNINSTALLED
tool_dependency.error_message = None
trans.sa_session.add( tool_dependency )
trans.sa_session.flush()
return removed, error_message
+def remove_tool_dependency_installation_directory( dependency_install_dir ):
+ if os.path.exists( dependency_install_dir ):
+ try:
+ shutil.rmtree( dependency_install_dir )
+ removed = True
+ error_message = ''
+ log.debug( "Removed tool dependency installation directory: %s" % str( dependency_install_dir ) )
+ except Exception, e:
+ removed = False
+ error_message = "Error removing tool dependency installation directory %s: %s" % ( str( dependency_install_dir ), str( e ) )
+ log.debug( error_message )
+ else:
+ removed = True
+ error_message = ''
+ return removed, error_message
def reset_tool_data_tables( app ):
# Reset the tool_data_tables to an empty dictionary.
app.tool_data_tables.data_tables = {}
@@ -1925,7 +1968,7 @@
translated.append( '' )
return ''.join( translated )
def to_html_str( text ):
- """Translates the characters in text to sn html string"""
+ """Translates the characters in text to an html string"""
translated = []
for c in text:
if c in VALID_CHARS:
@@ -1954,6 +1997,63 @@
else:
translated_string = ''
return translated_string
+def update_existing_tool_dependency( app, repository, original_dependency_dict, new_dependencies_dict ):
+ """
+ Update an exsiting tool dependency whose definition was updated in a change set pulled by a Galaxy administrator when getting updates
+ to an installed tool shed repository. The original_dependency_dict is a single tool dependency definition, an example of which is:
+ {"name": "bwa",
+ "readme": "\\nCompiling BWA requires zlib and libpthread to be present on your system.\\n ",
+ "type": "package",
+ "version": "0.6.2"}
+ The new_dependencies_dict is the dictionary generated by the generate_tool_dependency_metadata method.
+ """
+ new_tool_dependency = None
+ original_name = original_dependency_dict[ 'name' ]
+ original_type = original_dependency_dict[ 'type' ]
+ original_version = original_dependency_dict[ 'version' ]
+ # Locate the appropriate tool_dependency associated with the repository.
+ tool_dependency = None
+ for tool_dependency in repository.tool_dependencies:
+ if tool_dependency.name == original_name and tool_dependency.type == original_type and tool_dependency.version == original_version:
+ break
+ if tool_dependency and tool_dependency.can_update:
+ dependency_install_dir = tool_dependency.installation_directory( app )
+ removed_from_disk, error_message = remove_tool_dependency_installation_directory( dependency_install_dir )
+ if removed_from_disk:
+ sa_session = app.model.context.current
+ new_dependency_name = None
+ new_dependency_type = None
+ new_dependency_version = None
+ for new_dependency_key, new_dependency_val_dict in new_dependencies_dict.items():
+ # Match on name only, hopefully this will be enough!
+ if original_name == new_dependency_val_dict[ 'name' ]:
+ new_dependency_name = new_dependency_val_dict[ 'name' ]
+ new_dependency_type = new_dependency_val_dict[ 'type' ]
+ new_dependency_version = new_dependency_val_dict[ 'version' ]
+ break
+ if new_dependency_name and new_dependency_type and new_dependency_version:
+ # Update all attributes of the tool_dependency record in the database.
+ log.debug( "Updating tool dependency '%s' with type '%s' and version '%s' to have new type '%s' and version '%s'." % \
+ ( str( tool_dependency.name ),
+ str( tool_dependency.type ),
+ str( tool_dependency.version ),
+ str( new_dependency_type ),
+ str( new_dependency_version ) ) )
+ tool_dependency.type = new_dependency_type
+ tool_dependency.version = new_dependency_version
+ tool_dependency.status = app.model.ToolDependency.installation_status.UNINSTALLED
+ tool_dependency.error_message = None
+ sa_session.add( tool_dependency )
+ sa_session.flush()
+ new_tool_dependency = tool_dependency
+ else:
+ # We have no new tool dependency definition based on a matching dependency name, so remove the existing tool dependency record
+ # from the database.
+ log.debug( "Deleting tool dependency with name '%s', type '%s' and version '%s' from the database since it is no longer defined." % \
+ ( str( tool_dependency.name ), str( tool_dependency.type ), str( tool_dependency.version ) ) )
+ sa_session.delete( tool_dependency )
+ sa_session.flush()
+ return new_tool_dependency
def update_repository( repo, ctx_rev=None ):
"""
Update the cloned repository to changeset_revision. It is critical that the installed repository is updated to the desired
diff -r de2c99ce5f749582c3ce3bfb02422588c70b1a06 -r 844e566f36acc3d94856a55c0d4d4dcf291f8b81 lib/galaxy/webapps/community/controllers/common.py
--- a/lib/galaxy/webapps/community/controllers/common.py
+++ b/lib/galaxy/webapps/community/controllers/common.py
@@ -753,6 +753,7 @@
relative_install_dir=repo_dir,
repository_files_dir=work_dir,
resetting_all_metadata_on_repository=True,
+ updating_installed_repository=False,
webapp='community' )
if current_metadata_dict:
if not metadata_changeset_revision and not metadata_dict:
@@ -828,6 +829,7 @@
relative_install_dir=repo_dir,
repository_files_dir=None,
resetting_all_metadata_on_repository=False,
+ updating_installed_repository=False,
webapp='community' )
if metadata_dict:
downloadable = is_downloadable( metadata_dict )
diff -r de2c99ce5f749582c3ce3bfb02422588c70b1a06 -r 844e566f36acc3d94856a55c0d4d4dcf291f8b81 lib/galaxy/webapps/galaxy/controllers/admin_toolshed.py
--- a/lib/galaxy/webapps/galaxy/controllers/admin_toolshed.py
+++ b/lib/galaxy/webapps/galaxy/controllers/admin_toolshed.py
@@ -731,6 +731,7 @@
relative_install_dir=relative_install_dir,
repository_files_dir=None,
resetting_all_metadata_on_repository=False,
+ updating_installed_repository=False,
webapp='galaxy' )
tool_shed_repository.metadata = metadata_dict
trans.sa_session.add( tool_shed_repository )
@@ -1447,6 +1448,7 @@
relative_install_dir=relative_install_dir,
repository_files_dir=None,
resetting_all_metadata_on_repository=False,
+ updating_installed_repository=False,
webapp='galaxy' )
repository.metadata = metadata_dict
trans.sa_session.add( repository )
@@ -1566,8 +1568,7 @@
# Filter tool dependencies to only those that are installed.
tool_dependencies_for_uninstallation = []
for tool_dependency in tool_dependencies:
- if tool_dependency.status in [ trans.model.ToolDependency.installation_status.INSTALLED,
- trans.model.ToolDependency.installation_status.ERROR ]:
+ if tool_dependency.can_uninstall:
tool_dependencies_for_uninstallation.append( tool_dependency )
for tool_dependency in tool_dependencies_for_uninstallation:
uninstalled, error_message = remove_tool_dependency( trans, tool_dependency )
@@ -1616,14 +1617,16 @@
repository_clone_url = os.path.join( tool_shed_url, 'repos', owner, name )
pull_repository( repo, repository_clone_url, latest_ctx_rev )
update_repository( repo, latest_ctx_rev )
+ tool_shed = clean_tool_shed_url( tool_shed_url )
# Update the repository metadata.
- tool_shed = clean_tool_shed_url( tool_shed_url )
metadata_dict, invalid_file_tups = generate_metadata_for_changeset_revision( app=trans.app,
repository=repository,
repository_clone_url=repository_clone_url,
relative_install_dir=relative_install_dir,
repository_files_dir=None,
- resetting_all_metadata_on_repository=False )
+ resetting_all_metadata_on_repository=False,
+ updating_installed_repository=True,
+ webapp='galaxy' )
repository.metadata = metadata_dict
# Update the repository changeset_revision in the database.
repository.changeset_revision = latest_changeset_revision
Repository URL: https://bitbucket.org/galaxy/galaxy-central/
--
This is a commit notification from bitbucket.org. You are receiving
this because you have the service enabled, addressing the recipient of
this email.