Aracılığıyla paylaş


Gremlin sorgularınızı hesaplamak için yürütme profili adımını kullanma

ŞUNLAR IÇIN GEÇERLIDIR: Gremlin

Bu makalede, Gremlin graf veritabanları için Azure Cosmos DB için yürütme profili adımının nasıl kullanılacağına ilişkin genel bir bakış sağlanır. Bu adım, sorun giderme ve sorgu iyileştirmeleri için ilgili bilgileri sağlar ve Cosmos DB Gremlin API’si hesabında yürütülebilen tüm Gremlin sorgularıyla uyumludur.

Bu adımı kullanmak için Gremlin sorgunuzun sonuna işlev çağrısını eklemeniz executionProfile() yeterlidir. Gremlin sorgunuz yürütülür ve işlemin sonucu sorgu yürütme profiline sahip bir JSON yanıt nesnesi döndürür.

Örneğin:

    // Basic traversal
    g.V('mary').out()

    // Basic traversal with execution profile call
    g.V('mary').out().executionProfile()

Adım çağrıldıktan executionProfile() sonra yanıt, yürütülen Gremlin adımını, geçen toplam süreyi ve deyimin sonucunda elde edilen Cosmos DB çalışma zamanı işleçlerini içeren bir JSON nesnesi olacaktır.

Not

Yürütme Profili için bu uygulama Apache Tinkerpop belirtiminde tanımlanmamıştır. Gremlin'in uygulaması için Azure Cosmos DB'ye özgüdür.

Yanıt Örneği

Aşağıda, döndürülecek çıkışın açıklamalı bir örneği verilmiştir:

Not

Bu örnekte, yanıtın genel yapısını açıklayan açıklamalara yer verilmiştir. Gerçek bir executionProfile yanıtı herhangi bir açıklama içermez.

[
  {
    // The Gremlin statement that was executed.
    "gremlin": "g.V('mary').out().executionProfile()",

    // Amount of time in milliseconds that the entire operation took.
    "totalTime": 28,

    // An array containing metrics for each of the steps that were executed. 
    // Each Gremlin step will translate to one or more of these steps.
    // This list is sorted in order of execution.
    "metrics": [
      {
        // This operation obtains a set of Vertex objects.
        // The metrics include: time, percentTime of total execution time, resultCount, 
        // fanoutFactor, count, size (in bytes) and time.
        "name": "GetVertices",
        "time": 24,
        "annotations": {
          "percentTime": 85.71
        },
        "counts": {
          "resultCount": 2
        },
        "storeOps": [
          {
            "fanoutFactor": 1,
            "count": 2,
            "size": 696,
            "time": 0.4
          }
        ]
      },
      {
        // This operation obtains a set of Edge objects. 
        // Depending on the query, these might be directly adjacent to a set of vertices, 
        // or separate, in the case of an E() query.
        //
        // The metrics include: time, percentTime of total execution time, resultCount, 
        // fanoutFactor, count, size (in bytes) and time.
        "name": "GetEdges",
        "time": 4,
        "annotations": {
          "percentTime": 14.29
        },
        "counts": {
          "resultCount": 1
        },
        "storeOps": [
          {
            "fanoutFactor": 1,
            "count": 1,
            "size": 419,
            "time": 0.67
          }
        ]
      },
      {
        // This operation obtains the vertices that a set of edges point at.
        // The metrics include: time, percentTime of total execution time and resultCount.
        "name": "GetNeighborVertices",
        "time": 0,
        "annotations": {
          "percentTime": 0
        },
        "counts": {
          "resultCount": 1
        }
      },
      {
        // This operation represents the serialization and preparation for a result from 
        // the preceding graph operations. The metrics include: time, percentTime of total 
        // execution time and resultCount.
        "name": "ProjectOperator",
        "time": 0,
        "annotations": {
          "percentTime": 0
        },
        "counts": {
          "resultCount": 1
        }
      }
    ]
  }
]

Not

executionProfile adımı Gremlin sorgusunu yürütür. Bu, oluşturmayla addV sonuçlanacak ve sorguda belirtilen değişiklikleri işleyecek olan veya addEadımlarını içerir. Sonuç olarak, Gremlin sorgusu tarafından oluşturulan İstek Birimleri de ücretlendirilir.

Yürütme profili yanıt nesneleri

executionProfile() işlevinin yanıtı, aşağıdaki yapıya sahip bir JSON nesnelerinin hiyerarşisini verir:

  • Gremlin işlem nesnesi: Yürütülen Gremlin işleminin tamamını temsil eder. Aşağıdaki özellikleri içerir.

    • gremlin: Yürütülen açık Gremlin deyimi.
    • totalTime: Adımın yürütülmesinin tahakkuk ettirilen milisaniye cinsinden süresi.
    • metrics: Sorguyu gerçekleştirmek için yürütülen Cosmos DB çalışma zamanı işleçlerinin her birini içeren bir dizi. Bu liste yürütme sırasına göre sıralanır.
  • Cosmos DB çalışma zamanı işleçleri: Gremlin işleminin tamamının bileşenlerinin her birini temsil eder. Bu liste yürütme sırasına göre sıralanır. Her nesne aşağıdaki özellikleri içerir:

    • name: İşlecin adı. Bu, değerlendirilen ve yürütülen adım türüdür. Aşağıdaki tabloda daha fazla bilgi bulabilirsiniz.
    • time: Belirli bir işlecin aldığı milisaniye cinsinden süre.
    • annotations: Yürütülen işlecine özgü ek bilgiler içerir.
    • annotations.percentTime: Belirli bir işleci yürütmek için geçen toplam sürenin yüzdesi.
    • counts: Bu işleç tarafından depolama katmanından döndürülen nesne sayısı. Bu, içindeki skaler değerde counts.resultCount yer alır.
    • storeOps: Bir veya birden çok bölüme yayılabilen bir depolama işlemini temsil eder.
    • storeOps.fanoutFactor: Bu belirli depolama işlemine erişilen bölüm sayısını temsil eder.
    • storeOps.count: Bu depolama işleminin döndürdüğünü sonuç sayısını temsil eder.
    • storeOps.size: Belirli bir depolama işleminin sonucunun bayt cinsinden boyutunu temsil eder.
Cosmos DB Gremlin Çalışma Zamanı İşleci Açıklama
GetVertices Bu adım, kalıcılık katmanından önceden belirlenmiş bir nesne kümesi alır.
GetEdges Bu adım, bir köşe kümesine bitişik olan kenarları alır. Bu adım bir veya birden çok depolama işlemine neden olabilir.
GetNeighborVertices Bu adım, bir kenar kümesine bağlı köşeleri alır. Kenarlar, hem kaynak hem de hedef köşelerinin bölüm anahtarlarını ve kimliklerini içerir.
Coalesce Bu adım, Gremlin adımı her yürütülürken iki işlemin değerlendirilmesini coalesce() hesaplar.
CartesianProductOperator Bu adım, iki veri kümesi arasında kartezyen ürünü hesaplar. Genellikle koşul to() her kullanıldığında veya from() kullanıldığında yürütülür.
ConstantSourceOperator Bu adım, sonuç olarak sabit bir değer üretmek için bir ifade hesaplar.
ProjectOperator Bu adım, önceki işlemlerin sonucunu kullanarak bir yanıtı hazırlar ve serileştirir.
ProjectAggregation Bu adım, toplama işlemi için bir yanıtı hazırlar ve serileştirir.

Not

Yeni işleçler eklendikçe bu liste güncelleştirilmeye devam edecektir.

Yürütme profili yanıtlarını analiz etme örnekleri

Aşağıda, Yürütme Profili yanıtı kullanılarak tespit edilebilen yaygın iyileştirme örnekleri verilmiştir:

  • Kör fan-out sorgusu.
  • Filtrelenmemiş sorgu.

Kör fan-out sorgu desenleri

Bölümlenmiş bir grafikten aşağıdaki yürütme profili yanıtını varsayın:

[
  {
    "gremlin": "g.V('tt0093640').executionProfile()",
    "totalTime": 46,
    "metrics": [
      {
        "name": "GetVertices",
        "time": 46,
        "annotations": {
          "percentTime": 100
        },
        "counts": {
          "resultCount": 1
        },
        "storeOps": [
          {
            "fanoutFactor": 5,
            "count": 1,
            "size": 589,
            "time": 75.61
          }
        ]
      },
      {
        "name": "ProjectOperator",
        "time": 0,
        "annotations": {
          "percentTime": 0
        },
        "counts": {
          "resultCount": 1
        }
      }
    ]
  }
]

Bundan aşağıdaki sonuçlar elde edilebilir:

  • Gremlin deyimi desenini g.V('id')izlediğinden sorgu tek kimlikli bir aramadır.
  • Ölçüme time göre, tek bir noktadan okuma işlemi için 10 m'den uzun olduğundan bu sorgunun gecikme süresi yüksek gibi görünüyor.
  • nesnesine storeOps bakarsak, öğesinin fanoutFactor olduğunu 5görebiliriz. Bu, bu işlemle 5 bölüme erişildiği anlamına gelir.

Bu analizin sonucu olarak, ilk sorgunun gerekenden daha fazla bölüme eriştiğini belirleyebiliriz. Sorgudaki bölümleme anahtarı koşul olarak belirtilerek bu sorun giderilebilir. Bu, sorgu başına daha az gecikme süresine ve daha az maliyete yol açar. Grafik bölümleme hakkında daha fazla bilgi edinin. Daha uygun bir sorgu olacaktır g.V('tt0093640').has('partitionKey', 't1001').

Filtrelenmemiş sorgu desenleri

Aşağıdaki iki yürütme profili yanıtını karşılaştırın. Kolaylık olması için bu örneklerde tek bir bölümlenmiş grafik kullanılır.

Bu ilk sorgu etiketli tweet tüm köşeleri alır ve ardından komşu köşelerini alır:

[
  {
    "gremlin": "g.V().hasLabel('tweet').out().executionProfile()",
    "totalTime": 42,
    "metrics": [
      {
        "name": "GetVertices",
        "time": 31,
        "annotations": {
          "percentTime": 73.81
        },
        "counts": {
          "resultCount": 30
        },
        "storeOps": [
          {
            "fanoutFactor": 1,
            "count": 13,
            "size": 6819,
            "time": 1.02
          }
        ]
      },
      {
        "name": "GetEdges",
        "time": 6,
        "annotations": {
          "percentTime": 14.29
        },
        "counts": {
          "resultCount": 18
        },
        "storeOps": [
          {
            "fanoutFactor": 1,
            "count": 20,
            "size": 7950,
            "time": 1.98
          }
        ]
      },
      {
        "name": "GetNeighborVertices",
        "time": 5,
        "annotations": {
          "percentTime": 11.9
        },
        "counts": {
          "resultCount": 20
        },
        "storeOps": [
          {
            "fanoutFactor": 1,
            "count": 4,
            "size": 1070,
            "time": 1.19
          }
        ]
      },
      {
        "name": "ProjectOperator",
        "time": 0,
        "annotations": {
          "percentTime": 0
        },
        "counts": {
          "resultCount": 20
        }
      }
    ]
  }
]

Bitişik köşeleri keşfetmeden önce aynı sorgunun profiline dikkat edin, ancak şimdi ek bir filtreyle has('lang', 'en'), :

[
  {
    "gremlin": "g.V().hasLabel('tweet').has('lang', 'en').out().executionProfile()",
    "totalTime": 14,
    "metrics": [
      {
        "name": "GetVertices",
        "time": 14,
        "annotations": {
          "percentTime": 58.33
        },
        "counts": {
          "resultCount": 11
        },
        "storeOps": [
          {
            "fanoutFactor": 1,
            "count": 11,
            "size": 4807,
            "time": 1.27
          }
        ]
      },
      {
        "name": "GetEdges",
        "time": 5,
        "annotations": {
          "percentTime": 20.83
        },
        "counts": {
          "resultCount": 18
        },
        "storeOps": [
          {
            "fanoutFactor": 1,
            "count": 18,
            "size": 7159,
            "time": 1.7
          }
        ]
      },
      {
        "name": "GetNeighborVertices",
        "time": 5,
        "annotations": {
          "percentTime": 20.83
        },
        "counts": {
          "resultCount": 18
        },
        "storeOps": [
          {
            "fanoutFactor": 1,
            "count": 4,
            "size": 1070,
            "time": 1.01
          }
        ]
      },
      {
        "name": "ProjectOperator",
        "time": 0,
        "annotations": {
          "percentTime": 0
        },
        "counts": {
          "resultCount": 18
        }
      }
    ]
  }
]

Bu iki sorgu aynı sonuç elde etti, ancak ilk sorgu daha fazla İstek Birimi gerektirir çünkü bitişik öğeleri sorgulamadan önce daha büyük bir ilk veri kümesini yinelemesi gerekir. Her iki yanıttan aşağıdaki parametreleri karşılaştırırken bu davranışın göstergelerini görebiliriz:

  • İlk metrics[0].time yanıtta değer daha yüksektir ve bu da bu tek adımın çözülmesinin daha uzun sürdüğünü gösterir.
  • değer metrics[0].counts.resultsCount , ilk çalışma veri kümesinin daha büyük olduğunu gösteren ilk yanıtta olduğu gibi daha yüksektir.

Sonraki adımlar