code: def register_action(self, relative_directory, file_pattern, action_function):
          
          # test if directory exists
          if not os.path.isdir(os.path.join(self.__root_directory, relative_directory)):
              self.log_error('Relative directory \'%s\' does not exist.' % relative_directory)
              return
  
          if not self.__is_function_action(action_function):
                  self.log_error('Attached function is not an action function.')
  
          self.__add_action(relative_directory, GeneratorAction(file_pattern, action_function))
docs: Add/register an "action".
  
          Args:
              relative_directory (str): Relative directory from root directory. Separator is OS dependent. For instance,
                  under linux, you can register the following:
  
                  >>> register_action('cysparse/sparse/utils', 'find*.cpy', action_function)
  
                  This means that all files corresponding to the `'find*.cpy'` pattern inside the `cysparse/sparse/utils`
                  directory can (see Warning) be dealt with the `action_function`.
  
              file_pattern: A :program:`fnmatch` pattern for the files concerned by this action.
              action_function: A callback without argument. See documentation.
  
          Warning:
              The order in which you add actions is important. A file will be dealt with the **first** compatible
              action found.