Bagikan melalui


Memetakan data dengan menggunakan aliran data

Penting

Pratinjau Operasi Azure IoT – diaktifkan oleh Azure Arc saat ini dalam pratinjau. Anda tidak boleh menggunakan perangkat lunak pratinjau ini di lingkungan produksi.

Anda harus menyebarkan penginstalan Azure IoT Operations baru saat rilis yang tersedia secara umum tersedia. Anda tidak akan dapat memutakhirkan penginstalan pratinjau.

Untuk persyaratan hukum yang berlaku untuk fitur Azure yang beta, dalam pratinjau, atau belum dirilis ke ketersediaan umum, lihat Ketentuan Penggunaan Tambahan untuk Pratinjau Microsoft Azure.

Gunakan bahasa pemetaan aliran data untuk mengubah data di Operasi Azure IoT. Sintaksnya adalah cara sederhana, namun kuat, untuk menentukan pemetaan yang mengubah data dari satu format ke format lainnya. Artikel ini memberikan gambaran umum tentang bahasa pemetaan aliran data dan konsep utama.

Pemetaan memungkinkan Anda mengubah data dari satu format ke format lainnya. Pertimbangkan catatan input berikut:

{
  "Name": "Grace Owens",
  "Place of birth": "London, TX",
  "Birth Date": "19840202",
  "Start Date": "20180812",
  "Position": "Analyst",
  "Office": "Kent, WA"
}

Bandingkan dengan rekaman output:

{
  "Employee": {
    "Name": "Grace Owens",
    "Date of Birth": "19840202"
  },
  "Employment": {
    "Start Date": "20180812",
    "Position": "Analyst, Kent, WA",
    "Base Salary": 78000
  }
}

Dalam catatan output, perubahan berikut dilakukan pada data rekaman input:

  • Bidang diganti namanya: Bidang Birth Date sekarang Date of Birth.
  • Bidang direstrukturisasi: Keduanya Name dan Date of Birth dikelompokkan di bawah kategori baru Employee .
  • Bidang dihapus: Bidang Place of birth dihapus karena tidak ada dalam output.
  • Bidang ditambahkan: Bidang Base Salary adalah bidang baru dalam Employment kategori.
  • Nilai bidang diubah atau digabungkan: Bidang Position dalam output menggabungkan Position bidang dan Office dari input.

Transformasi dicapai melalui pemetaan, yang biasanya melibatkan:

  • Definisi input: Mengidentifikasi bidang dalam rekaman input yang digunakan.
  • Definisi output: Menentukan di mana dan bagaimana bidang input diatur dalam rekaman output.
  • Konversi (opsional): Memodifikasi bidang input agar pas dengan bidang output. expression diperlukan ketika beberapa bidang input digabungkan ke dalam satu bidang output.

Pemetaan berikut adalah contoh:

{
  inputs: [
    'BirthDate'
  ]
  output: 'Employee.DateOfBirth'
}
{
  inputs: [
    'Position'  // - - - - $1
    'Office'    // - - - - $2
  ]
  output: 'Employment.Position'
  expression: '$1 + ", " + $2'
}
{
  inputs: [
    '$context(position).BaseSalary'
  ]
  output: 'Employment.BaseSalary'
}

Contoh peta:

  • Pemetaan satu-ke-satu: BirthDate langsung dipetakan tanpa Employee.DateOfBirth konversi.
  • Pemetaan banyak ke satu: Menggabungkan Position dan Office ke dalam satu Employment.Position bidang. Rumus konversi ($1 + ", " + $2) menggabungkan bidang ini ke dalam string yang diformat.
  • Data kontekstual: BaseSalary ditambahkan dari himpunan data kontekstual bernama position.

Referensi bidang

Referensi bidang menunjukkan cara menentukan jalur dalam input dan output dengan menggunakan notasi titik seperti Employee.DateOfBirth atau mengakses data dari himpunan data kontekstual melalui $context(position).

Properti pengguna MQTT

Saat Anda menggunakan MQTT sebagai sumber atau tujuan, Anda dapat mengakses properti pengguna MQTT dalam bahasa pemetaan. Properti pengguna dapat dipetakan dalam input atau output.

Dalam contoh berikut, properti MQTT topic dipetakan ke origin_topic bidang dalam output.

inputs: [
  '$metadata.topic'
]
output: 'origin_topic'

Anda juga dapat memetakan properti MQTT ke header output. Dalam contoh berikut, MQTT topic dipetakan ke origin_topic bidang di properti pengguna output:

inputs: [
  '$metadata.topic'
]
output: '$metadata.user_property.origin_topic'

Pemilih himpunan data kontekstualisasi

Pemilih ini memungkinkan pemetaan untuk mengintegrasikan data tambahan dari database eksternal, yang disebut sebagai himpunan data kontekstualisasi.

Pemfilteran rekaman

Pemfilteran rekaman melibatkan kondisi pengaturan untuk memilih rekaman mana yang harus diproses atau dihilangkan.

Notasi titik

Notasi titik banyak digunakan dalam ilmu komputer untuk mereferensikan bidang, bahkan secara rekursif. Dalam pemrograman, nama bidang biasanya terdiri dari huruf dan angka. Sampel notasi titik standar mungkin terlihat seperti contoh ini:

inputs: [
  'Person.Address.Street.Number'
]

Dalam aliran data, jalur yang dijelaskan oleh notasi titik mungkin menyertakan string dan beberapa karakter khusus tanpa perlu melarikan diri:

inputs: [
  'Person.Date of Birth'
]

Dalam kasus lain, pelepasan diperlukan:

inputs: [
  'Person."Tag.10".Value'
]

Contoh sebelumnya, di antara karakter khusus lainnya, berisi titik-titik dalam nama bidang. Tanpa melarikan diri, nama bidang akan berfungsi sebagai pemisah dalam notasi titik itu sendiri.

Meskipun aliran data menguraikan jalur, aliran data hanya memperlakukan dua karakter sebagai khusus:

  • Titik (.) bertindak sebagai pemisah bidang.
  • Tanda kutip tunggal, saat ditempatkan di awal atau akhir segmen, mulai bagian yang lolos di mana titik tidak diperlakukan sebagai pemisah bidang.

Karakter lain diperlakukan sebagai bagian dari nama bidang. Fleksibilitas ini berguna dalam format seperti JSON, di mana nama bidang dapat berupa string arbitrer.

Di Bicep, semua string diapit dalam tanda kutip tunggal ('). Contoh tentang pengutipan yang tepat dalam YAML untuk penggunaan Kubernetes tidak berlaku.

Melarikan diri

Fungsi utama untuk melarikan diri dalam jalur yang diberi notasi titik adalah untuk mengakomodasi penggunaan titik-titik yang merupakan bagian dari nama bidang daripada pemisah:

inputs: [
  'Payload."Tag.10".Value'
]

Dalam contoh ini, jalur terdiri dari tiga segmen: Payload, , Tag.10dan Value.

Aturan pelepasan dalam notasi titik

  • Keluar dari setiap segmen secara terpisah: Jika beberapa segmen berisi titik-titik, segmen tersebut harus diapit dalam tanda kutip ganda. Segmen lain juga dapat dikutip, tetapi tidak memengaruhi interpretasi jalur:

    inputs: [
      'Payload."Tag.10".Measurements."Vibration.$12".Value'
    ]
    

  • Penggunaan tanda kutip ganda yang tepat: Tanda kutip ganda harus membuka dan menutup segmen yang lolos. Tanda kutip apa pun di tengah segmen dianggap sebagai bagian dari nama bidang:

    inputs: [
      'Payload.He said: "Hello", and waved'
    ]
    

Contoh ini mendefinisikan dua bidang: Payload dan He said: "Hello", and waved. Ketika titik muncul dalam keadaan ini, titik terus berfungsi sebagai pemisah:

inputs: [
  'Payload.He said: "No. It is done"'
]

Dalam hal ini, jalur dibagi menjadi segmen Payload, , He said: "Nodan It is done" (dimulai dengan spasi).

Algoritma segmentasi

  • Jika karakter pertama segmen adalah tanda kutip, pengurai mencari tanda kutip berikutnya. String yang diapit di antara tanda kutip ini dianggap sebagai segmen tunggal.
  • Jika segmen tidak dimulai dengan tanda kutip, pengurai mengidentifikasi segmen dengan mencari titik berikutnya atau akhir jalur.

Kartubebas

Dalam banyak skenario, rekaman output sangat menyerupai rekaman input, dengan hanya modifikasi kecil yang diperlukan. Saat Anda berurusan dengan rekaman yang berisi banyak bidang, menentukan pemetaan secara manual untuk setiap bidang bisa menjadi melelahkan. Wildcard menyederhanakan proses ini dengan memungkinkan pemetaan umum yang dapat diterapkan secara otomatis ke beberapa bidang.

Mari kita pertimbangkan skenario dasar untuk memahami penggunaan tanda bintang dalam pemetaan:

inputs: [
  '*'
]
output: '*'

Berikut adalah cara tanda bintang (*) beroperasi dalam konteks ini:

  • Pencocokan pola: Tanda bintang dapat cocok dengan satu segmen atau beberapa segmen jalur. Ini berfungsi sebagai tempat penampung untuk segmen apa pun di jalur.
  • Pencocokan bidang: Selama proses pemetaan, algoritma mengevaluasi setiap bidang dalam rekaman input terhadap pola yang ditentukan dalam inputs. Tanda bintang dalam contoh sebelumnya cocok dengan semua jalur yang mungkin, secara efektif pas dengan setiap bidang individu dalam input.
  • Segmen yang diambil: Bagian jalur yang cocok dengan tanda bintang disebut sebagai captured segment.
  • Pemetaan output: Dalam konfigurasi output, captured segment ditempatkan di mana tanda bintang muncul. Ini berarti bahwa struktur input dipertahankan dalam output, dengan captured segment mengisi tempat penampung yang disediakan oleh tanda bintang.

Konfigurasi ini menunjukkan bentuk pemetaan yang paling umum, di mana setiap bidang dalam input langsung dipetakan ke bidang yang sesuai dalam output tanpa modifikasi.

Contoh lain menggambarkan bagaimana kartubebas dapat digunakan untuk mencocokkan subbagian dan memindahkannya bersama-sama. Contoh ini secara efektif meratakan struktur berlapis dalam objek JSON.

JSON asli:

{
  "ColorProperties": {
    "Hue": "blue",
    "Saturation": "90%",
    "Brightness": "50%",
    "Opacity": "0.8"
  },
  "TextureProperties": {
    "type": "fabric",
    "SurfaceFeel": "soft",
    "SurfaceAppearance": "matte",
    "Pattern": "knitted"
  }
}

Konfigurasi pemetaan yang menggunakan wildcard:

{
  inputs: [
    'ColorProperties.*'
  ]
  output: '*'
}
{
  inputs: [
    'TextureProperties.*'
  ]
  output: '*'
}

Hasil JSON:

{
  "Hue": "blue",
  "Saturation": "90%",
  "Brightness": "50%",
  "Opacity": "0.8",
  "type": "fabric",
  "SurfaceFeel": "soft",
  "SurfaceAppearance": "matte",
  "Pattern": "knitted"
}

Penempatan kartubebas

Saat Anda menempatkan kartubebas, Anda harus mengikuti aturan ini:

  • Tanda bintang tunggal per dataDestination: Hanya satu tanda bintang (*) yang diizinkan dalam satu jalur.
  • Pencocokan segmen penuh: Tanda bintang harus selalu cocok dengan seluruh segmen jalur. Ini tidak dapat digunakan untuk mencocokkan hanya sebagian dari segmen, seperti path1.partial*.path3.
  • Posisi: Tanda bintang dapat diposisikan di berbagai bagian dari dataDestination:
    • Di awal: *.path2.path3 - Di sini, tanda bintang cocok dengan segmen apa pun yang mengarah ke path2.path3.
    • Di tengah: path1.*.path3 - Dalam konfigurasi ini, tanda bintang cocok dengan segmen apa pun antara path1 dan path3.
    • Di akhir: path1.path2.* - Tanda bintang di akhir cocok dengan segmen apa pun yang mengikuti setelah path1.path2.
  • Jalur yang berisi tanda bintang harus diapit dalam tanda kutip tunggal (').

Kartubebas multi-input

JSON asli:

{
  "Saturation": {
    "Max": 0.42,
    "Min": 0.67,
  },
  "Brightness": {
    "Max": 0.78,
    "Min": 0.93,
  },
  "Opacity": {
    "Max": 0.88,
    "Min": 0.91,
  }
}

Konfigurasi pemetaan yang menggunakan wildcard:

inputs: [
  '*.Max'  // - $1
  '*.Min'  // - $2
]
output: 'ColorProperties.*'
expression: '($1 + $2) / 2'

Hasil JSON:

{
  "ColorProperties" : {
    "Saturation": 0.54,
    "Brightness": 0.85,
    "Opacity": 0.89 
  }    
}

Jika Anda menggunakan wildcard multi-input, tanda bintang (*) harus secara konsisten mewakili hal yang sama Captured Segment di setiap input. Misalnya, ketika * mengambil dalam pola *.Max, algoritma pemetaan mengharapkan yang sesuai untuk dicocokkan Saturation.Min dengan pola *.MinSaturation . Di sini, * digantikan oleh Captured Segment dari input pertama, memandu pencocokan untuk input berikutnya.

Pertimbangkan contoh terperinci ini:

JSON asli:

{
  "Saturation": {
    "Max": 0.42,
    "Min": 0.67,
    "Mid": {
      "Avg": 0.51,
      "Mean": 0.56
    }
  },
  "Brightness": {
    "Max": 0.78,
    "Min": 0.93,
    "Mid": {
      "Avg": 0.81,
      "Mean": 0.82
    }
  },
  "Opacity": {
    "Max": 0.88,
    "Min": 0.91,
    "Mid": {
      "Avg": 0.89,
      "Mean": 0.89
    }
  }
}

Konfigurasi pemetaan awal yang menggunakan wildcard:

inputs: [
  '*.Max'    // - $1
  '*.Min'    // - $2
  '*.Avg'    // - $3
  '*.Mean'   // - $4
]

Pemetaan awal ini mencoba membangun array (misalnya, untuk Opacity: [0.88, 0.91, 0.89, 0.89]). Konfigurasi ini gagal karena:

  • Input *.Max pertama menangkap segmen seperti Saturation.
  • Pemetaan mengharapkan input berikutnya hadir pada tingkat yang sama:
    • Saturation.Max
    • Saturation.Min
    • Saturation.Avg
    • Saturation.Mean

Karena Avg dan Mean ditumpuk dalam Mid, tanda bintang dalam pemetaan awal tidak menangkap jalur ini dengan benar.

Konfigurasi pemetaan yang dikoreksi:

inputs: [
  '*.Max'        // - $1
  '*.Min'        // - $2
  '*.Mid.Avg'    // - $3
  '*.Mid.Mean'   // - $4
]

Pemetaan yang direvisi ini secara akurat menangkap bidang yang diperlukan. Ini menentukan jalur dengan benar untuk menyertakan objek berlapis Mid , yang memastikan bahwa tanda bintang bekerja secara efektif di berbagai tingkat struktur JSON.

Aturan kedua vs. spesialisasi

Saat Anda menggunakan contoh sebelumnya dari wildcard multi-input, pertimbangkan pemetaan berikut yang menghasilkan dua nilai turunan untuk setiap properti:

{
  inputs: [
    '*.Max'   // - $1
    '*.Min'   // - $2
  ]
  output: 'ColorProperties.*.Avg'
  expression: '($1 + $2) / 2'
}
{
  inputs: [
    '*.Max'   // - $1
    '*.Min'   // - $2
  ]
  output: 'ColorProperties.*.Diff'
  expression: 'abs($1 - $2)'
}

Pemetaan ini dimaksudkan untuk membuat dua perhitungan terpisah (Avg dan Diff) untuk setiap properti di bawah ColorProperties. Contoh ini menunjukkan hasilnya:

{
  "ColorProperties": {
    "Saturation": {
      "Avg": 0.54,
      "Diff": 0.25
    },
    "Brightness": {
      "Avg": 0.85,
      "Diff": 0.15
    },
    "Opacity": {
      "Avg": 0.89,
      "Diff": 0.03
    }
  }
}

Di sini, definisi pemetaan kedua pada input yang sama bertindak sebagai aturan kedua untuk pemetaan.

Sekarang, pertimbangkan skenario di mana bidang tertentu memerlukan perhitungan yang berbeda:

{
  inputs: [
    '*.Max'   // - $1
    '*.Min'   // - $2
  ]
  output: 'ColorProperties.*'
  expression: '($1 + $2) / 2'
}
{
  inputs: [
    'Opacity.Max'   // - $1
    'Opacity.Min'   // - $2
  ]
  output: 'ColorProperties.OpacityAdjusted'
  expression: '($1 + $2 + 1.32) / 2'
}

Dalam hal ini, Opacity bidang memiliki perhitungan unik. Dua opsi untuk menangani skenario yang tumpang tindih ini adalah:

  • Sertakan kedua pemetaan untuk Opacity. Karena bidang output berbeda dalam contoh ini, bidang tersebut tidak akan saling menimpa.
  • Gunakan aturan yang lebih spesifik untuk Opacity dan hapus aturan yang lebih umum.

Pertimbangkan kasus khusus untuk bidang yang sama untuk membantu memutuskan tindakan yang tepat:

{
  inputs: [
    '*.Max'   // - $1
    '*.Min'   // - $2
  ]
  output: 'ColorProperties.*'
  expression: '($1 + $2) / 2'
}
{
  inputs: [
    'Opacity.Max'   // - $1
    'Opacity.Min'   // - $2
  ]
}

Bidang kosong output dalam definisi kedua menyiratkan tidak menulis bidang dalam rekaman output (secara efektif menghapus Opacity). Penyiapan ini lebih dari satu Specialization dari .Second Rule

Resolusi pemetaan yang tumpang tindih menurut aliran data:

  • Evaluasi berlangsung dari aturan teratas dalam definisi pemetaan.
  • Jika pemetaan baru diselesaikan ke bidang yang sama dengan aturan sebelumnya, kondisi berikut berlaku:
    • Rank dihitung untuk setiap input yang diselesaikan berdasarkan jumlah segmen yang diambil kartubebas. Misalnya, jika Captured Segments adalah Properties.Opacity, Rank adalah 2. Jika hanya Opacity, Rank adalah 1. Pemetaan tanpa kartubebas memiliki Rank 0.
    • Rank Jika aturan terakhir sama dengan atau lebih tinggi dari aturan sebelumnya, aliran data memperlakukannya sebagai Second Rule.
    • Jika tidak, aliran data memperlakukan konfigurasi sebagai Specialization.

Misalnya, pemetaan yang mengarahkan Opacity.Max dan Opacity.Min ke output kosong memiliki Rank 0. Karena aturan kedua memiliki yang lebih rendah Rank dari yang sebelumnya, aturan tersebut dianggap sebagai spesialisasi dan mengambil alih aturan sebelumnya, yang akan menghitung nilai untuk Opacity.

Kartubebas dalam himpunan data kontekstualisasi

Sekarang, mari kita lihat bagaimana himpunan data kontekstualisasi dapat digunakan dengan kartubebas melalui contoh. Pertimbangkan himpunan data bernama position yang berisi catatan berikut:

{
  "Position": "Analyst",
  "BaseSalary": 70000,
  "WorkingHours": "Regular"
}

Dalam contoh sebelumnya, kami menggunakan bidang tertentu dari himpunan data ini:

inputs: [
  '$context(position).BaseSalary'
]
output: 'Employment.BaseSalary'

Pemetaan ini menyalin BaseSalary dari himpunan data konteks langsung ke bagian Employment rekaman output. Jika Anda ingin mengotomatiskan proses dan menyertakan semua bidang dari himpunan position data ke dalam Employment bagian , Anda dapat menggunakan kartubebas:

inputs: [
  '$context(position).*'
]
output: 'Employment.*'

Konfigurasi ini memungkinkan pemetaan dinamis di mana setiap bidang dalam himpunan position data disalin ke bagian Employment rekaman output:

{
    "Employment": {      
      "Position": "Analyst",
      "BaseSalary": 70000,
      "WorkingHours": "Regular"
    }
}

Nilai terakhir diketahui

Anda dapat melacak nilai properti terakhir yang diketahui. Akhiri bidang input dengan ? $last untuk mengambil nilai bidang terakhir yang diketahui. Ketika properti kehilangan nilai dalam payload input berikutnya, nilai terakhir yang diketahui dipetakan ke payload output.

Misalnya, pertimbangkan pemetaan berikut:

inputs: [
  'Temperature ? $last'
]
output: 'Thermostat.Temperature'

Dalam contoh ini, nilai terakhir yang Temperature diketahui dilacak. Jika payload input berikutnya tidak berisi Temperature nilai, nilai terakhir yang diketahui digunakan dalam output.