ecluse:ecluse-core
Safe HaskellNone
LanguageGHC2021

Ecluse.Core.Text

Description

Small pure text helpers shared across the codebase, so the blank-value, URL-path-join, and last-path-segment idioms have a single definition rather than several near-identical re-spellings -- plus the hot-path ISO-8601 instant renderer the serve path uses (renderIso8601Utc). This module depends on nothing else in Ecluse, so any module may import it without risking an import cycle.

Synopsis

Documentation

nonBlank :: Text -> Maybe Text Source #

The text trimmed of surrounding whitespace, or Nothing when nothing remains. A value that is empty or all-whitespace is treated as absent -- the idiom an environment lookup or an optional configuration field wants for "present but blank means unset". The surviving text is returned trimmed, so a caller never has to strip it a second time.

stripTrailingSlash :: Text -> Text Source #

Drop a single trailing '/' from a URL base when present, leaving any other base untouched. At most one slash is removed, and the function is idempotent on a base that already carries none.

joinUrlPath :: Text -> Text -> Text Source #

Join a URL base and an already-encoded path with exactly one '/', tolerating one trailing slash on the base so the join never doubles it. The path is appended verbatim -- this neither encodes nor validates it.

lastPathSegment :: Text -> Maybe Text Source #

The last path segment of a slash-separated string: the text after the final '/', or the whole string when it carries none. Nothing when that segment is empty (the string ends in a slash), so a caller supplies its own fallback rather than forming a segmentless path. This neither decodes nor validates the segment.

renderIso8601Utc :: UTCTime -> Text Source #

Render a UTCTime as the ISO-8601 instant iso8601Show produces, byte-for-byte, at a fraction of the allocation cost: a handful of digit writes into a builder instead of the general time formatting machinery. The packument serve path re-renders one instant per surviving version per request (the served time map is rebuilt from the merge plan's normalised instants), so the formatter sits on a hot loop where the general machinery's cost is paid thousands of times per request.

The fast path covers the whole real-world domain: years 0-9999 and a time-of-day below 86 400 s. An input outside it (an expanded-representation year, a leap-second reading) delegates to iso8601Show itself, so parity is total by construction and property-tested byte-for-byte in TextSpec. The fractional second renders exactly as iso8601Show does: omitted when zero, else the picosecond digits with trailing zeros trimmed.

displayExceptionT :: Exception e => e -> Text Source #

Render an exception as Text for a log line or error value. relude's displayException is over String; this is the Text form the log and error sites want, defined once rather than re-spelled at each call site.