Может ли graph db решить мои проблемы с графом?

У меня есть данные транзакций (pastebin.com/ZswbyVHM), например:

{"accountId":3,"recordedAt":"2013-12-01T00:00:00.000Z","region":"South","status":"H"}
{"accountId":3,"recordedAt":"2014-01-01T00:00:00.000Z","region":"South","status":"A"}
{"accountId":3,"recordedAt":"2014-02-01T00:00:00.000Z","region":"South","status":"B"}
{"accountId":3,"recordedAt":"2014-03-01T00:00:00.000Z","region":"South","status":"E"}
{"accountId":3,"recordedAt":"2014-04-01T00:00:00.000Z","region":"South","status":"C"}

когда групповые транзакции по accountId это можно рассматривать как:

{"accountId": 3, "region":"South", "transactions": [
    {"recordedAt":"2013-12-01T00:00:00.000Z", "status": "H"},
    {"recordedAt":"2014-01-01T00:00:00.000Z", "status": "A"},
    {"recordedAt":"2014-02-01T00:00:00.000Z", "status": "B"}]
}

Исходя из вышесказанного, я хотел бы создать график отношения статуса из коллекции транзакций, который может сохранить порядок статуса, recordedAt, accountId со следующими свойствами:

  • Узлы графика представляют статус и неявно порядок статуса.
  • Их края имеют accountsмассив accountId, имеющий одинаковый статус, изменяющийся от одного к другому в том же порядке.

  • Путь графа является пересечением между accountId, status а также level (порядок статуса).

Пример: график отношения статуса

  1. Есть два состояния от корня "A" и "H".

  2. На уровне 0,

    AccountId 1, 2, 4 имеют такой же статус "A", кроме AccountId 3.

    Путь AccountId 4 заканчивается на этом уровне.

  3. На уровне 1,

    AccountId 1, 2 имеют одинаковый статус "A",

    AccountId 3 имеет тот же статус "A", но с другого пути.

    Путь AccountId 1 заканчивается на этом уровне.

  4. На уровне 2

    AccountId 2 имеет статус "B".

    AccountId 3 имеет тот же статус "B", но с другого пути.

  5. На уровне 3

    AccountId 2 имеет статус "A", а AccountId 3 имеет статус "E"

Итак, я разработал 3 крайние коллекции:

Дизайн 1: Каждое ребро представляет собой отношение между вершиной состояния, которая использует level сохранить порядок транзакции.

{"_from": "status/root", "_to": "status/A", "level": 0, "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-05-01"}]}
{"_from": "status/A"   , "_to": "status/A", "level": 1, "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-06-01"}]}
{"_from": "status/A"   , "_to": "status/B", "level": 2, "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-07-01"}]}
{"_from": "status/B"   , "_to": "status/A", "level": 3, "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-08-01"}]}
{"_from": "status/A"   , "_to": "status/G", "level": 4, "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-09-01"}]}
{"_from": "status/G"   , "_to": "status/G", "level": 5, "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-10-01"}]}
{"_from": "status/G"   , "_to": "status/H", "level": 6, "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-11-01"}]}
{"_from": "status/H"   , "_to": "status/D", "level": 7, "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-12-01"}]}
{"_from": "status/D"   , "_to": "status/A", "level": 8, "accounts": [{"id": 2, "region": "South", "recordedAt": "2013-01-01"}]}
{"_from": "status/A"   , "_to": "status/A", "level": 9, "accounts": [{"id": 2, "region": "South", "recordedAt": "2013-02-01"}]}

Дизайн 2: Каждое ребро - это отношение между вершиной уровня, которая имеет атрибут ребра status,

{"_from": "level/root", "_to": "level/0", "status": "A", "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-05-01"}]}
{"_from": "level/0"   , "_to": "level/1", "status": "A", "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-06-01"}]}
{"_from": "level/1"   , "_to": "level/2", "status": "B", "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-07-01"}]}
{"_from": "level/2"   , "_to": "level/3", "status": "A", "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-08-01"}]}
{"_from": "level/3"   , "_to": "level/4", "status": "G", "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-09-01"}]}
{"_from": "level/4"   , "_to": "level/5", "status": "G", "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-10-01"}]}
{"_from": "level/5"   , "_to": "level/6", "status": "H", "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-11-01"}]}
{"_from": "level/6"   , "_to": "level/7", "status": "D", "accounts": [{"id": 2, "region": "South", "recordedAt": "2012-12-01"}]}
{"_from": "level/7"   , "_to": "level/8", "status": "A", "accounts": [{"id": 2, "region": "South", "recordedAt": "2013-01-01"}]}
{"_from": "level/8"   , "_to": "level/9", "status": "A", "accounts": [{"id": 2, "region": "South", "recordedAt": "2013-02-01"}]}

Дизайн 3: путем добавления виртуальной вершины (регион, год).

Эту конструкцию пытаются устранить accounts чтобы избежать фильтрации массива объектов. Проще фильтровать по атрибуту ребра.

{"_from": "level/root" , "_to": "level/South"}
{"_from": "level/South", "_to": "level/2012"}
{"_from": "level/2016" , "_to": "level/0", "status": "A", "accountId": 1}
{"_from": "level/2012" , "_to": "level/0", "status": "A", "accountId": 2}
{"_from": "level/2017" , "_to": "level/0", "status": "A", "accountId": 4}
{"_from": "level/0"    , "_to": "level/1", "status": "A", "accountId": 1}
{"_from": "level/0"    , "_to": "level/1", "status": "A", "accountId": 2}
{"_from": "level/1"    , "_to": "level/2", "status": "B", "accountId": 2}
{"_from": "level/2"    , "_to": "level/3", "status": "A", "accountId": 2}
{"_from": "level/3"    , "_to": "level/4", "status": "G", "accountId": 2}
{"_from": "level/4"    , "_to": "level/5", "status": "G", "accountId": 2}
{"_from": "level/5"    , "_to": "level/6", "status": "H", "accountId": 2}
{"_from": "level/6"    , "_to": "level/7", "status": "D", "accountId": 2}
{"_from": "level/7"    , "_to": "level/8", "status": "A", "accountId": 2}
{"_from": "level/8"    , "_to": "level/9", "status": "A", "accountId": 2}
  • Этот график использует для запроса:
    1. Напомним шаблон состояния для конкретного accountId путем фильтрации пути, чтобы все ребра указали идентификатор.

Псевдо AQL:

FOR v, e, p IN 1..20 OUTBOUND status/root statusRelations
  FILTER p.edges[*].accountId ALL == id
RETURN p.edges.status
  1. Какие статусы приводят к интересному статусу (по региону или году)?

Псевдо AQL:

FILTER e._to == "status/D" (AND e.region == "North" AND e.year == 2013)
RETURN SLICE(p.edges[*], -3) // RETURN 3 previous statuses that followed by "D"
  1. Какой статус больше всего произошел за год?

Псевдо AQL:

FILTER e.year == 2013
COLLECT status = e.status WITH COUNT INTO length
RETURN status

Какой из моих дизайнов лучше всего подходит для ArangoDB и может отвечать на мои вопросы?

0 ответов

Другие вопросы по тегам