HumanSignal/label-studio · error · ValidationError

All tasks are empty (None)

Error message

All tasks are empty (None)

What it means

Raised by TaskListSerializer.to_internal_value (the bulk task import serializer) when the entire submitted data payload is null. Since there are no tasks to validate at all, the serializer fails fast with 'All tasks are empty (None)' instead of iterating items.

Source

Thrown at label_studio/tasks/serializers.py:525

    @property
    def project(self):
        return self.context.get('project')

    @staticmethod
    def format_error(i, detail, item):
        if len(detail) == 1:
            code = f' {detail[0].code}' if detail[0].code != 'invalid' else ''
            return f'Error{code} at item {i}: {detail[0]} :: {item}'
        else:
            errors = ', '.join(detail)
            codes = [d.code for d in detail]
            return f'Errors {codes} at item {i}: {errors} :: {item}'

    def to_internal_value(self, data):
        """Body of run_validation for all data items"""
        if data is None:
            raise ValidationError('All tasks are empty (None)')

        if not isinstance(data, list):
            raise ValidationError({api_settings.NON_FIELD_ERRORS_KEY: 'not a list'}, code='not_a_list')

        if not self.allow_empty and len(data) == 0:
            if self.parent and self.partial:
                raise SkipField()
            raise ValidationError({api_settings.NON_FIELD_ERRORS_KEY: 'empty'}, code='empty')

        ret, errors = [], []
        self.annotation_count, self.prediction_count = 0, 0
        for i, item in enumerate(data):
            try:
                validated = self.child.validate(item)
            except ValidationError as exc:
                error = self.format_error(i, exc.detail, item)
                errors.append(error)
                # do not print to user too many errors

View on GitHub (pinned to 0b49e9b539)

Solutions

  1. Ensure the request body contains a non-null list of tasks, e.g. [{"data": {...}}, ...]
  2. Check your client code for undefined variables being JSON.stringify'd as null before sending
  3. Verify the upload file field name and that the file actually parsed (JSON/CSV) to a list
  4. If data may legitimately be empty, guard client-side before calling the API

Example fix

// before
await fetch(`/api/projects/${id}/import`, { method: 'POST', body: JSON.stringify({ tasks: tasksOrNull }) });
// after
if (!Array.isArray(tasks)) throw new Error('tasks must be a non-null list');
await fetch(`/api/projects/${id}/import`, { method: 'POST', body: JSON.stringify({ tasks }) });
Defensive patterns

Strategy: type-guard

Validate before calling

function assertTasksList(tasks) {
  if (tasks === null || tasks === undefined) throw new Error('tasks payload is null');
  if (!Array.isArray(tasks)) throw new Error('tasks must be an array');
  if (tasks.length === 0) console.warn('importing zero tasks');
}

Type guard

function isNonNullArray(v) {
  return Array.isArray(v) && v !== null;
}

Try / catch

try {
  await importTasks(projectId, tasks);
} catch (e) {
  if (e.response?.data?.non_field_errors?.[0] === 'All tasks are empty (None)') {
    console.error('Payload was null — check data extraction step');
  } else throw e;
}

Prevention

When it happens

Trigger: POSTing to /api/projects/<id>/import or /api/tasks/ with a JSON body whose tasks/data key is explicitly null, or a form/file upload that resolves to None (e.g., missing upload file field decoded to null).

Common situations: API clients sending {"tasks": null}; CSV/JSON file upload where the file field name is wrong so the parsed content is None; scripts that serialize an empty/undefined variable to null instead of an array; ETL jobs with upstream data loss.

Related errors


AI-assisted analysis of HumanSignal/label-studio@0b49e9b539 (2026-08-29). Data as JSON: /api/errors/24b7f7be1a7dc611. Report an issue: GitHub.