Banking and finance

Updated at:

In modern financial crimes, fraudsters change their identities to evade risk control rules. You can use Graph Database (GDB) to build a graph structure that tracks user behavior. This lets you analyze discrete data from fraudulent activities in real time and identify fraud rings. This helps you quickly prevent and resolve fraudulent activities.

1. Data model

This topic uses the IEEE-CIS Fraud Detection dataset, a public dataset for financial transactions, as an example. For more information, see Data model reference download.

The data consists of transaction records from the E-commerce platform Vesta. It includes information about devices, addresses, and mailboxes related to the transactions. The data model is shown in the following figure:

Note

In the examples in this topic, many filtering and statistical operations are performed on transaction properties. Therefore, transaction records and their properties are modeled as edges. If your business focuses more on the transaction records themselves, you can consider modeling the transaction properties directly as point properties.

5.6

The following is sample data:

  • Point file:

    // Transaction information.
    ~id,~label,is_fraud:int
    2987000,"transaction",0
    2987001,"transaction",0
    2987002,"transaction",0
    2987003,"transaction",0
    2987004,"transaction",0
    
    // Device type information.
    ~id,~label
    "mobile","devicetype"
    "desktop","devicetype"
  • Edge file:

    ~id,~from,~to,~label
    1,2987000,"","t_e_p"
    2,2987000,"","t_e_r"
    3,2987000,"315.0","t_a1"
    4,2987000,"87.0","t_a2"

2. Create an instance

Create a Graph Database instance. For more information, see Create a primary instance.

Note
  • After you purchase an instance, you can view its information on the Instance List page. The instance creation process typically takes 3 to 5 minutes.

  • After you create a GDB instance, create an account and password, and configure a security group. This ensures you have access permissions for the GDB instance. For more information, see Create an account and Set a whitelist.

3. Data import

Graph Database (GDB) supports importing data from multiple data sources. You can use one of the following two methods to import data:

4. Connect to an instance

Graph Database (GDB) supports multiple connection methods. You can use one of the following five methods to connect to an instance:

5. Usage examples

  • Simple queries

    • Data statistics:

      // Count the number of points.
      gremlin> g.V().count()
      ==>592789
      
      // Count the number of edges.
      gremlin> g.E().count()
      ==>2533038
    • Filter and sort queries:

      // Query the transaction information for ID 2987000.
      gremlin> g.V('2987000').valueMap(true)
      ==>[id:2987000,label:transaction,is_fraud:[0]]
      
      // Query the transaction information for ID 2987000.
      gremlin> g.V('2987000').outE()
      ==>e[3][2987000-t_a1->315.0]
      ==>e[4][2987000-t_a2->87.0]
      ==>e[5][2987000-t_p->W]

  • Common scenarios

    • K-hop neighbors:

      // Query other transaction records that share the same address as transaction record 2987000.
      gremlin> g.V('2987000').repeat(bothE('t_a1').otherV().simplePath()).times(2).path() // The bothE() part controls the edge type to query, and the times() part controls the query depth.
      ==>[v[2987000],e[3][2987000-t_a1->315.0],v[315.0],e[86][2987015-t_a1->315.0],v[2987015]]
      ==>[v[2987000],e[3][2987000-t_a1->315.0],v[315.0],e[171][2987031-t_a1->315.0],v[2987031]]
      ==>[v[2987000],e[3][2987000-t_a1->315.0],v[315.0],e[196][2987036-t_a1->315.0],v[2987036]]
      ==>[v[2987000],e[3][2987000-t_a1->315.0],v[315.0],e[305][2987056-t_a1->315.0],v[2987056]]
      ==>[v[2987000],e[3][2987000-t_a1->315.0],v[315.0],e[356][2987066-t_a1->315.0],v[2987066]]
      ==>[v[2987000],e[3][2987000-t_a1->315.0],v[315.0],e[399][2987073-t_a1->315.0],v[2987073]]
      ==>[v[2987000],e[3][2987000-t_a1->315.0],v[315.0],e[411][2987075-t_a1->315.0],v[2987075]]
      ==>[v[2987000],e[3][2987000-t_a1->315.0],v[315.0],e[451][2987083-t_a1->315.0],v[2987083]]
      ==>[v[2987000],e[3][2987000-t_a1->315.0],v[315.0],e[510][2987094-t_a1->315.0],v[2987094]]
      ......

    • Shortest path:

      // Find the shortest path between transaction record 2987000 and transaction record 2987172 with a maximum depth of 2.
      gremlin> g.V('2987000').repeat(bothE().otherV().simplePath())
                  .until(hasId('2987172').or().loops().is(gt(2L)))  // The hasId() part controls the end ID, and the gt() part controls the query depth.
                      .hasId('2987172').path().dedup()
      ==>[v[2987000],e[3][2987000-t_a1->315.0],v[315.0],e[938][2987172-t_a1->315.0],v[2987172]]
      ==>[v[2987000],e[4][2987000-t_a2->87.0],v[87.0],e[939][2987172-t_a2->87.0],v[2987172]]
      ==>[v[2987000],e[5][2987000-t_p->W],v[W],e[940][2987172-t_p->W],v[2987172]]

    • Common neighbors:

      // Find the common neighbors of transaction record 2987000 and transaction record 2987172 to identify transactions with the same properties, such as address and device.
      gremlin> g.V('2987000').repeat(bothE().otherV().simplePath()).times(2).hasId('2987172').path().dedup() // The hasId() part controls the end ID.
      ==>[v[2987000],e[3][2987000-t_a1->315.0],v[315.0],e[938][2987172-t_a1->315.0],v[2987172]]
      ==>[v[2987000],e[4][2987000-t_a2->87.0],v[87.0],e[939][2987172-t_a2->87.0],v[2987172]]
      ==>[v[2987000],e[5][2987000-t_p->W],v[W],e[940][2987172-t_p->W],v[2987172]]

    • Jaccard similarity:

      // Query transaction records similar to transaction record 2987000 and retrieve the top 10 based on the similarity score.
      gremlin> g.V('2987000')
                  .sideEffect(out().store('v1n'))
                  .as('v1')
                  .select('v1n').unfold().in().limit(100).simplePath().dedup().as('v2')
                  .project('i', 'u')
                      .by(select('v2').out().where(within('v1n')).count())
                      .by(union(select('v2').out().fold(),select('v1n')).unfold().dedup().count())
                  .project('Transaction', 'Similarity')
                      .by(select('v2').id())
                      .by(math('i/u'))
                  .order().by(select('Similarity'), desc).limit(10)
      ==>[Transaction:2987015,Similarity:1.0]
      ==>[Transaction:2987056,Similarity:1.0]
      ==>[Transaction:2987216,Similarity:1.0]
      ==>[Transaction:2987251,Similarity:1.0]
      ==>[Transaction:2987371,Similarity:1.0]
      ==>[Transaction:2987474,Similarity:1.0]
      ==>[Transaction:2987699,Similarity:1.0]
      ==>[Transaction:2987707,Similarity:1.0]
      ==>[Transaction:2987735,Similarity:1.0]
      ==>[Transaction:2987770,Similarity:1.0]

6. Customer results

The credit card center of a leading commercial bank automatically constructed 890 features. They discovered 12 suspected fraudulent merchants, predicted 18,600 overdue users, found 22,000 cards used for cash-out fraud, and identified 102 fraud rings. The model recall hit rate was 92.4%, compared to the 60% hit rate of the customer's previous model.