---
title: MULTIPLE_EXPRESSIONS_FOR_ALIAS ClickHouse error
meta:
  description: Learn how to fix the MULTIPLE_EXPRESSIONS_FOR_ALIAS error in ClickHouse and Tinybird. Understand what causes it and see examples of how to resolve it
---

# MULTIPLE_EXPRESSIONS_FOR_ALIAS ClickHouse error

{% callout %}
This error usually means you have multiple expressions with the same alias name in your SELECT clause. Each alias must be unique within a query.
{% /callout %}

The `MULTIPLE_EXPRESSIONS_FOR_ALIAS` error in ClickHouse (and Tinybird) happens when you try to use the same alias name for multiple expressions in a SELECT clause. Each column alias must be unique within a query to avoid ambiguity.

## What causes this error

You'll typically see it when:

* Using the same alias for multiple columns in SELECT
* Having duplicate alias names in subqueries
* Using the same alias in UNION queries
* Having conflicting aliases in JOIN queries
* Using reserved words as aliases
* Collisions between columns and functions (e.g., `col AS value` and `count(*) AS value`)

## Example errors

```sql {% title="Fails: duplicate alias names" %}
SELECT user_id as id, event_id as id FROM events
```

```sql {% title="Fails: same alias in UNION" %}
SELECT user_id as id FROM events
UNION ALL
SELECT user_id as id FROM events
```

```sql {% title="Fails: conflicting aliases in JOIN" %}
SELECT u.id as id, e.event_type as id FROM users u JOIN events e ON u.id = e.user_id
```

```sql {% title="Fails: subquery with duplicate aliases" %}
SELECT * FROM (
    SELECT user_id as id, event_id as id FROM events
) t
```

## How to fix it

### Use unique alias names

Give each column a unique alias:

```sql {% title="Fix: unique aliases" %}
SELECT user_id as user_id, event_id as event_id FROM events
```

### Use descriptive aliases

Make aliases more descriptive to avoid conflicts:

```sql {% title="Fix: descriptive aliases" %}
SELECT user_id as user_identifier, event_id as event_identifier FROM events
```

### Use table prefixes

Prefix aliases with table names:

```sql {% title="Fix: table prefixes" %}
SELECT u.id as user_id, e.id as event_id
FROM users u JOIN events e ON u.id = e.user_id
```

### Remove unnecessary aliases

If aliases aren't needed, remove them:

```sql {% title="Fix: remove unnecessary aliases" %}
SELECT user_id, event_id FROM events
```

## Common patterns and solutions

### Simple column selection

When selecting columns with aliases:

```sql {% title="Correct: unique aliases" %}
SELECT
    user_id as user_identifier,
    event_type as event_category,
    timestamp as event_time
FROM events
```

### Aggregated columns

When using aggregate functions:

```sql {% title="Correct: unique aggregate aliases" %}
SELECT
    user_id,
    COUNT(*) as event_count,
    SUM(value) as total_value,
    AVG(value) as average_value
FROM events
GROUP BY user_id
```

### JOIN queries

When joining tables with similar column names:

```sql {% title="Correct: table-specific aliases" %}
SELECT
    u.id as user_id,
    u.name as user_name,
    e.id as event_id,
    e.event_type as event_category
FROM users u
JOIN events e ON u.id = e.user_id
```

### UNION queries

When combining results from multiple queries:

```sql {% title="Correct: unique aliases in UNION" %}
SELECT user_id as user_identifier, 'user' as source FROM users
UNION ALL
SELECT event_id as user_identifier, 'event' as source FROM events
```

{% callout type="caution" %}
In UNION ALL, column names are taken from the first SELECT. Subsequent SELECTs should use implicit column order, not repeated aliases.
{% /callout %}

## Advanced solutions

### Using CTEs with aliases

When using Common Table Expressions:

```sql {% title="CTEs with unique aliases" %}
WITH user_stats AS (
    SELECT
        user_id as user_identifier,
        COUNT(*) as event_count
    FROM events
    GROUP BY user_id
),
event_stats AS (
    SELECT
        event_type as event_category,
        COUNT(*) as type_count
    FROM events
    GROUP BY event_type
)
SELECT
    us.user_identifier,
    us.event_count,
    es.event_category,
    es.type_count
FROM user_stats us
CROSS JOIN event_stats es
```

### Subqueries with aliases

When using subqueries:

```sql {% title="Subqueries with unique aliases" %}
SELECT
    u.id as user_id,
    u.name as user_name,
    (SELECT COUNT(*) FROM events e WHERE e.user_id = u.id) as user_event_count
FROM users u
```

### Window functions with aliases

When using window functions:

```sql {% title="Window functions with unique aliases" %}
SELECT
    user_id,
    event_type,
    timestamp,
    ROW_NUMBER() OVER (PARTITION BY user_id ORDER BY timestamp) as user_event_rank,
    ROW_NUMBER() OVER (ORDER BY timestamp) as global_event_rank
FROM events
```

## Best practices

### Naming conventions

* Use descriptive, unique alias names
* Avoid generic names like `id`, `name`, `value`
* Use table prefixes when joining multiple tables
* Be consistent with naming patterns

### Query structure

* Plan your aliases before writing complex queries
* Use meaningful names that describe the data
* Avoid reserved words as aliases
* Test queries with simple aliases first

### Documentation

* Document your alias naming conventions
* Use consistent patterns across your codebase
* Comment complex queries with alias explanations
* Maintain a glossary of common aliases

## Tinybird-specific notes

In Tinybird, this error often occurs when:

* Building Pipes with conflicting column names
* Using Materialized Views with duplicate aliases
* Working with nested Pipes that have similar schemas
* Creating API endpoints with conflicting response fields

To debug in Tinybird:

1. Check your Pipe node outputs for duplicate column names
2. Verify Materialized View schemas for conflicts
3. Use descriptive column names in your Pipes
4. Test Pipe outputs with simple queries first

## See also

* [SQL Reference](/sql-reference) - SQL reference documentation
* [Working with Pipes](/forward/work-with-data/pipes)
