2 puan yazan GN⁺ 2024-10-23 | Henüz yorum yok. | WhatsApp'ta paylaş
  • ClickHouse, JSON belgelerini string olarak koyup her seferinde parse etme darboğazından kaçınmak için, JSON yoluna göre değerleri gerçek sütunlu depolamaya yerleştiren yeni bir JSON tipi tanıttı
  • Uygulamanın merkezinde Variant ve Dynamic tipleri var; aynı JSON yoluna tam sayı, string, dizi gibi farklı tipler gelse bile bunları zorla en küçük ortak tipte birleştirmiyor
  • max_dynamic_paths varsayılan değeri 1024, max_dynamic_types varsayılan değeri 32; böylece alt sütun ve tipe göre dosya sayısı sınırlandırılarak dosya tanımlayıcıları ve merge maliyetindeki artış kontrol ediliyor
  • Tip ipuçları, SKIP, SKIP REGEXP ile yola göre depolama biçimi ayarlanabiliyor; değerler C.a.b gibi alt sütun söz dizimi ile okunabiliyor
  • Yeni tip, kullanımdan kaldırılmış Object('json') tipinin yerini almayı hedefliyor; JSON anahtar yollarını birincil anahtarda veya data-skipping index içinde kullanmaya yönelik iyileştirmeler de yol haritasında duruyor

JSON'u sütunlu depolamaya uydurma görevi

  • JSON, loglar, gözlemlenebilirlik, gerçek zamanlı veri akışı, mobil uygulama depolaması ve makine öğrenimi pipeline'larında yarı yapılandırılmış ve yapılandırılmamış verilerle çalışmak için ortak bir format olarak kullanılır
  • ClickHouse, gerçek sütun odaklı bir veritabanıdır; tabloları diskteki sütun veri dosyaları koleksiyonu olarak saklar ve sıkıştırma ile vektörleştirilmiş filtreleme/toplama yapar
  • JSON'da da aynı performansı elde etmek için belgeleri bir string sütununda saklayıp daha sonra parse etmek yerine, her benzersiz JSON yolunun değerlerini sütun gibi saklamak gerekir

Yeni JSON tipinin ele aldığı dört kısıt

  • Yola göre sütunlu depolama

    • JSON yoluna göre değerler de sayısal tipler gibi normal sütunlar gibi sıkıştırılabilmeli, vektörleştirilmiş biçimde filtrelenip toplanabilmelidir
  • Dinamik olarak değişen tipler

    • Aynı JSON yolu a içinde tam sayı, ondalıklı sayı, dizi gibi farklı tipler bulunabilir
    • ClickHouse bunu önceden bilemez ve tipler birbiriyle uyumlu olmayabilir; en küçük ortak tipe birleştirmek bilgi kaybına yol açabilir
  • Sütun dosyası patlamasını önleme

    • Her yeni JSON yolu için yeni bir sütun dosyası oluşturulursa, çok sayıda benzersiz anahtarı olan verilerde disk dosyası sayısı hızla artar
    • Dosya tanımlayıcıları bellek kullanır; işlenmesi gereken dosya sayısı arttıkça merge performansı da etkilenir
  • Seyrek anahtarların yoğun depolanması

    • Benzersiz ama seyrek JSON anahtarları çok olduğunda, değeri olmayan her satır için NULL veya varsayılan değer tekrar tekrar saklanmamalıdır
    • PB ölçekli analizlerde de ölçeklenebilmek için yalnızca gerçek değerler yoğun depolanmalıdır

Variant tipi: tipleri zorla birleştirmeyen temel

  • Variant veri tipi, JSON'dan bağımsız olarak kullanılabilen ayrı bir özelliktir; tek bir tablo sütunu içinde farklı veri tiplerindeki değerleri saklayıp okuyabilir
  • Mevcut ClickHouse sütunları sabit tipe sahiptir; eklenen değer bu tipte olmalı ya da örtük olarak dönüştürülmelidir
    • Nullable sütunlar değer dosyasına ek olarak NULL maskesi dosyası kullanır
    • Array, dizi boyutunu ayrı bir dosyada saklar ve bunun üzerinden offset hesaplar
  • Variant sütunu, aynı somut tipteki değerleri tipe göre alt sütunlarda saklar
    • Örn: tüm Int64 değerleri C.Int64.bin, tüm String değerleri C.String.bin içinde saklanır
  • Her satırın hangi tipi kullandığı UInt8 discriminator sütunuyla izlenir
    • discriminator değeri, sıralanmış tip adı listesindeki indekstir
    • discriminator 255, NULL için ayrılmış değerdir
    • Bu tasarım nedeniyle Variant en fazla 255 somut tipe sahip olabilir
  • Tipe göre veri dosyaları yalnızca değeri olan satırları içeren yoğun depolama yapısındadır
    • Tipe göre dosyalarda NULL değerleri saklanmaz
    • discriminator satırından gerçek tip dosyasındaki satır konumunu bulmak için bellekteki UInt64 offset sütunu kullanılır
    • Bu offset diske yazılmaz; discriminator sütun dosyasından anında üretilebilir
  • Variant keyfi iç içe geçmeyi destekler
    • Variant(T1, T2) ile Variant(T2, T1) tip sırasına göre aynı anlama gelir
    • Variant içine tekrar Variant koyulabilir
  • Belirli bir iç içe tip değeri, tip adı alt sütun gibi eklenerek okunur
    • Örn: C.Int64

Dynamic tipi: tip listesini önceden bilmeden depolama

  • Dynamic tipi, Variant üzerine uygulanmış bağımsız bir özelliktir ve JSON bağlamı dışında da kullanılabilir
  • Dynamic, Variant'a iki özellik ekler
    • Tek bir sütun içinde keyfi tipte değerleri saklar, üstelik tip listesini önceden belirtmek gerekmez
    • Ayrı sütun veri dosyası olarak saklanacak tip sayısını sınırlayabilir
  • İç depolama biçimi Variant ile aynıdır; ancak C.dynamic_structure.bin dosyası eklenir
    • Bu dosya, alt sütun olarak saklanan tip listesini ve tipe göre sütun veri dosyası boyut istatistiklerini içerir
    • Bu metadata, alt sütun okuma ve veri parçası merge işlemlerinde kullanılır
  • Dynamic(max_types=N), ayrı dosya olarak saklanacak tip sayısını sınırlar
    • 0 <= N < 255
    • Varsayılan değer 32'dir
  • Sınıra ulaşıldığında kalan tip değerleri C.SharedVariant.bin gibi tek bir sütun dosyasında saklanır
    • Bu dosyanın tipi String'dir
    • Her satır <binary_encoded_data_type><binary_value> yapısında bir string değeri içerir
    • Birden fazla tipteki değer tek bir sütun dosyası içinde saklanıp tekrar okunabilir
  • Dynamic de Variant gibi, belirli tip değerlerini okumak için tip adını alt sütun olarak kullanabilir
    • Örn: C.Int64

JSON tipi bildirimi ve depolama yapısı

  • Yeni JSON tipi, keyfi yapıdaki JSON nesnelerini saklar ve her JSON değerinin yol tabanlı alt sütun olarak okunabilmesini sağlar
  • Tip bildirimi isteğe bağlı parametreler ve ipuçları içerebilir
<column_name> JSON(
    max_dynamic_paths=N,
    max_dynamic_types=M,
    some.path TypeName,
    SKIP path.to.skip,
    SKIP REGEXP 'paths_regexp')
  • max_dynamic_paths
    • Varsayılan değer 1024'tür
    • Ayrı alt sütun olarak saklanacak JSON anahtar yolu sayısını belirtir
    • Sınırı aşan yollar, özel yapılı tek bir alt sütunda birlikte saklanır
  • max_dynamic_types
    • Varsayılan değer 32'dir
    • Değer aralığı 0 ile 254 arasındadır
    • Tek bir JSON anahtar yolu sütununda ayrı sütun veri dosyası olarak saklanacak veri tipi sayısını belirtir
    • Sınırı aşan yeni tipler, özel yapılı tek bir sütun veri dosyasında birlikte saklanır
  • some.path TypeName
    • Belirli bir JSON yolu için tip ipucudur
    • Bu yol, belirtilen tipte bir alt sütun olarak her zaman saklanır ve performans garantisi sağlar
  • SKIP path.to.skip
    • Parse sırasında belirli bir JSON yolunu atlar
    • Bu yol JSON sütununa kaydedilmez
    • Belirtilen yol iç içe bir JSON nesnesiyse, iç içe nesnenin tamamı atlanır
  • SKIP REGEXP 'path_regexp'
    • Düzenli ifadeyle eşleşen yolları JSON parse işlemi sırasında atlar
    • Eşleşen yollar JSON sütununa kaydedilmez

JSON yollarını sütun gibi okuma biçimi

  • JSON sütunundaki her benzersiz leaf yol değeri diskte iki biçimden biriyle saklanır
    • Tip ipucu olan yollar normal sütun veri dosyası olarak saklanır
    • Tipi dinamik olarak değişebilen yollar Dynamic alt sütun olarak saklanır
  • JSON tipi object_structure adlı özel bir dosya kullanır
    • Dinamik yollarla ilgili metadata içerir
    • Her dinamik yolun non-null değer istatistiklerini içerir
    • Alt sütun okuma ve veri parçası merge işlemlerinde kullanılır
  • Sütun dosyası patlaması iki aşamalı sınırlamayla kontrol edilir
    • max_dynamic_types, tek bir JSON anahtar yolu içinde ayrı dosya olarak saklanacak tip sayısını sınırlar
    • max_dynamic_paths, ayrı alt sütun olarak saklanacak JSON anahtar yolu sayısını sınırlar
  • max_dynamic_paths sınırını aşan ek dinamik JSON yolları shared data olarak saklanır
    • Örnek dosyalar: C.object_shared_data.size0.bin, C.object_shared_data.paths.bin, C.object_shared_data.values.bin
    • object_shared_data.values tipi String'dir
    • Her entry <binary_encoded_data_type><binary_value> yapısına sahiptir
  • shared data için de object_structure.bin içinde ek istatistikler saklanır
    • Mevcut shared data sütununda saklanan yollar içinden ilk 10000 yol için non-null değer istatistikleri saklanır

JSON yol söz dizimi ve iç içe nesneler

  • JSON tipi, her yolun leaf değerini yol adına dayalı alt sütun olarak okuyabilir
    • Örn: C.a.b
  • Tip ipucu belirtilmeyen yolların değeri her zaman Dynamic tipindedir
    • Örn: C.a.d tipi Dynamic'tir
  • Dynamic tipinin alt tip alt sütunları özel JSON söz dizimiyle okunur
    • Örn: C.a.d.:Int64
  • İç içe JSON nesneleri JSON_column.^some.path söz dizimiyle JSON tipi alt sütun gibi okunabilir
    • Örn: C.^a
  • Mevcut nokta söz dizimi performans nedenleriyle iç içe nesneleri okumaz
    • Yol bazında literal değerleri okumak için mevcut depolama yapısı verimlidir
    • Yol bazında tüm alt nesneyi okumak daha fazla veri okumayı gerektirdiğinden yavaşlayabilir
    • Nesne döndürmek için .^ söz dizimi gerekir
    • ClickHouse iki . söz dizimini birleştirmeyi planlıyor

Compact discriminator serileştirmesi

  • Çok sayıda dinamik JSON yolunda değer tipi çoğunlukla aynı olabilir
  • Benzersiz ama seyrek JSON yolları çok olduğunda, her yolun discriminator dosyası ağırlıklı olarak 255, yani NULL değerini içerir
  • Bu tür dosyalar iyi sıkıştırılır; ancak tüm satırların değeri aynıysa yine de çok tekrar barındırır
  • ClickHouse, discriminator serileştirmesi için compact format uyguladı
    • Normalde tüm UInt8 discriminator değerlerini yazmak yerine, hedef granule içindeki discriminator'lar aynıysa yalnızca 3 değer serileştirilir
    • compact granule format göstergesi
    • ilgili granule'deki değer sayısı göstergesi
    • discriminator değeri
  • Bu optimizasyon MergeTree ayarı use_compact_variant_discriminators_serialization ile kontrol edilir
    • Varsayılan olarak etkindir
    • Normal index granularity için 8192 değer yerine yalnızca 3 değerin saklandığı durumlar olur

Sürüm durumu ve sonraki adımlar

  • Yeni JSON tipi, kullanımdan kaldırılmış Object('json') tipinin yerini almak üzere tasarlandı
  • Uygulama, ClickHouse 24.08 sürümünde test amaçlı experimental özellik olarak sunuldu
  • JSON yol haritası, JSON anahtar yollarının tablo birincil anahtarında veya data-skipping index içinde kullanılmasına yönelik iyileştirmeleri içeriyor
  • Variant ve Dynamic gibi bileşenler, JSON dışında XML, YAML gibi ek yarı yapılandırılmış tip desteğinin temelini oluşturuyor
  • Yeni JSON veri tipini test etmek isteyen ClickHouse Cloud kullanıcıları, private preview erişimi istemek için ClickHouse destek ekibiyle iletişime geçmelidir

Henüz yorum yok.

Henüz yorum yok.