Skip to main content
Version: 1.0.1

Defining Indexes

CREATE/DROP INDEX gibi yaygın DDL komutlarına ek olarak dizinleri tanımlamak için Ignite'ın SQL API'lerini kullanabilirsiniz.

Ignite, her primary key ve affinity key alanı için otomatik olarak indexler oluşturur. Değer nesnesindeki bir alan üzerinde bir index tanımladığınızda, Ignite, indexlenmiş alandan ve cache’in primary keyinden oluşan bir composite index oluşturur. SQL açısından bu, indexin iki sütundan oluşacağı anlamına gelir: indexe eklemek istediğiniz sütun ve primary key sütunu.

Creating Indexes With SQL

CREATE INDEX bölümüne bakın.

Configuring Indexes Using Annotations

Indexler ve sorgulanabilir alanlar, [QuerySqlField] attribute’u aracılığıyla koddan yapılandırılabilir. Aşağıdaki örnekte, Ignite SQL motoru id ve salary alanları için indexler oluşturacaktır.

  • ⌨️ .NET Sample
    class Person
    {
    // Indexed field. Will be visible to the SQL engine.
    [QuerySqlField(IsIndexed = true)] public long Id;

    //Queryable field. Will be visible to the SQL engine
    [QuerySqlField] public string Name;

    //Will NOT be visible to the SQL engine.
    public int Age;

    /** Indexed field sorted in descending order.
    * Will be visible to the SQL engine. */
    [QuerySqlField(IsIndexed = true, IsDescending = true)]
    public float Salary;
    }

Tür adı, SQL sorgularında tablo adı olarak kullanılır. Bu durumda tablomuzun adı Person olacaktır (şema adı kullanımı ve tanımı Schemas bölümünde anlatılmıştır).

Hem id hem de salary indexli alanlardır. id artan şekilde (varsayılan) ve salary azalan şekilde sıralanacaktır.

Bir alanı indexe eklemek istemiyorsanız, ancak yine de SQL sorgularında kullanmanız gerekiyorsa, o zaman alana index = true parametresi olmadan attribute eklenmelidir. Böyle bir alana sorgulanabilir alan denir. Yukarıdaki örnekte, name sorgulanabilir bir alan olarak tanımlanmıştır.

Age alanı ne sorgulanabilir ne de indexlenmiş bir alandır ve bu nedenle SQL sorgularından erişilemez.

İndexlenmiş alanları tanımladığınızda, indexlenmiş türleri kaydetmeniz gerekir.

Indexing Nested Objects

Nested nesnelerin alanları da ek attributelar kullanılarak indexe eklenebilir ve sorgulanabilir. Örneğin, bir alan olarak Address nesnesine sahip bir Person nesnesini düşünün:

  • ⌨️ Java Sample
    public class Person {
    /** Indexed field. Will be visible for SQL engine. */
    @QuerySqlField(index = true)
    private long id;

    /** Queryable field. Will be visible for SQL engine. */
    @QuerySqlField
    private String name;

    /** Will NOT be visible for SQL engine. */
    private int age;

    /** Indexed field. Will be visible for SQL engine. */
    @QuerySqlField(index = true)
    private Address address;
    }

Address sınıfının yapısı şöyle görünebilir:

  • ⌨️ Java Sample
    public class Address {
    /** Indexed field. Will be visible for SQL engine. */
    @QuerySqlField (index = true)
    private String street;

    /** Indexed field. Will be visible for SQL engine. */
    @QuerySqlField(index = true)
    private int zip;
    }

Yukarıdaki örnekte, @QuerySqlField(index = true) annotation’u, Person sınıfındaki Address nesnesinin yanı sıra Address sınıfının tüm alanlarında belirtilmiştir.

Bu, aşağıdaki gibi SQL sorgularını yürütmeyi mümkün kılar:

QueryCursor<List<?>> cursor = personCache.query(new SqlFieldsQuery( "select * from Person where street = 'street1'"));

SQL sorgusunun WHERE yan tümcesinde address.street belirtmeniz gerekmediğini unutmayın. Bunun nedeni, Address sınıfının alanlarının Person tablosunda düzleştirilmesidir(flattened); bu, sorgulardaki Address alanlarına doğrudan erişmemizi sağlar.

Nested nesneler için indexler oluşturursanız, tabloda UPDATE veya INSERT deyimlerini çalıştıramazsınız.

Registering Indexed Types

Indexlenmiş ve sorgulanabilir alanlar tanımlandıktan sonra ait oldukları nesne türleri ile birlikte SQL motorunda kaydedilmeleri gerekir.

Hangi türlerin indexe eklenmesi gerektiğini belirtmek için aşağıdaki örnekte gösterildiği gibi CacheConfiguration.setIndexedTypes() yönteminde karşılık gelen key/value pairlerini iletin.

  • ⌨️ .NET Sample
    var ccfg = new CacheConfiguration
    {
    QueryEntities = new[]
    {
    new QueryEntity(typeof(long), typeof(Person))
    }
    };

Bu method yalnızca tür pairlerini kabul eder: biri key sınıf için, diğeri value sınıfı için. Primitive tipler boxed tipler olarak geçirilir.

*[QuerySqlField] attribute’u ile işaretlenmiş tüm alanlara ek olarak, her tablo önceden tanımlanmış iki özel alana sahip olacaktır: _key ve _val, tüm key ve value nesnelerine bağlantıları temsil eder. Bu, örneğin, bunlardan biri primitive bir tür olduğunda ve değerine göre filtrelemek istediğinizde kullanışlıdır. Bunu yapmak için şöyle bir sorgu çalıştırın: SELECT * FROM Person WHERE _key = 100.*

Ignite, Binary Nesneleri desteklediğinden, cluster node’larının sınıf yoluna index’e alınmış türden sınıflar eklemeye gerek yoktur. SQL sorgu motoru, indexe alınmış ve sorgulanabilir alanların değerlerini algılayarak nesne deserialization işleminden kaçınabilir.

Group Indexes

Karmaşık koşullara sahip sorguları hızlandırabilen çok alanlı bir index ayarlamak için bir [QuerySqlField.IndexGroups] özelliğini kullanabilirsiniz. Bir alanın birden fazla grubun parçası olmasını istiyorsanız, IndexGroups'a birden çok [QuerySqlField.IndexGroups] özelliği ekleyebilirsiniz.

Örneğin, aşağıdaki Person sınıfında, age_salary_idx adlı, "0" grup düzeni ve azalan sıralama düzeni ile indexlenmiş bir gruba ait age alanına sahibiz. Ayrıca aynı grupta, "3" grup düzeninde ve artan sıralama düzeninde salary alanımız var. Ayrıca, salary alanının kendisi tek sütunlu bir indextir(IndexGroups bildirimine ek olarak index = true parametresi belirtilir). Grup sırası belirli bir sayı olmak zorunda değildir. Yalnızca belirli bir grubun içindeki alanları sıralamak için gereklidir.

  • ⌨️ .NET Sample
    class Person
    {
    [QuerySqlField(IndexGroups = new[] {"age_salary_idx"})]
    public int Age;

    [QuerySqlField(IsIndexed = true, IndexGroups = new[] {"age_salary_idx"})]
    public double Salary;
    }

Configuring Indexes Using Query Entities

Indexler ve sorgulanabilir alanlar, Spring XML tabanlı yapılandırma için uygun olan org.apache.ignite.cache.QueryEntity sınıfı aracılığıyla da yapılandırılabilir.

Yukarıda attribute tabanlı yapılandırmanın bir parçası olarak açıklanan tüm kavramlar, QueryEntity tabanlı yaklaşım için de geçerlidir. Ayrıca, alanları [QuerySqlField] attribute’u ile yapılandırılan ve CacheConfiguration.setIndexedTypes() yöntemiyle kaydedilen türler, dahili olarak sorgu varlıklarına dönüştürülür.

Aşağıdaki örnek, tek bir alan indexi, grup indexleri ve sorgulanabilir alanların nasıl tanımlanacağını gösterir.

  • ⌨️ .NET Sample
    var cacheCfg = new CacheConfiguration
    {
    Name = "myCache",
    QueryEntities = new[]
    {
    new QueryEntity
    {
    KeyType = typeof(long),
    KeyFieldName = "id",
    ValueType = typeof(dotnet_helloworld.Person),
    Fields = new[]
    {
    new QueryField
    {
    Name = "id",
    FieldType = typeof(long)
    },
    new QueryField
    {
    Name = "name",
    FieldType = typeof(string)
    },
    new QueryField
    {
    Name = "salary",
    FieldType = typeof(long)
    },
    },
    Indexes = new[]
    {
    new QueryIndex("name"),
    new QueryIndex(false, QueryIndexType.Sorted, new[] {"id", "salary"})
    }
    }
    }
    };

    Ignition.Start(new IgniteConfiguration
    {
    CacheConfiguration = new[] {cacheCfg}
    });

ValueType'ın kısa adı, SQL sorgularında tablo adı olarak kullanılır. Bu durumda tablomuzun adı olacaktır.

QueryEntity tanımlandıktan sonra, SQL sorgusunu aşağıdaki gibi yürütebilirsiniz:

SqlFieldsQuery qry = new SqlFieldsQuery("SELECT id, name FROM Person" + "WHERE id > 1500 LIMIT 10");

Configuring Index Inline Size

Uygun index satır içi boyutu, indexe alınmış alanlarda sorguları hızlandırmaya yardımcı olabilir. Uygun bir satır içi boyutun nasıl seçileceği hakkında bilgi için SQL Ayarlama kılavuzundaki ilgili bölüme bakın.

Çoğu durumda, yalnızca stringler veya arrayler gibi değişken uzunluklu alanlardaki indexler için satır içi boyutunu ayarlamanız gerekir. Varsayılan değer 10'dur.

Varsayılan değeri

  • her index için ayrı ayrı satır içi boyut veya,
  • belirli bir cache içindeki tüm indexler için CacheConfiguration.sqlIndexMaxInlineSize özelliği veya
  • Clusterdaki tüm indexler için IGNITE_MAX_INDEX_PAYLOAD_SIZE sistem özelliği

ayarlayarak değiştirebilirsiniz. Ayarlar, yukarıda listelenen sırayla uygulanır.

Ayrıca varsayılan değerin üzerine yazacak şekilde her index için satır içi boyutunu ayrı ayrı yapılandırabilirsiniz. Kullanıcı tanımlı bir index için index satır içi boyutunu ayarlamak üzere aşağıdaki yöntemlerden birini kullanın. Her durumda, değer bayt olarak ayarlanır.

  • ⌨️ .NET Sample with Attribute
    [QuerySqlField(IsIndexed = true, IndexInlineSize = 13)]
    public string Country { get; set; }
  • ⌨️ .NET Sample with QueryEntity
    var qe = new QueryEntity
    {
    Indexes = new[]
    {
    new QueryIndex
    {
    InlineSize = 13
    }
    }
    };

CREATE INDEX komutunu kullanarak indexler oluşturursanız, satır içi boyutunu ayarlamak için INLINE_SIZE seçeneğini kullanabilirsiniz. İlgili bölümdeki örneklere bakın;

create index country_idx on Person (country) INLINE_SIZE 13;

Custom Keys

Primary keyler için yalnızca önceden tanımlanmış SQL veri türlerini kullanırsanız, SQL şeması yapılandırmasıyla ek manipülasyon yapmanız gerekmez. Bu veri türleri, aşağıda listelendiği gibi GridQueryProcessor.SQL_TYPES sabiti tarafından tanımlanır.

Önceden tanımlanmış SQL veri türleri şunları içerir:

  • char ve Character dışındaki tüm primitive tipler ve wrapperları
  • String
  • BigDecimal
  • byte[]
  • java.util.Datejava.sql.Datejava.sql.Timestamp
  • java.util.UUID

Ancak, özel bir karmaşık key uygulamaya karar verdiğinizde ve alanlarına DML ifadelerinden başvurduğunuzda, şunları yapmanız gerekir:

  • QueryEntity'deki bu alanları, değer nesnesi için alanları ayarladığınız şekilde tanımlayın.
  • Key alanları value alanlarından ayırmak için yeni yapılandırma parametresi QueryEntity.setKeyFields(..) kullanın.

Aşağıdaki örnek bunun nasıl yapılacağını göstermektedir.

  • ⌨️ .NET Sample