---
"@context": https://schema.org
"@type": TechArticle
"@id": https://www.twilio.com/docs/cohorts/cel/type-matching#article
headline: Type matching
description: Learn how Twilio Cohorts enforces data types in filter criteria, and how to reconcile mismatched types.
url: https://www.twilio.com/docs/cohorts/cel/type-matching
inLanguage: en
dateModified: 2026-09-15T09:58:28.000Z
author:
  "@type": Organization
  name: Twilio Developer Education Team
publisher:
  "@type": Organization
  name: Twilio
---

# Type matching

## Supported data types

Twilio Cohorts filter criteria accept the following primitive types:

| Type        | Description                           | Example                              |
| ----------- | ------------------------------------- | ------------------------------------ |
| `string`    | Text value                            | `"hello"`, `"US"`                    |
| `integer`   | Whole number (64-bit signed)          | `0`, `25`, `-1`                      |
| `float`     | Floating-point number (64-bit double) | `3.14`, `-0.5`                       |
| `boolean`   | Boolean value                         | `true`, `false`                      |
| `timestamp` | Date-time value                       | `timestamp("2026-01-01T00:00:00Z")`  |
| `duration`  | Time duration                         | `duration("24h")`, `duration("30m")` |

## Operands must match type

When you combine two values in filter criteria, both sides generally need to be the same type.

### Comparison operators

| Operator             | Allowed operand types                                                                                                                                                |
| -------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `==`, `!=`           | Any type, provided that both operands are the same type — except for `integer` and `float`, which are numerically coerced when compared.                             |
| `<`, `<=`, `>`, `>=` | integer, float, string, timestamp, or duration. Both operands must be the same type — except for `integer` and `float`, which are numerically coerced when compared. |

```txt
profile.trait.Account.age > 18
```

`age` and `18` are both numbers, so this comparison is valid. Comparing a string-typed trait to an integer literal, or a timestamp to a string, is invalid and causes an evaluation failure.

### Arithmetic operators

| Operator | Allowed operand types                                                                       |
| -------- | ------------------------------------------------------------------------------------------- |
| `+`      | integer + integer, float + float, string + string (concatenation), or timestamp + duration. |
| `-`      | integer - integer, float - float, timestamp - duration, or timestamp - timestamp.           |
| `*`, `/` | integer \* integer, float \* float, integer / integer, or float / float.                    |
| `%`      | integer % integer only.                                                                     |

Mixed types, such as a string plus an integer, are invalid.

### Membership (`in`)

The left-hand value's type must be compatible with the type of the elements in the list on the right.

```txt
profile.trait.Contact.country in ["US", "FR", "DE"]
```

Comparing a string-typed trait to a list of integers is invalid.

### Conditional (ternary)

Both branches of a `?:` expression must evaluate to compatible types.

```txt
profile.trait.Metrics.score > 0 ? profile.trait.Metrics.score : 0
```

Here, both branches resolve to a number. Returning a number from one branch and a string from the other is invalid.

## Type mismatches are rejected, not silently excluded

A type mismatch behaves differently from a [missing trait](/docs/cohorts/cel/null-handling). A missing trait evaluates to `false` and quietly excludes the profile. A type mismatch fails validation when you create or update a cohort or create a snapshot from inline criteria. In those cases, the request is rejected with an HTTP `400 Bad Request` error.

## Reconciling mismatched types

If you need to combine or compare values of different types, convert one of them explicitly by using a [type-conversion function](/docs/cohorts/cel/functions#type-conversion) such as `string()`, `int()`, or `double()`.

```txt
string(profile.trait.Account.age) == "18"
```

## Next steps

* Review the available [functions](/docs/cohorts/cel/functions), including type conversion.
* Learn about [null handling](/docs/cohorts/cel/null-handling) for missing traits.
