Serialize this workflow to JSON

def to_json(self, indent=None):
        """Serialize this workflow to JSON"""

        inputs = ParameterCollection(self.inputs)

        d = {
            'meta': {
                'name': self.name,
                'description': self.description
            },
            'inputs': [],
            'workflow': [],
            'outputs': [{'name': k, 'node': v} for k, v in six.iteritems(self.output_mapping)]
        }

        for parameter in self.inputs:
            input_info = {
                'name': parameter.name,
                'type': parameter.id
            }

            args, kwargs = parameter.serialize_args()
            args = list(args)
            args.pop(0)  # 'name' is already taken care of
            kwargs.pop('required', None)  # 'required' is assumed True for workflow inputs
            if args or kwargs:
                input_info['args'] = [args, kwargs]

            d['inputs'].append(input_info)

        for node in sorted(six.itervalues(self.nodes_by_id), key=lambda x: x.id):
            task_name = node.task.name
            if not task_name:
                raise ValueError('The task {0} does not have a name and therefore cannot be serialized.'.format(
                    node.task.__class__.__name__)
                )

            node_inputs = {}
            for input_name, (source, value) in six.iteritems(node.inputs):
                input_info = {'source': source}

                if source == 'input':
                    input_info['input'] = inputs.by_name[value].name
                else:
                    input_info['node'] = value

                node_inputs[input_name] = input_info

            d['workflow'].append({
                'id': node.id,
                'task': task_name,
                'inputs': node_inputs
            })

        return json.dumps(d, indent=indent)