# IHP v1.5 has been released

**URL:** <https://discourse.haskell.org/t/ihp-v1-5-has-been-released/13846>\
**Category:** Announcements\
**Created:** [March 25, 2026, 11:26am UTC](https://discourse.haskell.org/t/ihp-v1-5-has-been-released/13846 "2026-03-25T11:26:50Z")\
**Posts on this page:** 2\
**Page:** 1

<div class="post-metadata">

**Author:** ![mpscholten](https://sea2.discourse-cdn.com/flex002/user_avatar/discourse.haskell.org/mpscholten/32/1441_2.png) [@mpscholten](https://discourse.haskell.org/u/mpscholten)\
**Post date:** [March 25, 2026, 11:26am UTC](https://discourse.haskell.org/t/ihp-v1-5-has-been-released/13846/1 "2026-03-25T11:26:50Z")

</div>

We just released IHP v1.5, the largest release in IHP’s history. With 1,051 commits, it includes a complete database layer rewrite, major performance improvements, a new typed SQL package, and 15+ modules extracted into standalone Hackage packages.

Here are the highlights:

## Hasql Database Migration

The entire database access layer has been rewritten from `postgresql-simple` to `hasql`, delivering up to 2x lower query latency in production. Hasql uses prepared statements and binary protocol encoding. The  
query builder API is unchanged — existing code like `query @User |> filterWhere (#active, True) |> fetch` works exactly as before.

## Typed SQL (`ihp-typed-sql`)

A new `typedSql` quasiquoter connects to your dev database at compile time to infer column types, detect nullable columns from LEFT JOINs, and validate parameters:

```haskell
users <- [typedSql|
    SELECT users.name, orders.total
    FROM users
    LEFT JOIN orders ON orders.user_id = users.id
|] -- inferred: TypedQuery (Text, Maybe Double)

```

## Pipeline Queries

`fetchPipelined` batches multiple independent queries into a single PostgreSQL round-trip:

```haskell
(allItems, activeItems, count) <- pipeline do
    allItems <- query @Item |> fetchPipelined
    activeItems <- query @Item |> filterWhere (#active, True) |> fetchPipelined
    count <- query @Item |> fetchCountPipelined
    pure (allItems, activeItems, count)

```

## Performance

Lots of performance work across the stack: 3x faster session middleware (published as standalone Hackage packages [wai-session-maybe](https://hackage.haskell.org/package/wai-session-maybe) and [wai-session-clientsession-deferred](https://hackage.haskell.org/package/wai-session-clientsession-deferred-1.0.0)), 5x faster URL generation, 2x faster render pipeline, and GHCi dev server memory reduced from 4GB to 500MB.

Other highlights: composite primary key support, customRoutes/customPathTo for clean URLs alongside AutoRoute, GHC 9.10 (with experimental 9.12 support), and 15+ modules extracted into standalone Hackage packages.

Full release notes and changelog: [IHP v1.5.0 on GitHub](https://github.com/digitallyinduced/ihp/releases/tag/v1.5.0)  
Upgrade guide: [UPGRADE.md](https://github.com/digitallyinduced/ihp/blob/master/UPGRADE.md)

---

<div class="post-metadata">

**Author:** ![unhammer](https://sea2.discourse-cdn.com/flex002/user_avatar/discourse.haskell.org/unhammer/32/580_2.png) [@unhammer](https://discourse.haskell.org/u/unhammer)\
**Post date:** [March 25, 2026, 12:47pm UTC](https://discourse.haskell.org/t/ihp-v1-5-has-been-released/13846/2 "2026-03-25T12:47:56Z")

</div>

So many nice changes! Looking forward to typing my plain sql’s 😃 I’ve missed having type-checking for the cases where the ihp “builtin” `innerJoin` etc. didn’t cut it, so that’s a very welcome change.
