Lookup field pada Dynamics 365 CRM adalah elemen UI krusial yang memungkinkan pengguna membuat referensi ke record terkait dalam sistem. Namun, bagaimana jika data yang ingin direferensikan berada di luar Dynamics 365, di sebuah sistem eksternal yang hanya bisa diakses melalui API? Tantangan ini sering muncul dalam skenario integrasi, di mana entitas seperti “Produk”, “Vendor”, atau “Proyek” mungkin dikelola di sistem lain.
Artikel ini akan memandu Anda secara teknis tentang cara mengisi lookup field Dynamics 365 dengan data yang bersumber dari API eksternal menggunakan JavaScript, memastikan integrasi yang mulus dan pengalaman pengguna yang kohesif. Kita akan membahas strategi, langkah-langkah implementasi, dan contoh kode.
Memahami Tantangan Integrasi Lookup Field dengan Data Eksternal
Secara native, lookup field Dynamics 365 dirancang untuk mereferensikan record yang sudah ada di dalam database Dynamics 365 itu sendiri. Saat Anda memilih item dari lookup, Dynamics 365 akan menyimpan GUID (Globally Unique Identifier) dari record terkait, nama record, dan tipe entitas. Format ini penting untuk koneksi data internal.
Ketika Anda ingin menampilkan data dari API eksternal, masalah utamanya adalah data tersebut tidak memiliki GUID yang valid di Dynamics 365, dan juga bukan merupakan tipe entitas yang dikenal oleh sistem secara langsung. Mencoba mengisi lookup field dengan data “mentah” dari API eksternal tanpa penanganan yang tepat akan menghasilkan referensi yang tidak valid atau bahkan error.
Strategi “Bridge Entity” untuk Integrasi Data Eksternal
Solusi paling robust dan umum untuk skenario ini adalah dengan menggunakan apa yang disebut “Bridge Entity” atau entitas perantara di dalam Dynamics 365. Bridge entity ini berfungsi sebagai proxy atau representasi lokal dari data eksternal Anda. Pendekatan ini melibatkan langkah-langkah berikut:
- Buat Entitas Kustom (Bridge Entity): Buat entitas kustom di Dynamics 365 (misalnya,
crrm_externalitem) yang akan menyimpan properti kunci dari data eksternal Anda, seperti ID eksternal unik (crrm_externalid) daama (crrm_name). - Fetch Data dari API Eksternal: Ambil data dari API eksternal saat dibutuhkan.
- Pilih dan Simpan ke Bridge Entity: Ketika pengguna memilih item dari daftar data eksternal, periksa apakah record bridge entity yang sesuai sudah ada di Dynamics 365. Jika belum, buat record baru di bridge entity tersebut, menyimpan ID dan properti relevan laiya dari data eksternal.
- Referensi Lookup Field: Setelah Anda memiliki GUID dari record bridge entity (baik yang sudah ada maupun yang baru dibuat), gunakan GUID ini untuk mengisi lookup field target.
Langkah-langkah Implementasi Teknis
1. Persiapan Lingkungan Dynamics 365
Pertama, buat bridge entity. Misal, kita membuat entitas kustom bernama “External Item” dengaama skema crrm_externalitem. Tambahkan field:
crrm_externalid(Text, harus unik) untuk menyimpan ID unik dari sistem eksternal.crrm_name(Text) sebagai nama utama (Primary Field) untuk entitas ini.
Pastikan lookup field target Anda (misalnya, pada entitas “Opportunity”) mereferensikan entitas crrm_externalitem ini.
2. Mengambil Data dari API Eksternal dengan JavaScript
Untuk mengambil data, kita akan menggunakan API fetch. Fungsi ini biasanya dipicu oleh interaksi pengguna, seperti mengetik di field teks atau mengklik tombol.
function fetchExternalData(searchTerm) {
const apiUrl = `https://your-external-api.com/items?search=${searchTerm}`;
return fetch(apiUrl)
.then(response => {
if (!response.ok) {
throw new Error(`HTTP error! Status: ${response.status}`);
}
return response.json();
})
.then(data => {
// Asumsi data adalah array objek: [{ id: "EXT1001", name: "Item A" }, ...]
return data;
})
.catch(error => {
console.error("Error fetching external data:", error);
Xrm.Navigation.openAlertDialog({ text: "Gagal mengambil data eksternal." });
return [];
});
}
3. Menampilkan Pilihan dan Interaksi Pengguna
Setelah mendapatkan data, Anda perlu menampilkaya kepada pengguna agar mereka bisa memilih. Ini bisa dilakukan dengan beberapa cara:
- Custom HTML Web Resource: Ini adalah cara paling fleksibel. Anda bisa membuat UI kustom (tabel, daftar, tombol) di dalam Web Resource dan menempatkaya di form Dynamics 365.
- Dialog (Xrm.Navigation.openAlertDialog/openConfirmDialog): Meskipun terbatas, Anda bisa menggunakaya untuk menampilkan pilihan sederhana.
- Temporary Text Field + AutoSuggest (lebih kompleks): Gunakan field teks dan populate opsi saat user mengetik.
Untuk contoh ini, kita asumsikan Anda memiliki mekanisme di mana setelah pengguna memilih item (misalnya, { externalId: "EXT1001", externalName: "Item A" }), fungsi berikutnya akan dipanggil.
4. Membuat atau Memperbarui Record Bridge Entity di Dynamics 365
Ini adalah langkah krusial. Kita perlu berinteraksi dengan Web API Dynamics 365 untuk mencari, membuat, atau memperbarui record crrm_externalitem.
async function getOrCreateExternalItem(externalId, externalName) {
const entityLogicalName = "crrm_externalitem";
const primaryFieldName = "crrm_name"; // Field Primary Name
const externalIdFieldName = "crrm_externalid"; // Field External ID try {
// Cek apakah record sudah ada berdasarkan crrm_externalid
const filter = `?$filter=${externalIdFieldName} eq '${externalId}'&$select=${primaryFieldName},${externalIdFieldName}`;
const existingRecords = await Xrm.WebApi.retrieveMultipleRecords(entityLogicalName, filter);
if (existingRecords.entities.length > 0) {
// Record sudah ada, kembalikan GUID-nya
return existingRecords.entities[0];
} else {
// Record belum ada, buat yang baru
const data = {};
data[externalIdFieldName] = externalId;
data[primaryFieldName] = externalName; // Set nama utama
const newRecord = await Xrm.WebApi.createRecord(entityLogicalName, data);
returewRecord; // newRecord akan berisi id (GUID) dari record yang baru dibuat
}
} catch (error) {
console.error("Error getting or creating external item:", error);
Xrm.Navigation.openAlertDialog({ text: "Gagal memproses item eksternal di Dynamics 365." });
throw error;
}
}
5. Mengisi Lookup Field Target
Setelah Anda mendapatkan objek externalItemRecord (yang berisi id dan crrm_name) dari langkah sebelumnya, Anda dapat menggunakaya untuk mengisi lookup field target.
function setLookupField(formContext, lookupFieldName, recordGuid, recordName, entityLogicalName) {
const lookupValue = [
{
id: recordGuid,
name: recordName,
entityType: entityLogicalName
}
];
formContext.getAttribute(lookupFieldName).setValue(lookupValue);
formContext.getAttribute(lookupFieldName).fireOnChange(); // Opsional: memicu event OnChange
}
Contoh Kode Praktis (Integrasi Keseluruhan)
Berikut adalah contoh bagaimana semua fungsi dapat disatukan dalam satu alur kerja:
// Fungsi ini akan dipanggil misalnya dari tombol kustom atau event text field
async function handleExternalItemSelection(formContext, selectedExternalItem) {
const targetLookupFieldName = "crrm_externalitemlookupfield"; // Ganti dengan schema name lookup Anda
const externalItemEntityLogicalName = "crrm_externalitem"; try {
// 1. Dapatkan atau buat record bridge entity di D365
const d365ExternalItem = await getOrCreateExternalItem(
selectedExternalItem.externalId,
selectedExternalItem.externalName
);
// 2. Isi lookup field dengan data dari record bridge entity D365
if (d365ExternalItem && d365ExternalItem.id) {
setLookupField(
formContext,
targetLookupFieldName,
d365ExternalItem.id,
d365ExternalItem["crrm_name"], // Mengakses nama primary field
externalItemEntityLogicalName
);
Xrm.Utility.showProgressIndicator("Lookup berhasil diperbarui.");
setTimeout(() => Xrm.Utility.closeProgressIndicator(), 2000);
} else {
Xrm.Navigation.openAlertDialog({ text: "Gagal mendapatkan referensi item eksternal." });
}
} catch (error) {
console.error("Kesalahan dalam proses pemilihan item eksternal:", error);
Xrm.Navigation.openAlertDialog({ text: "Terjadi kesalahan saat memproses item eksternal." });
}
}
// Contoh penggunaan (misalnya, setelah fetchExternalData dan user memilih):
// const formContext = executionContext.getFormContext();
// const selectedItemFromApi = { externalId: "EXT12345", externalName: "Produk X dari API" };
// handleExternalItemSelection(formContext, selectedItemFromApi);
Pertimbangan UX dan Penanganan Kesalahan
- Indikator Loading: Gunakan
Xrm.Utility.showProgressIndicator()saat melakukan panggilan API atau Web API untuk memberi tahu pengguna bahwa proses sedang berjalan. - Validasi Input: Pastikan Anda memvalidasi input dari API eksternal dan dari pengguna.
- Pesan Kesalahan yang Jelas: Tangani error dengan elegan dan berikan pesan yang informatif kepada pengguna menggunakan
Xrm.Navigation.openAlertDialog(). - Debouncing (untuk pencarian): Jika Anda menggunakan pencarian berbasis teks, terapkan debouncing untuk menghindari panggilan API yang berlebihan saat pengguna mengetik.
Kesimpulan
Mengisi lookup field Dynamics 365 dengan data dari API eksternal adalah skenario integrasi yang kuat, dan dengan strategi “Bridge Entity” yang dijelaskan di atas, Anda dapat mencapainya dengan efisien dan andal. Pendekatan ini memastikan bahwa data eksternal Anda terwakili dengan baik di Dynamics 365, memungkinkan referensi lookup yang valid dan pengalaman pengguna yang mulus. Dengan menguasai teknik-teknik JavaScript dan Web API Dynamics 365, Anda dapat memperluas kapabilitas CRM Anda secara signifikan.