> ## Documentation Index
> Fetch the complete documentation index at: https://mintlify.com/cvat-ai/cvat/llms.txt
> Use this file to discover all available pages before exploring further.

# Labels & Attributes

> Configure annotation labels, attributes, hierarchies, and import/export label schemas

Labels define the object classes you want to annotate, while attributes capture additional properties of those objects. A well-designed label schema is crucial for high-quality annotations.

## Understanding Labels

A label represents an annotation class in CVAT. Each label has:

* **Name**: Unique identifier for the object class
* **Color**: Visual color for annotations (auto-generated if not specified)
* **Type**: Shape type constraint (optional)
* **Attributes**: Additional properties for labeled objects
* **Sublabels**: Nested labels for hierarchical classification

### Label Types

Labels can be constrained to specific annotation shapes:

| Type        | Description              | Use Case                   |
| ----------- | ------------------------ | -------------------------- |
| `any`       | Any shape type (default) | General purpose            |
| `rectangle` | Bounding boxes only      | Object detection           |
| `polygon`   | Polygons only            | Precise segmentation       |
| `polyline`  | Lines only               | Lane detection, boundaries |
| `points`    | Point annotations        | Keypoints, landmarks       |
| `ellipse`   | Ellipses only            | Circular objects           |
| `cuboid`    | 3D cuboids               | 3D object detection        |
| `mask`      | Pixel masks              | Semantic segmentation      |
| `skeleton`  | Skeleton structures      | Pose estimation            |
| `tag`       | Frame-level tags         | Image classification       |

## Creating Labels

### In Projects

Labels defined at the project level are shared across all tasks:

**Using the API:**

```bash theme={null}
curl -X POST "https://app.cvat.ai/api/projects" \
  -H "Authorization: Token <your-token>" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "Autonomous Driving",
    "labels": [
      {
        "name": "car",
        "color": "#ff0000",
        "type": "rectangle"
      },
      {
        "name": "pedestrian",
        "color": "#00ff00",
        "type": "rectangle"
      },
      {
        "name": "road",
        "color": "#0000ff",
        "type": "polygon"
      }
    ]
  }'
```

**Using the SDK:**

```python theme={null}
from cvat_sdk import Client, models

client = Client(url="https://app.cvat.ai")
client.login(("username", "password"))

labels = [
    models.PatchedLabelRequest(
        name="vehicle",
        color="#ff0000",
        type="rectangle"
    ),
    models.PatchedLabelRequest(
        name="lane_marking",
        color="#ffff00",
        type="polyline"
    )
]

project = client.projects.create(
    spec=models.ProjectWriteRequest(
        name="Road Scene Annotation",
        labels=labels
    )
)
```

### In Standalone Tasks

Tasks without a project can have their own labels:

```python theme={null}
task = client.tasks.create(
    spec=models.TaskWriteRequest(
        name="Custom Task",
        labels=[
            models.PatchedLabelRequest(
                name="defect",
                color="#ff0000"
            )
        ]
    )
)
```

### Using the CLI

```bash theme={null}
# Create project with labels from JSON file
cvat-cli --auth user:password project create \
  --labels labels.json \
  "My Project"

# Inline label definition
cvat-cli --auth user:password task create \
  --labels '[
    {"name": "person", "type": "rectangle"},
    {"name": "bike", "type": "rectangle"}
  ]' \
  "Detection Task"
```

## Label Attributes

Attributes capture additional properties of annotated objects.

### Attribute Types

| Type       | Description                   | Example                       |
| ---------- | ----------------------------- | ----------------------------- |
| `checkbox` | Boolean value                 | Occluded: true/false          |
| `radio`    | Single selection (deprecated) | Use `select` instead          |
| `select`   | Dropdown selection            | Vehicle type: sedan/suv/truck |
| `number`   | Numeric value                 | Confidence: 0-100             |
| `text`     | Free-form text                | License plate: ABC123         |

### Mutable vs Immutable

* **Immutable attributes**: Set once per object (e.g., vehicle type)
* **Mutable attributes**: Can change per frame in tracks (e.g., occlusion state)

### Defining Attributes

```python theme={null}
label_with_attributes = models.PatchedLabelRequest(
    name="car",
    color="#ff0000",
    type="rectangle",
    attributes=[
        # Checkbox attribute
        models.AttributeRequest(
            name="occluded",
            input_type="checkbox",
            mutable=True,  # Can change per frame
            default_value="false",
            values=["false"]  # Checkbox values
        ),
        # Select attribute
        models.AttributeRequest(
            name="vehicle_type",
            input_type="select",
            mutable=False,  # Set once per object
            default_value="sedan",
            values=["sedan", "suv", "truck", "van"]
        ),
        # Number attribute
        models.AttributeRequest(
            name="confidence",
            input_type="number",
            mutable=False,
            default_value="100",
            values=["0", "100", "1"]  # min, max, step
        ),
        # Text attribute
        models.AttributeRequest(
            name="license_plate",
            input_type="text",
            mutable=False,
            default_value="",
            values=[]  # No predefined values
        )
    ]
)
```

**API format:**

```json theme={null}
{
  "name": "car",
  "color": "#ff0000",
  "attributes": [
    {
      "name": "color",
      "input_type": "select",
      "mutable": false,
      "default_value": "unknown",
      "values": ["red", "blue", "white", "black", "unknown"]
    },
    {
      "name": "damaged",
      "input_type": "checkbox",
      "mutable": false,
      "default_value": "false",
      "values": ["false"]
    }
  ]
}
```

## Label Hierarchies (Sublabels)

Create nested label structures for complex classification:

```python theme={null}
vehicle_label = models.PatchedLabelRequest(
    name="vehicle",
    color="#ff0000",
    type="rectangle",
    sublabels=[
        models.PatchedLabelRequest(
            name="car",
            color="#ff3333",
            type="rectangle"
        ),
        models.PatchedLabelRequest(
            name="truck",
            color="#ff6666",
            type="rectangle"
        ),
        models.PatchedLabelRequest(
            name="motorcycle",
            color="#ff9999",
            type="rectangle"
        )
    ]
)
```

**API format:**

```json theme={null}
{
  "name": "animal",
  "color": "#00ff00",
  "sublabels": [
    {"name": "dog", "color": "#00ff33"},
    {"name": "cat", "color": "#00ff66"},
    {"name": "bird", "color": "#00ff99"}
  ]
}
```

<Note>
  Sublabels inherit the parent label's type if not specified. They can have their own attributes.
</Note>

## Skeleton Labels

For pose estimation and keypoint detection:

```python theme={null}
person_skeleton = models.PatchedLabelRequest(
    name="person",
    type="skeleton",
    svg="""<line x1='0' y1='0' x2='10' y2='10' />...""",
    sublabels=[
        models.PatchedLabelRequest(name="head"),
        models.PatchedLabelRequest(name="left_shoulder"),
        models.PatchedLabelRequest(name="right_shoulder"),
        models.PatchedLabelRequest(name="left_elbow"),
        # ... more keypoints
    ]
)
```

The `svg` field defines connections between keypoints.

## Updating Labels

### Update Project Labels

```python theme={null}
project = client.projects.retrieve(project_id=1)

# Add new label
project.update(models.PatchedProjectWriteRequest(
    labels=[
        # Existing label (must include ID)
        models.PatchedLabelRequest(
            id=10,
            name="existing_label"
        ),
        # New label (no ID)
        models.PatchedLabelRequest(
            name="new_label",
            color="#ff00ff"
        )
    ]
))

# Update existing label
project.update(models.PatchedProjectWriteRequest(
    labels=[
        models.PatchedLabelRequest(
            id=10,
            name="updated_name",
            color="#00ff00"
        )
    ]
))
```

**Using the API:**

```bash theme={null}
curl -X PATCH "https://app.cvat.ai/api/projects/1" \
  -H "Authorization: Token <your-token>" \
  -H "Content-Type: application/json" \
  -d '{
    "labels": [
      {"id": 10, "name": "updated_car"},
      {"name": "new_label", "color": "#ff00ff"}
    ]
  }'
```

### Delete Labels

To delete a label, mark it with `deleted: true`:

```bash theme={null}
curl -X PATCH "https://app.cvat.ai/api/projects/1" \
  -H "Authorization: Token <your-token>" \
  -H "Content-Type: application/json" \
  -d '{
    "labels": [
      {"id": 10, "deleted": true}
    ]
  }'
```

<Warning>
  Deleting a label removes all associated annotations. This action cannot be undone.
</Warning>

## Retrieving Labels

### Get Project Labels

```python theme={null}
# Using project
project = client.projects.retrieve(project_id=1)
labels = project.get_labels()

for label in labels:
    print(f"Label: {label.name}")
    print(f"  Color: {label.color}")
    print(f"  Type: {label.type}")
    
    # Print attributes
    for attr in label.attributespec_set:
        print(f"  Attribute: {attr.name} ({attr.input_type})")
        if attr.values:
            print(f"    Values: {attr.values}")
```

### Get Task Labels

```python theme={null}
task = client.tasks.retrieve(task_id=10)
labels = task.get_labels()

# Tasks in projects inherit project labels
if task.project_id:
    print("Labels inherited from project")
else:
    print("Task-specific labels")
```

### Query Labels via API

```bash theme={null}
# Get all labels for a project
curl "https://app.cvat.ai/api/labels?project_id=1" \
  -H "Authorization: Token <your-token>"

# Get all labels for a task
curl "https://app.cvat.ai/api/labels?task_id=10" \
  -H "Authorization: Token <your-token>"
```

## Importing Label Schemas

### From JSON File

**labels.json:**

```json theme={null}
[
  {
    "name": "person",
    "color": "#ff0000",
    "type": "rectangle",
    "attributes": [
      {
        "name": "age_group",
        "input_type": "select",
        "mutable": false,
        "default_value": "adult",
        "values": ["child", "adult", "senior"]
      }
    ]
  },
  {
    "name": "vehicle",
    "color": "#00ff00",
    "type": "polygon"
  }
]
```

**Using CLI:**

```bash theme={null}
cvat-cli --auth user:password project create \
  --labels labels.json \
  "Project from JSON"
```

**Using SDK:**

```python theme={null}
import json

with open("labels.json") as f:
    labels_data = json.load(f)

labels = [models.PatchedLabelRequest(**label) for label in labels_data]

project = client.projects.create(
    spec=models.ProjectWriteRequest(
        name="Imported Labels Project",
        labels=labels
    )
)
```

### From Existing Project

```python theme={null}
# Copy labels from one project to another
source_project = client.projects.retrieve(project_id=1)
source_labels = source_project.get_labels()

# Convert to creation format (remove IDs)
new_labels = [
    models.PatchedLabelRequest(
        name=label.name,
        color=label.color,
        type=label.type,
        attributes=[
            models.AttributeRequest(
                name=attr.name,
                input_type=attr.input_type,
                mutable=attr.mutable,
                default_value=attr.default_value,
                values=attr.values.split("\n") if attr.values else []
            )
            for attr in label.attributespec_set
        ]
    )
    for label in source_labels
]

target_project = client.projects.create(
    spec=models.ProjectWriteRequest(
        name="Cloned Label Schema",
        labels=new_labels
    )
)
```

## Exporting Label Schemas

```python theme={null}
import json

project = client.projects.retrieve(project_id=1)
labels = project.get_labels()

# Convert to JSON-serializable format
labels_export = []
for label in labels:
    label_data = {
        "name": label.name,
        "color": label.color,
        "type": label.type,
        "attributes": [
            {
                "name": attr.name,
                "input_type": attr.input_type,
                "mutable": attr.mutable,
                "default_value": attr.default_value,
                "values": attr.values.split("\n") if attr.values else []
            }
            for attr in label.attributespec_set
        ]
    }
    labels_export.append(label_data)

# Save to file
with open("exported_labels.json", "w") as f:
    json.dump(labels_export, f, indent=2)

print("Labels exported to exported_labels.json")
```

## Best Practices

<AccordionGroup>
  <Accordion title="Design labels for your use case">
    * Use clear, descriptive names: "pedestrian" not "ped"
    * Avoid ambiguous class boundaries
    * Consider annotation difficulty when splitting classes
    * Balance between specificity and annotator burden
  </Accordion>

  <Accordion title="Use appropriate label types">
    * `rectangle`: Fast annotation for bounding boxes
    * `polygon`: Precise segmentation when needed
    * `polyline`: Lane markings, boundaries
    * `skeleton`: Human pose, articulated objects
    * `tag`: Image-level classification
  </Accordion>

  <Accordion title="Configure attributes thoughtfully">
    * Use `select` for categorical properties
    * Set `mutable=true` for properties that change over time
    * Provide `default_value` to speed annotation
    * Limit attribute count to avoid annotator fatigue
  </Accordion>

  <Accordion title="Maintain color consistency">
    * Use distinct colors for different classes
    * Maintain color scheme across projects
    * Consider colorblind-friendly palettes
    * Let CVAT auto-generate colors if unsure
  </Accordion>

  <Accordion title="Plan for schema evolution">
    * Start with core classes, add as needed
    * Export label schemas for reuse
    * Document label definitions clearly
    * Communicate changes to annotation team
  </Accordion>
</AccordionGroup>

## Example Label Schemas

### Object Detection (COCO-style)

```json theme={null}
[
  {"name": "person", "type": "rectangle"},
  {"name": "bicycle", "type": "rectangle"},
  {"name": "car", "type": "rectangle"},
  {"name": "motorcycle", "type": "rectangle"},
  {"name": "bus", "type": "rectangle"},
  {"name": "truck", "type": "rectangle"}
]
```

### Semantic Segmentation

```json theme={null}
[
  {"name": "road", "type": "polygon", "color": "#804080"},
  {"name": "sidewalk", "type": "polygon", "color": "#f423e8"},
  {"name": "building", "type": "polygon", "color": "#464646"},
  {"name": "vegetation", "type": "polygon", "color": "#6b8e23"},
  {"name": "sky", "type": "polygon", "color": "#87ceeb"}
]
```

### Document Classification

```json theme={null}
[
  {
    "name": "document",
    "type": "tag",
    "attributes": [
      {
        "name": "document_type",
        "input_type": "select",
        "values": ["invoice", "receipt", "contract", "form"],
        "default_value": "invoice"
      },
      {
        "name": "language",
        "input_type": "select",
        "values": ["en", "es", "fr", "de"],
        "default_value": "en"
      }
    ]
  }
]
```

## Next Steps

<CardGroup cols={2}>
  <Card title="Quality Control" icon="shield-check" href="/projects/quality-control">
    Set up validation and quality metrics
  </Card>

  <Card title="Managing Tasks" icon="tasks" href="/projects/managing-tasks">
    Create tasks and upload data
  </Card>

  <Card title="Annotation Tools" icon="pen" href="/annotation/editor-overview">
    Learn annotation tools and shortcuts
  </Card>

  <Card title="API Reference" icon="code" href="/api/projects">
    Complete labels API documentation
  </Card>
</CardGroup>
