partiql-value

    The PartiQL data model for MoonBit, with a PartiQL-encoded Ion codec.

    partiql
    sql
    query
    ion
    data-model
    Download zip
    Author
    Version
    0.1.0
    License
    Apache-2.0
    Last updated
    5 hours ago
    Downloads
    1

    Dependencies

    #moonrockz/partiql-value

    The PartiQL data model for MoonBit, with the PartiQL-encoded Ion codec that the partiql-tests suite uses.

    #Packages

    PackageAliasContent
    moonrockz/partiql-value@valueValue, Tuple, Bag, MapValue (RFC 0104), GraphValue (RFC 0025), Date, Time, Timestamp, IntervalYM, IntervalDT, and the relations ==, sql_equals, eqg, compare
    moonrockz/partiql-value/ion@partiql_ionfrom_ion, to_ion (PartiQL-encoded Ion, as in partiql-tests); from_ion_data, to_ion_data (Ion-preserving: Ion data passes through exactly)
    moonrockz/partiql-value/arbitrary@arbitraryquickcheck generators for property-based tests

    #Example

    let bag = @value.Value::Bag(@value.Bag::new([@value.Value::Int(1L), @value.Value::Int(2L)]))
    let same = @value.Value::Bag(@value.Bag::new([@value.Value::Int(2L), @value.Value::Int(1L)]))
    @value.sql_equals(bag, same) // Bool(true): bags compare as multisets

    // A tuple never holds MISSING: the constructor drops the pair.
    let t = @value.Tuple::new([("a", @value.Value::Missing), ("b", @value.Value::Null)])
    t.length() // 1

    // Boxed Ion values compare by their lowered value: an Ion symbol equals a string.
    let symbol = @value.Value::Ion(@ion_core.IonValue::symbol("hello"))
    @value.sql_equals(symbol, @value.Value::String("hello")) // Bool(true)

    // PartiQL-encoded Ion.
    @partiql_ion.to_ion(bag) // $bag::[1, 2]

    #Relations

    RelationUse
    == (Eq)Structural identity: same case and contents; bags and tuples as multisets; decimal scale counts
    sql_equalsThe PartiQL = operator: MISSING beats NULL; numbers compare by value across types
    eqgGrouping equivalence: NULL eqg NULL, MISSING eqg MISSING, NaN eqg NaN
    compareThe ORDER BY total order, with NullsFirst or NullsLast

    See docs/architecture.md and ADR 0005 in the repository.

    DateTimeError

    pub(all) suberror DateTimeError {
    InvalidDate(String)
    InvalidTime(String)
    } derive(Eq,
    Debug
    )

    A date, time or timestamp field that is out of range.

    GraphError

    pub(all) suberror GraphError {
    DuplicateNodeId(String)
    DuplicateEdgeId(String)
    UnknownNode(String)
    MissingPayload(String)
    } derive(Eq,
    Debug
    )

    Why a graph could not be built.

    IntervalError

    pub(all) suberror IntervalError {
    Overflow(String)
    } derive(Eq,
    Debug
    )

    An interval that does not fit the representation.

    LowerError

    pub(all) suberror LowerError {
    SymbolWithoutText
    } derive(Eq,
    Debug
    )

    An Ion value that has no PartiQL equivalent.

    MapError

    pub(all) suberror MapError {
    InvalidKey(String)
    DuplicateKey(String)
    DynamicKeyType
    } derive(Eq,
    Debug
    )

    Why a MAP could not be built.

    Bag

    pub struct Bag {
    // private fields
    } derive(
    Debug
    )

    A PartiQL bag: an unordered collection that allows duplicates.
    impl Eq for Bag

    Bag::items

    fn Bag::items(self : Bag) -> ArrayView[Value]

    Bag::length

    fn Bag::length(self : Bag) -> Int

    Bag::new

    fn Bag::new(items : Array[Value]) -> Bag

    Date

    pub struct Date {
    year : Int
    month : Int
    day : Int
    } derive(
    Debug
    )

    A calendar date (proleptic Gregorian).
    impl Eq for Date

    Date::new

    fn Date::new(year~ : Int, month~ : Int, day~ : Int) -> Date raise DateTimeError

    Ends

    pub(all) enum Ends {
    Directed(from~ : String, to~ : String)
    Undirected(String, String)
    } derive(
    Debug
    )

    The ends of a graph edge (RFC 0025): an ordered pair for a directed edge, an unordered pair for an undirected edge. Ends name node ids.
    impl Eq for Ends

    GraphEdge

    pub struct GraphEdge {
    id : String
    ends : Ends
    payload : Value?
    // private fields
    } derive(
    Debug
    )

    A graph edge: id, labels, ends and an optional payload.

    GraphEdge::labels

    fn GraphEdge::labels(self : GraphEdge) -> ArrayView[String]

    The labels, without duplicates, in first-seen order.

    GraphEdge::new

    fn GraphEdge::new(id~ : String, ends~ : Ends, labels? : Array[String], payload? : Value?) -> GraphEdge

    GraphNode

    pub struct GraphNode {
    id : String
    payload : Value?
    // private fields
    } derive(
    Debug
    )

    A graph node: its id from the source data, its labels (a set, kept in first-seen order) and an optional payload. An absent payload is not NULL: it acts as MISSING in queries.

    GraphNode::labels

    fn GraphNode::labels(self : GraphNode) -> ArrayView[String]

    The labels, without duplicates, in first-seen order.

    GraphNode::new

    fn GraphNode::new(id~ : String, labels? : Array[String], payload? : Value?) -> GraphNode

    GraphValue

    pub struct GraphValue {
    // private fields
    } derive(
    Debug
    )

    A PartiQL graph (RFC 0025). Node ids are unique among nodes, edge ids among edges (two namespaces), and every edge end names a node.
    impl Eq for GraphValue

    GraphValue::edges

    GraphValue::new

    fn GraphValue::new(nodes : Array[GraphNode], edges : Array[GraphEdge]) -> GraphValue raise GraphError

    GraphValue::nodes

    IntervalDT

    pub struct IntervalDT {
    seconds : Int64
    nanos : Int
    } derive(
    Debug
    )

    A day-time interval: seconds + nanos / 10^9, with nanos in 0..999,999,999 (floor form).
    impl Eq for IntervalDT

    IntervalDT::days

    fn IntervalDT::days(self : IntervalDT) -> Int64

    IntervalDT::from_parts

    fn IntervalDT::from_parts(negative~ : Bool, days~ : Int64, hours~ : Int64, minutes~ : Int64, seconds~ : Int64, nanos~ : Int64) -> IntervalDT raise IntervalError

    IntervalDT::hours

    fn IntervalDT::hours(self : IntervalDT) -> Int64

    IntervalDT::is_negative

    fn IntervalDT::is_negative(self : IntervalDT) -> Bool

    IntervalDT::minutes

    fn IntervalDT::minutes(self : IntervalDT) -> Int64

    IntervalDT::nanos_part

    fn IntervalDT::nanos_part(self : IntervalDT) -> Int64

    IntervalDT::new

    fn IntervalDT::new(seconds : Int64, nanos : Int64) -> IntervalDT raise IntervalError

    IntervalDT::seconds_part

    fn IntervalDT::seconds_part(self : IntervalDT) -> Int64

    IntervalYM

    pub struct IntervalYM {
    months : Int64
    } derive(
    Debug
    )

    A year-month interval, as a signed number of months.
    impl Eq for IntervalYM

    IntervalYM::from_parts

    fn IntervalYM::from_parts(negative~ : Bool, years~ : Int64, months~ : Int64) -> IntervalYM raise IntervalError

    IntervalYM::is_negative

    fn IntervalYM::is_negative(self : IntervalYM) -> Bool

    IntervalYM::months_part

    fn IntervalYM::months_part(self : IntervalYM) -> Int64

    IntervalYM::new

    fn IntervalYM::new(months : Int64) -> IntervalYM raise IntervalError

    IntervalYM::years

    fn IntervalYM::years(self : IntervalYM) -> Int64

    MapType

    pub(all) enum MapType {
    Dynamic
    Bool
    TinyInt
    SmallInt
    Integer
    BigInt
    Numeric
    Decimal
    Real
    Double
    String
    Char
    Varchar
    Date
    Time
    Timestamp
    } derive(Eq,
    Debug
    )

    The declared key or value type of a MAP (RFC 0104). The names are the static type names of partiql-tests' $map::<key>::<value>:: encoding.

    MapType::from_name

    fn MapType::from_name(name : String) -> MapType?

    The type for a name; int is accepted for integer.

    MapType::name

    fn MapType::name(self : MapType) -> String

    The type name as partiql-tests writes it.

    MapValue

    pub struct MapValue {
    key_type : MapType
    value_type : MapType
    // private fields
    } derive(
    Debug
    )

    A PartiQL MAP: unique scalar keys, no MISSING values. The stored order is the insertion order (for output); equality and ordering ignore it.
    impl Eq for MapValue

    MapValue::entries

    fn MapValue::entries(self : MapValue) -> ArrayView[(Value, Value)]

    MapValue::length

    fn MapValue::length(self : MapValue) -> Int

    MapValue::new

    fn MapValue::new(key_type~ : MapType, value_type~ : MapType, entries : Array[(Value, Value)]) -> MapValue raise MapError

    Builds a MAP. Entries whose value is MISSING are dropped (RFC 0104). Keys are lowered first; NULL, MISSING and non-scalar keys, and keys equal under eqg to an earlier key, raise.

    NullOrder

    pub(all) enum NullOrder {
    NullsFirst
    NullsLast
    } derive(Eq,
    Debug
    )

    Where NULL and MISSING sort.

    Time

    pub struct Time {
    hour : Int
    minute : Int
    second : Int
    nanos : Int
    precision : Int
    offset : Int?
    } derive(
    Debug
    )

    A time of day. offset is minutes east of UTC; None means WITHOUT TIME ZONE. precision is the number of fractional-second digits (TIME(p)).
    impl Eq for Time

    Time::new

    fn Time::new(hour~ : Int, minute~ : Int, second~ : Int, nanos? : Int, precision? : Int, offset? : Int?) -> Time raise DateTimeError

    Timestamp

    pub struct Timestamp {
    date : Date
    time : Time
    } derive(
    Debug
    )

    A date and a time. The time's offset is the timestamp's offset.
    impl Eq for Timestamp

    Timestamp::new

    fn Timestamp::new(date : Date, time : Time) -> Timestamp

    Tuple

    pub struct Tuple {
    // private fields
    } derive(
    Debug
    )

    A PartiQL tuple: (name, value) pairs. Order is kept for output only; duplicate names are allowed; no value is MISSING.
    impl Eq for Tuple

    Tuple::fields

    fn Tuple::fields(self : Tuple) -> ArrayView[(String, Value)]

    Tuple::get_all

    fn Tuple::get_all(self : Tuple, name : String) -> Array[Value]

    The values of the attributes named name (case-sensitive).

    Tuple::length

    fn Tuple::length(self : Tuple) -> Int

    Tuple::new

    fn Tuple::new(fields : Array[(String, Value)]) -> Tuple

    Builds a tuple. Pairs whose value is MISSING are dropped.

    Value

    pub(all) enum Value {
    Null
    Missing
    Bool(Bool)
    Int(Int64)
    BigInt(
    BigInt
    )
    Float(Double)
    Decimal(
    Decimal
    )
    String(String)
    Clob(Bytes)
    Blob(Bytes)
    Date(Date)
    Time(Time)
    Timestamp(Timestamp)
    IntervalYM(IntervalYM)
    IntervalDT(IntervalDT)
    List(Array[Value])
    Bag(Bag)
    Tuple(Tuple)
    Map(MapValue)
    Graph(GraphValue)
    Ion(
    IonValue
    )
    } derive(
    Debug
    )

    A PartiQL value.

    Ion holds an exact Ion value (from a backtick literal or $ion::). It is a representation, never a PartiQL type: every semantic acts on its lowered value (see Value::lower).
    impl Eq for Value

    Value::integer

    An integer value: Int when it fits in Int64, else BigInt.

    Value::is_absent

    fn Value::is_absent(self : Value) -> Bool

    Whether the value is NULL or MISSING.

    Value::lower

    fn Value::lower(self : Value) -> Value raise LowerError

    Converts a boxed Ion value to its core value, one level deep. Other values are returned unchanged.

    Value::lower_deep

    fn Value::lower_deep(self : Value) -> Value raise LowerError

    Lowers recursively, including the children of collections and tuples.

    compare

    fn compare(a : Value, b : Value, nulls~ : NullOrder) -> Int

    The ORDER BY total order (spec section 4.4). Returns -1, 0 or 1.

    eqg

    fn eqg(a : Value, b : Value) -> Bool

    Grouping equivalence: NULL eqg NULL, MISSING eqg MISSING, NaN eqg NaN; otherwise the same as =.

    sql_equals

    fn sql_equals(a : Value, b : Value) -> Value

    The PartiQL = operator: MISSING if either side is MISSING, else NULL if either side is NULL, else a Bool. Never fails on mixed types.

    timestamp_of_ion

    Converts an Ion timestamp: missing fields become 0, an unknown offset becomes UTC, and more than 9 fractional digits are truncated.

    Powered by MoonBit

    Site sourceReport issuePackagesBuild queueSkillsStatistics

    © 2026 mooncakes.io