- Published on
Alpine.js x-for Template Problem and Solution
- Authors

- Name
- Kiet
When using Alpine.js and the x-for directive for looping, you might encounter an issue when trying to add dividers between elements. Typically, you'd use the divide-y class on the ul tag for this purpose. However, a problem arises where the first item also has a divider above it. Let's understand the issue and find a solution.
The Issue
Consider the following code:
<ul x-data="{ items: ['Item 1', 'Item 2', 'Item 3'] }" class="divide-y p-2">
<template x-for="item in items">
<p x-text="item"></p>
</template>
</ul>
Surprisingly, this results in an unexpected output. By inspecting the rendered HTML using devtools, we find that the template tag itself is rendered as an element:
<ul x-data="{ items: ['Item 1', 'Item 2', 'Item 3'] }" class="divide-y p-2">
<template x-for="item in items">
<p x-text="item"></p>
</template>
<p x-text="item">Item 1</p>
<p x-text="item">Item 2</p>
<p x-text="item">Item 3</p>
</ul>
This leads to an extra item in the list (the template tag itself), causing an unwanted divider above the first actual item.
The Solution
Fortunately, Tailwind CSS provides a simple fix for this issue. Although it's mentioned in version 2 documentation and not in the latest one, the solution remains relevant. You can add the hidden attribute to the template tag to resolve the problem:
<ul x-data="{ items: ['Item 1', 'Item 2', 'Item 3'] }" class="divide-y p-2">
<template x-for="item in items" hidden>
<p x-text="item"></p>
</template>
</ul>
By doing this, you effectively hide the template tag from rendering, and the problem is solved. Now, your list will correctly display only the intended items without an extra divider above the first item.
You can find the relevant information about resolving this issue in the link below. Tailwind CSS v2 Documentation - Adding hidden to Template Tags