rent
PostgreSQL extensions

citext

What it is

citext is a PostgreSQL-supplied, case-insensitive text type. Comparisons behave as though both values were lowered, while the originally entered capitalization remains available for display.

What it provides

  • Case-insensitive equality, uniqueness, ordering, and pattern matching
  • Index and primary-key behavior that follows case-insensitive comparisons
  • A text-like type that removes repeated lower(...) expressions from queries

Use it for email addresses, usernames, identifiers, tags, or other values where Ada and ada should compare as the same value.

Use it with Rent

extension citext {
  name = "citext"
}

model User {
  id    BigInt        @id
  email citext.CiText @unique
}

Add rent-ext-citext to your dependencies and enable Rent's postgres and extensions features. Run rent generate and rent migrate dev --name add_case_insensitive_email to generate and migrate the field.

let user = client
    .user()
    .email_eq("Ada@Example.com")?
    .only_or_none()
    .await?;

Create and update setters accept strings directly: .email("Ada@Example.com"). Reads return CiText, whose .as_str() preserves the original spelling. Generated SQL comparisons and uniqueness use PostgreSQL's case-insensitive behavior; comparing two CiText values in Rust uses their exact spelling. Case rules follow the database's locale, so choose and test the database collation for your application's languages.

Run the application

cargo run -p rent --example extension_09_citext

Set DATABASE_URL to a disposable PostgreSQL server with vector, PostGIS, and citext available. The example creates and removes its own database, requiring database-creation and extension-installation privileges. It verifies case-insensitive account lookup, rejects a differently capitalized duplicate email, and rolls back a second account. The schema and workflow are in crates/rent/examples/native_extension_fields/. The extension matrix runs the same workflow under nextest.

On this page