Audit profil bisnis suatu usaha dengan listings scan

Cek bisnis mana pun di peta, mesin pencari, direktori, asisten AI; akurasi nama/alamat/telepon per direktori; hasil via webhook atau polling.

listings scan memeriksa profil bisnis suatu bisnis di seluruh jaringan direktori listingsAPI dan memberi tahu Anda, untuk setiap direktori, apakah bisnis tersebut ditemukan dan apakah nama, alamat, serta nomor teleponnya cocok dengan data yang Anda berikan. Bisnis tersebut tidak harus menjadi lokasi di akun Anda. Panduan ini menjelaskan cara membuat pemindaian, menunggu hingga selesai, dan membaca hasilnya.

Gunakan untuk:

  • mengaudit calon klien sebelum Anda mendaftarkannya, agar percakapan pertama dimulai dengan membahas profil bisnis yang belum ada atau keliru;
  • memeriksa keberadaan profil bisnis klien dan konsistensi NAP (nama, alamat, nomor telepon) sebelum dan sesudah Anda memperbaiki profil bisnisnya;
  • memberi agen AI cara untuk menjawab "bagaimana bisnis ini tercantum di berbagai direktori?" tanpa menambahkan bisnis tersebut ke akun.

1. Buat pemindaian

POST /listings/scans menerima data bisnis sebagai satu objek input dan segera mengembalikan pemindaian dengan status QUEUED. Direktori diperiksa di latar belakang.

FieldWajibCatatan
nameYaMaksimal 150 karakter.
streetYaMaksimal 200 karakter.
cityYaMaksimal 100 karakter.
stateIsoYa, kecuali GBKode negara bagian atau provinsi, maksimal 50 karakter.
postalCodeYa, kecuali NG dan AEMaksimal 20 karakter.
countryIsoYaKode ISO 3166-1 dua huruf, misalnya US.
phoneYa6 hingga 15 digit. Format lokal ditafsirkan berdasarkan countryIso, dan awalan + juga dapat digunakan.
Create a scan
curl -X POST https://listingsapi.com/api/v4/listings/scans \-H "Authorization: API $LISTINGSAPI_KEY" \-H "Content-Type: application/json" \-d @- <<'JSON'{"input": {  "name": "Joe's Pizza",  "street": "7 Carmine Street",  "city": "New York",  "stateIso": "NY",  "postalCode": "10014",  "countryIso": "US",  "phone": "2123661182"}}JSON

Respons mengembalikan pemindaian, dengan phone yang telah dinormalisasi ke format internasional. results kosong hingga direktori diperiksa, jadi simpan id.

JSON
{  "data": {    "createListingScan": {      "reused": false,      "scan": {        "id": "TGlzdGluZ1NjYW46Mzk0YTRhNWMtZjcwMy00NjZiLTg2NjAtMDU4MTlmNDhkZjMz",        "status": "QUEUED",        "source": "DIRECTORY_SEARCH",        "locationId": null,        "resultsAsOf": null,        "createdAt": "2026-11-05T07:01:08Z",        "startedAt": null,        "completedAt": null,        "business": {          "name": "Joe's Pizza",          "street": "7 Carmine Street",          "city": "New York",          "stateIso": "NY",          "postalCode": "10014",          "countryIso": "US",          "phone": "+12123661182"        },        "summary": {          "total": 0,          "found": 0,          "accurate": 0,          "inaccurate": 0,          "notFound": 0,          "pending": 0,          "unavailable": 0        },        "failure": null,        "results": []      },      "errors": []    }  }}

Respons juga menyertakan objek quota, yang dibahas dalam Biaya, batas, dan kesalahan.

Dua hal yang perlu diperiksa sebelum melanjutkan:

  • reused. Saat Anda meminta pemindaian untuk bisnis yang telah Anda pindai dalam 7 hari terakhir, listingsAPI mengembalikan pemindaian tersebut alih-alih memulai pemindaian baru, beserta reused: true dan statusnya saat ini, biasanya COMPLETED. Kuota Anda tidak berkurang, dan tidak ada webhook baru yang dikirim untuk pemindaian tersebut.
  • errors. Permintaan yang ditolak tetap menerima respons HTTP 200. Penolakan tercantum dalam data.createListingScan.errors, dan scan bernilai null. Nomor telepon yang terlalu pendek menghasilkan respons seperti ini:
JSON
{  "data": {    "createListingScan": {      "reused": false,      "scan": null,      "errors": [        {          "code": "SY83003",          "message": "SY83003: Invalid value for phone",          "contextInfo": [            {              "key": "field",              "value": "phone"            }          ]        }      ]    }  }}

contextInfo menyebutkan nama field yang gagal. Kode lain yang dapat Anda terima tercantum dalam tabel kesalahan.

2. Tunggu hasilnya

Pemindaian beralih dari QUEUED ke IN_PROGRESS lalu ke COMPLETED atau FAILED. Sebagian besar selesai dalam 1 hingga 7 menit. Jika suatu direktori belum merespons setelah sekitar 15 menit, hasilnya ditetapkan menjadi UNAVAILABLE dan pemindaian diselesaikan dengan hasil dari direktori lainnya. Gunakan webhook jika memungkinkan, dan lakukan polling hanya sebagai alternatif cadangan.

Saat pemindaian mencapai status akhir, listingsAPI mengirim satu peristiwa listing_scan.completed atau listing_scan.failed ke URL webhook Anda. data.scan pada peristiwa tersebut adalah objek yang sama dengan yang dikembalikan oleh GET, termasuk hasilnya, sehingga tidak ada data yang perlu diambil setelahnya.

JSON
{  "event": "listing_scan.completed",  "timestamp": "2026-11-05T07:01:52Z",  "account_id": 12345,  "data": {    "scan": {      "id": "TGlzdGluZ1NjYW46Mzk0YTRhNWMtZjcwMy00NjZiLTg2NjAtMDU4MTlmNDhkZjMz",      "status": "COMPLETED",      "summary": { "total": 62, "found": 21, "accurate": 18, "inaccurate": 2, "notFound": 41, "pending": 0, "unavailable": 0 },      "results": [ "..." ]    }  }}

Payload dipersingkat di sini; contoh lengkapnya ada di referensi peristiwa. Peristiwa ditandatangani dan dikirim seperti peristiwa lainnya, dengan satu upaya pengiriman dan batas waktu 5 detik, jadi verifikasi tanda tangan, simpan isi mentah permintaan, dan kirim konfirmasi penerimaan sebelum melakukan hal lain. Penerima dalam Merespons peristiwa dengan webhook sudah melakukan hal ini; satu-satunya perubahan adalah penambahan satu cabang pada event.

One more branch in your receiver
# After the signature check and the endpoint.verification branch:if body.get("event") in ("listing_scan.completed", "listing_scan.failed"):  inbox.put(raw)  # commit before the 200; read data.scan from the queue  return {"received": True}, 200

Peristiwa hanya dikirim ke akun yang webhook-nya diaktifkan dan memiliki URL terverifikasi. Jika akun Anda tidak memenuhi ketentuan tersebut, atau jika suatu peristiwa tidak pernah tiba, lakukan polling terhadap pemindaian; pemindaian tetap disimpan selama 90 hari dalam kedua keadaan tersebut. Detail penandatanganan tersedia dalam Tanda tangan dan verifikasi.

2b. Gunakan polling sebagai alternatif

GET /listings/scans/{scanId} mengembalikan pemindaian beserta hasil yang sudah tersedia. Selama pemindaian berjalan, results terisi saat direktori memberikan respons dan summary.pending menghitung direktori yang masih menunggu respons. Lakukan polling setiap 15 detik dan jangan lebih sering; setiap permintaan diperhitungkan dalam batas laju Anda.

Poll until the scan finishes
SCAN_ID="TGlzdGluZ1NjYW46Mzk0YTRhNWMtZjcwMy00NjZiLTg2NjAtMDU4MTlmNDhkZjMz" while true; doscan=$(curl -s "https://listingsapi.com/api/v4/listings/scans/$SCAN_ID" \  -H "Authorization: API $LISTINGSAPI_KEY")status=$(echo "$scan" | jq -r '.data.listingScan.status')echo "status: $status"case "$status" in  COMPLETED|FAILED)    echo "$scan" | jq '.data.listingScan | {status, summary, failure}'    break ;;  null)    echo "$scan"    break ;;esacsleep 15done
statusArti
QUEUEDDiterima dan menunggu untuk dimulai.
IN_PROGRESSDirektori sedang diperiksa. results berisi hasil sementara.
COMPLETEDSemua direktori sudah memiliki hasil. results dan summary sudah final.
FAILEDPemindaian tidak dapat dimulai, misalnya karena layanan sementara tidak tersedia (SY83010). failure berisi code dan message, dan results kosong. Pemindaian yang gagal tidak mengurangi kuota Anda, sehingga Anda dapat membuatnya kembali.

Pemindaian yang hasilnya diambil dari pemindaian terbaru atau dari salah satu lokasi Anda sendiri langsung berstatus COMPLETED saat dibuat, sehingga satu GET sudah cukup.

3. Baca hasilnya

Pemindaian yang selesai memiliki summary dan satu entri dalam results untuk setiap direktori yang diperiksa, hingga sekitar 60 direktori tergantung negaranya. business mengembalikan input yang Anda kirim, dengan phone yang telah dinormalisasi ke format internasional.

JSON
{  "total": 62,  "found": 21,  "accurate": 18,  "inaccurate": 2,  "notFound": 41,  "pending": 0,  "unavailable": 0}

total adalah jumlah direktori. found adalah jumlah direktori yang mencantumkan bisnis tersebut, dan terbagi menjadi accurate, inaccurate, serta profil bisnis yang hanya mengonfirmasi keberadaan bisnis sebagaimana dijelaskan di bawah. notFound adalah jumlah direktori yang tidak mencantumkannya. unavailable menghitung direktori yang tidak dapat diperiksa kali ini, dan pending hanya bernilai selain nol selama pemindaian berjalan.

Setiap hasil memiliki status untuk direktori tersebut:

status hasilArti
FOUNDDirektori mencantumkan bisnis tersebut. listing berisi informasi yang ditampilkan direktori.
NOT_FOUNDDirektori sudah diperiksa dan bisnis tersebut tidak tercantum di sana.
UNAVAILABLEDirektori tidak dapat diperiksa kali ini. Ini tidak sama dengan tidak tercantum, jadi jangan laporkan sebagai kekurangan cakupan. Periksa kembali direktori tersebut nanti.
PENDINGBelum diperiksa. Hanya muncul selama pemindaian berjalan.

Untuk hasil FOUND, accurate menunjukkan apakah profil bisnis cocok dengan input Anda:

  • true berarti nama, alamat, dan nomor telepon semuanya cocok.
  • false berarti setidaknya salah satunya tidak cocok. Kolom yang tidak dicantumkan dalam profil bisnis dianggap tidak cocok, sehingga profil bisnis tanpa nomor telepon berstatus false.
  • null berarti bisnis ditemukan, tetapi tidak ada pemeriksaan per kolom.

accuracy menjelaskan hasil penilaian dengan status dan message untuk masing-masing name, address, dan phone. Nilai status adalah ACCURATE, INACCURATE, atau MISSING, dan message bernilai null jika kolom tersebut akurat. Berikut adalah halaman Facebook dengan nama dan alamat yang cocok, tetapi tanpa nomor telepon:

JSON
{  "directory": {    "id": 184,    "name": "Facebook",    "url": "facebook.com"  },  "status": "FOUND",  "accurate": false,  "accuracySource": "DIRECTORY_MATCH",  "accuracy": {    "name": {      "status": "ACCURATE",      "message": null    },    "address": {      "status": "ACCURATE",      "message": null    },    "phone": {      "status": "MISSING",      "message": "No phone number on the listing"    }  },  "listing": {    "name": "Joe's Pizza",    "street": "7 Carmine St",    "city": "New York",    "state": "NY",    "postalCode": "10014",    "country": "US",    "fullAddress": "7 Carmine St, New York, NY 10014",    "phones": [],    "url": "https://www.facebook.com/177353602413952"  },  "syncStatus": null}

Beberapa direktori hanya mengonfirmasi bahwa bisnis tersebut ada dan tidak menampilkan detail yang cukup untuk dibandingkan. Hasil dari direktori ini dikembalikan sebagai FOUND dengan accurate: null, dan hanya dihitung dalam found, bukan dalam accurate atau inaccurate. Anggap bisnis tersebut tercantum, bukan terverifikasi:

JSON
{  "directory": {    "id": 374,    "name": "Map Quest",    "url": "www.mapquest.com"  },  "status": "FOUND",  "accurate": null,  "accuracySource": "DIRECTORY_MATCH",  "accuracy": {    "name": {      "status": "ACCURATE",      "message": null    },    "address": {      "status": "MISSING",      "message": "Not shown"    },    "phone": {      "status": "MISSING",      "message": "Not shown"    }  },  "listing": {    "name": "Joe's Pizza",    "street": "7 Carmine St",    "city": "New York",    "state": "NY",    "postalCode": "10014",    "country": null,    "fullAddress": "7 Carmine St, New York, NY 10014, US",    "phones": [],    "url": null  },  "syncStatus": null}

Hasil NOT_FOUND tidak memiliki listing maupun accuracy:

JSON
{  "directory": {    "id": 352,    "name": "YellowPages",    "url": "www.yellowpages.com"  },  "status": "NOT_FOUND",  "accurate": null,  "accuracySource": "DIRECTORY_MATCH",  "accuracy": null,  "listing": null,  "syncStatus": null}

Sejumlah direktori tidak menyimpan data sendiri. Uber, Waze, dan Lyft menampilkan data Google Maps, sedangkan Copilot menampilkan data Bing. Hasilnya mengikuti direktori sumber, sehingga biasanya sama dengan hasil yang dikembalikan Google Maps atau Bing, dan tidak memiliki url profil bisnis. Hitung hasil tersebut sebagai entri terpisah dalam summary, tetapi jangan anggap sebagai konfirmasi independen:

JSON
{  "directory": {    "id": 350,    "name": "Uber",    "url": "uber.com"  },  "status": "FOUND",  "accurate": true,  "accuracySource": "DIRECTORY_MATCH",  "accuracy": {    "name": {      "status": "ACCURATE",      "message": null    },    "address": {      "status": "ACCURATE",      "message": null    },    "phone": {      "status": "ACCURATE",      "message": null    }  },  "listing": {    "name": "Joe's Pizza",    "street": "7 Carmine Street",    "city": "New York",    "state": "NY",    "postalCode": "10014",    "country": "US",    "fullAddress": "7 Carmine St, New York, NY 10014, USA",    "phones": [      "+1 212-366-1182"    ],    "url": null  },  "syncStatus": null}

Asisten AI seperti ChatGPT dan Gemini juga disertakan. Untuk asisten ini, listing menampilkan informasi yang diketahui asisten tentang bisnis tersebut, yang sering kali hanya berupa nama, alamat lengkap, dan nomor telepon, dan tidak ada accuracy per kolom.

Untuk menyusun daftar perbaikan dari pemindaian yang telah selesai, cetak setiap direktori yang memiliki kolom dengan nilai salah atau tidak terisi:

Directories that need attention
curl -s https://listingsapi.com/api/v4/listings/scans/TGlzdGluZ1NjYW46Mzk0YTRhNWMtZjcwMy00NjZiLTg2NjAtMDU4MTlmNDhkZjMz \-H "Authorization: API $LISTINGSAPI_KEY" \| jq -r '.data.listingScan.results[]         | select(.accurate == false)         | .directory.name as $directory         | .accuracy         | to_entries[]         | select(.value.status != "ACCURATE")         | $directory + " " + .key + ": " + (.value.message // .value.status)'

Untuk pemindaian Joe's Pizza, ini mencetak dua baris: Facebook tidak mencantumkan nomor telepon, dan Judys Book menampilkan nomor telepon yang berbeda.

Text
Facebook phone: No phone number on the listingJudys Book phone: Phone number does not match

Sumber hasil

source menunjukkan cara hasil pemindaian diperoleh, dan resultsAsOf menunjukkan waktu pengumpulan data.

sourceArti
DIRECTORY_SEARCHPencarian baru di direktori. resultsAsOf menunjukkan waktu pemindaian ini selesai.
RECENT_SCANSalinan hasil pemindaian bisnis yang sama, yang dilakukan oleh siapa pun dalam 7 hari terakhir. Proses ini langsung selesai, dan resultsAsOf menunjukkan waktu pengumpulan data asli, sehingga waktunya bisa lebih awal daripada createdAt.
LOCATION_LISTINGSBisnis tersebut cocok dengan salah satu lokasi Anda berdasarkan nomor telepon, kode pos, dan negara, sehingga hasilnya berasal dari profil bisnis yang sebenarnya untuk lokasi tersebut. locationId diisi, accuracySource bernilai SYNC_STATUS alih-alih DIRECTORY_MATCH, dan setiap hasil menyertakan syncStatus dari profil bisnis tersebut.

Biaya, batas, dan kesalahan

Hanya pemindaian DIRECTORY_SEARCH baru yang menggunakan kuota bulanan Anda, yang bergantung pada paket Anda dan diatur ulang sesuai periode penagihan Anda. Berikut ini gratis:

  • mengulangi pemindaian bisnis yang sama dalam 7 hari. Hasil pemindaian Anda sebelumnya dikembalikan dengan reused: true;
  • pemindaian yang hasilnya dapat diambil dari pemindaian terbaru atas bisnis yang sama oleh akun mana pun. Hasilnya berupa salinan RECENT_SCAN;
  • pemindaian yang cocok dengan salah satu lokasi Anda (LOCATION_LISTINGS);
  • pemindaian yang berakhir dengan FAILED, yang penggunaan kuotanya dikembalikan.

Hasil pemindaian disimpan selama 90 hari. Setelah itu, GET mengembalikan 404 dengan SY83005.

Respons create dan list menyertakan objek quota, sehingga Anda dapat melihat penggunaan kuota Anda sebelum memulai pemrosesan secara berkelompok. List mengembalikan hasil pemindaian Anda mulai dari yang terbaru, dengan 1 hingga 50 hasil per halaman menggunakan perPage, tanpa results.

Check your allowance
curl -s "https://listingsapi.com/api/v4/listings/scans?page=1&perPage=20" \-H "Authorization: API $LISTINGSAPI_KEY" \| jq '.data.listingScans.quota'
Kolom quotaArti
limitJumlah pemindaian baru yang diizinkan oleh paket Anda dalam periode saat ini.
usedJumlah pemindaian baru yang telah digunakan.
remaininglimit dikurangi used, tidak pernah kurang dari 0.
resetsAtWaktu kuota diatur ulang.

Berikut adalah kesalahan yang paling sering Anda temui. Create mengembalikan kesalahannya dalam isi respons dengan HTTP 200; get dan list mengembalikan status HTTP yang biasa digunakan.

KodeTempatArti dan cara memperbaiki
SY83002CreateKuota bulanan telah habis. Pesan menyertakan batas dan waktu pengaturan ulang, dan quota dikembalikan. Tunggu hingga resetsAt, atau gunakan kembali hasil pemindaian dari 7 hari terakhir tanpa biaya.
SY83003Create, atau failure pada pemindaianAda nilai yang tidak diisi atau tidak valid. contextInfo menunjukkan nama kolomnya. Perbaiki masukan dan kirim ulang.
SY83004CreateListings scans tidak tersedia untuk countryIso tersebut.
SY83001CreatePaket Anda tidak mencakup listings scans.
SY83005GetTidak ada pemindaian dengan id tersebut, atau pemindaian tersebut milik akun lain atau berusia lebih dari 90 hari. HTTP 404.
SY83010Create, atau failure pada pemindaianPemindaian untuk sementara tidak tersedia. Coba lagi nanti.
SY90016CreateKunci tersebut hanya memiliki akses baca. Gunakan kunci Write.

GET untuk id yang tidak ada mengembalikan:

JSON
{  "data": {    "listingScan": null  },  "errors": [    {      "message": "SY83005: Listing scan not found"    }  ]}

Pemindaian yang berakhir dengan FAILED mencantumkan alasannya dalam failure, dan results tetap kosong:

JSON
{  "status": "FAILED",  "failure": {    "code": "SY83010",    "message": "SY83010: Listing scans are temporarily unavailable, try again later",    "field": null  }}

Format kesalahan umum dijelaskan di Kode kesalahan.

Untuk agen AI

Server MCP yang dihosting menyediakan fitur ini melalui 3 alat: listings_scans_create, listings_scans_get, dan listings_scans_list. Asisten dapat memulai pemindaian untuk bisnis yang disebutkan pengguna, memeriksa statusnya secara berkala dengan listings_scans_get, dan merangkum direktori yang memerlukan perhatian. Seperti pada REST, pembuatan pemindaian memerlukan kunci Write. Petunjuk penyiapan tersedia di Hubungkan agen AI ke MCP listingsAPI.

Langkah berikutnya