4th Street Bar Hive-Bar

Hive-Bar Powered by Hive beta-fdb5b5b

Community post

EctoPgJson 0.1 release: Elixir/Ecto extension for Posgres JSON/JSONB operators

I've released EctoPgJson, a new Elixir/Erlang library for Postgres JSON operators for JSON and JSONB datatypes. EctoPgJson provides a macro-based utility functions for Ecto queries.

Links

Repo

Commits and changes

Implemented operators and functions

PG operator right PG operand type EctoPgJson function description
-> int get_object(jsonb, field) Get JSON array element
-> text get_object(jsonb, field) Get JSON object field by key
->> int get_text(jsonb, field) Get JSON array element as text
->> text get_text(jsonb, field) Get JSON object field as text
#> text[] get_json_in(jsonb, field) Get JSON object at specified path
#>> text[] get_text_in(jsonb, field) Get JSON object at specified path as text
@> jsonb left_cotains?(jsonb, jsonb) Does the left JSON value contain the right JSON path/value entries at the top level?
<@ jsonb right_contains?(jsonb, jsonb) Are the left JSON path/value entries contained at the top level within the right JSON value?
? text keys_exist?(jsonb, key) Does the string exist as a top-level key within the JSON value?
?| text[] keys_exist?(jsonb, any: strings) Do any of these array strings exist as top-level keys?
?& text[] keys_exist?(jsonb, all: strings) Do all of these array strings exist as top-level keys?

Example data

      create table metrics (
        id serial primary key,
        attributes jsonb
      );
  
      insert into metrics (id, attributes)
      values
        (1, '{"data": "nope"}'),
        (2, '{"data": {"level2": "yep"}}'),
        (3, '{"data": {"level2": {"level3": "yepyep"}}}');
  

Example queries

   q =
     from t in @table,
       where: get_text(t.attributes, "data") == "nope",
       select: t.id

   assert TestRepo.one(q) == 1
   q =
     from t in @table,
       where: t.id == 2,
       select: get_object(t.attributes, "data")

   assert TestRepo.one(q) == %{"level2" => "yep"}
  q =
    from t in @table,
      where: t.id == 2,
      select: get_text_in(t.attributes, "{data, level2}")

  q2 =
    from t in @table,
      where: t.id == 2,
      select: get_text_in(t.attributes, ["data", "level2"])

  assert TestRepo.one(q) == TestRepo.one(q2)
  assert TestRepo.one(q) == "yep"
  q =
    from t in @table,
      where: t.id == 3,
      select: get_object_in(t.attributes, "{data, level2}")

  q2 =
    from t in @table,
      where: t.id == 3,
      select: get_object_in(t.attributes, ["data", "level2"])

  assert TestRepo.one(q) == TestRepo.one(q2)
  assert TestRepo.one(q) == %{"level3" => "yepyep"}
(*`□)<炎炎炎炎
32 upvotes $6.39

Replies (5)

Review before signing

Posting as . Signing with . Keychain permission: Posting. Hive Keychain will ask you to approve this action next.


  
Technical details

Operation fingerprint: