From 1c5691964e0f0645d3c80e69a2e9982a7602b9b4 Mon Sep 17 00:00:00 2001 From: John Chilton Date: Fri, 25 Jul 2014 10:28:50 -0500 Subject: [PATCH] Implement optional collection params. Was already parsing optional attribute but I put exactly zero thought into the implementation so these didn't work at all I don't think. This fills out the implementation, adds a test tool, and some cheetah helpers to facilitate this: "#if $collect_param" will fail if input not supplied or collection is empty and "#if $collect_param.is_input_supplied" will fail is input not supplied (i.e. empty collections will pass this check). --- lib/galaxy/tools/actions/__init__.py | 2 + lib/galaxy/tools/wrappers.py | 23 +++++++++++ .../tools/collection_optional_param.xml | 38 +++++++++++++++++++ test/functional/tools/samples_tool_conf.xml | 1 + 4 files changed, 64 insertions(+) create mode 100644 test/functional/tools/collection_optional_param.xml diff --git a/lib/galaxy/tools/actions/__init__.py b/lib/galaxy/tools/actions/__init__.py index d9168401e54..fb6cd299adb 100644 --- a/lib/galaxy/tools/actions/__init__.py +++ b/lib/galaxy/tools/actions/__init__.py @@ -114,6 +114,8 @@ class DefaultToolAction( object ): #allow explicit conversion to be stored in job_parameter table target_dict[ conversion_name ] = conversion_data.id # a more robust way to determine JSONable value is desired elif isinstance( input, DataCollectionToolParameter ): + if not value: + return for i, v in enumerate( value.collection.dataset_instances ): data = v current_user_roles = trans.get_current_user_roles() diff --git a/lib/galaxy/tools/wrappers.py b/lib/galaxy/tools/wrappers.py index 5cc047af2c5..38e1956758e 100644 --- a/lib/galaxy/tools/wrappers.py +++ b/lib/galaxy/tools/wrappers.py @@ -269,6 +269,12 @@ class DatasetCollectionWrapper( object, HasDatasets ): def __init__( self, has_collection, dataset_paths=[], **kwargs ): super(DatasetCollectionWrapper, self).__init__() + if has_collection is None: + self.__input_supplied = False + return + else: + self.__input_supplied = True + if hasattr( has_collection, "name" ): # It is a HistoryDatasetCollectionAssociation collection = has_collection.collection @@ -298,20 +304,37 @@ class DatasetCollectionWrapper( object, HasDatasets ): self.element_instance_list = element_instance_list def keys( self ): + if not self.__input_supplied: + return [] return self.element_instances.keys() @property def is_collection( self ): return True + @property + def is_input_supplied( self ): + return self.__input_supplied + def __getitem__( self, key ): + if not self.__input_supplied: + return None if isinstance( key, int ): return self.element_instance_list[ key ] else: return self.element_instances[ key ] def __getattr__( self, key ): + if not self.__input_supplied: + return None return self.element_instances[ key ] def __iter__( self ): + if not self.__input_supplied: + return [].__iter__() return self.element_instance_list.__iter__() + + def __nonzero__( self ): + # Fail `#if $param` checks in cheetah is optional input + # not specified or if resulting collection is empty. + return self.__input_supplied and bool( self.element_instance_list ) diff --git a/test/functional/tools/collection_optional_param.xml b/test/functional/tools/collection_optional_param.xml new file mode 100644 index 00000000000..2839461c025 --- /dev/null +++ b/test/functional/tools/collection_optional_param.xml @@ -0,0 +1,38 @@ + + + #if $f1 + cat $f1.forward $f1['reverse'] >> $out1; + #else + echo "No input specified." >> $out1; + #end if + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/test/functional/tools/samples_tool_conf.xml b/test/functional/tools/samples_tool_conf.xml index 730e8bea78d..7bda6b73816 100644 --- a/test/functional/tools/samples_tool_conf.xml +++ b/test/functional/tools/samples_tool_conf.xml @@ -22,4 +22,5 @@ + \ No newline at end of file