Skip to main content
एड्रेस ऑटोकम्पलीट से चेकआउट कन्वर्जन 35% बढ़ाएं: MapAtlas Geocoding
Tutorials

एड्रेस ऑटोकम्पलीट से चेकआउट कन्वर्जन 35% बढ़ाएं: MapAtlas Geocoding

MapAtlas Geocoding API से React चेकआउट में एड्रेस ऑटोकम्पलीट जोड़ें। कार्ट छोड़ना कम करें, मोबाइल एंट्री तेज़ करें और रियल-टाइम एड्रेस वैलिडेशन पाएं।

Brent van der Heiden9 min read
#address autocomplete#geocoding api#checkout conversion#address validation#javascript autocomplete

चेकआउट का एड्रेस फील्ड वह जगह है जहां मोबाइल कन्वर्जन दम तोड़ देते हैं। यूज़र प्रोडक्ट पेज पर आता है, कार्ट में आइटम जोड़ता है, चेकआउट पर जाता है, और फिर उसे 6-इंच टचस्क्रीन कीबोर्ड पर पूरा पता टाइप करना पड़ता है। अगर पोस्टल कोड गलत हो, हाउस नंबर का फॉर्मेट गड़बड़ हो, या बस यूज़र हार मान ले, तो वो सेल जा चुकी जिसे आप पहले ही जीत चुके थे।

एड्रेस ऑटोकम्पलीट इसे ठीक करता है। इम्प्लीमेंटेशन के बाद, एड्रेस एंट्री 15-25 कीस्ट्रोक से घटकर 3-4 रह जाती है। यूज़र एक स्ट्रीट नेम टाइप करता है, आधे सेकेंड में मिलती हुई सजेशन देखता है, उस पर टैप करता है, और पूरा पता, स्ट्रीट, हाउस नंबर, शहर, पोस्टल कोड, देश, अपने आप और सही-सही भर जाता है। टाइपो से होने वाली फेल डिलीवरी कम होती है। चेकआउट छोड़ना कम होता है। और सबसे अहम बात, हर ऑर्डर के साथ वेरिफाइड, जियोकोडेड कोऑर्डिनेट्स मिलते हैं, जिन्हें आपके लॉजिस्टिक्स और रूटिंग सिस्टम सीधे इस्तेमाल कर सकते हैं।

ई-कॉमर्स इम्प्लीमेंटेशन के शोध लगातार दिखाते हैं कि एड्रेस ऑटोकम्पलीट जोड़ने के बाद चेकआउट कम्प्लीशन रेट में 25-35% सुधार होता है, और यह असर मोबाइल पर और भी मज़बूत होता है, जहां मैनुअल टेक्स्ट एंट्री सबसे धीमी और गलतियों से भरी होती है।

यह ट्यूटोरियल MapAtlas Geocoding API का उपयोग करके एक पूरा React एड्रेस ऑटोकम्पलीट कॉम्पोनेंट बनाता है, जिसमें debouncing, कीबोर्ड नेविगेशन, EU एड्रेस फॉर्मेट हैंडलिंग और फॉर्म इंटीग्रेशन शामिल हैं। पूरा कॉम्पोनेंट करीब 90 लाइन का है।

एड्रेस एरर कन्वर्जन क्यों खत्म करते हैं

फेल डिलीवरी हर तरफ महंगी पड़ती है: कैरियर री-डिलीवरी फीस लेता है, कस्टमर सर्विस टीम शिकायत संभालती है, और आपके ब्रांड पर ग्राहक का भरोसा टूटता है। B2C ई-कॉमर्स में, एड्रेस एंट्री एरर सभी शिपिंग एक्सेप्शन का करीब 5-8% हिस्सा होते हैं।

इसके पीछे की वजहें अनुमानित हैं:

  • मोबाइल कीबोर्ड एंट्री डेस्कटॉप से ज़्यादा टाइपो पैदा करती है। ऑटोकरेक्ट अक्सर स्ट्रीट नेम और शहर के नाम खराब कर देता है।
  • पोस्टल कोड फॉर्मेट हर देश में अलग होते हैं। UK फॉर्मेट (AN NAA) वाले फील्ड में 5-डिजिट जर्मन कोड डालने पर वैलिडेशन एरर आएगा।
  • EU देशों में स्ट्रीट/हाउस नंबर का क्रम अलग है। जर्मनी और नीदरलैंड्स में हाउस नंबर स्ट्रीट नेम के बाद आता है। फ्रांस में पहले। मैनुअल एंट्री फॉर्म शायद ही कभी यूज़र को सही गाइड करते हैं।
  • अपार्टमेंट और फ्लोर डेसिग्नेशन का कोई स्टैंडर्ड फॉर्मेट नहीं है। यूज़र जो स्वाभाविक लगे वो डालते हैं, जो अक्सर शिपिंग कैरियर की अपेक्षाओं से मेल नहीं खाता।

ऑटोकम्पलीट इनमें से अधिकांश समस्याओं को एक प्री-वैलिडेटेड, स्ट्रक्चर्ड एड्रेस ऑब्जेक्ट लौटाकर हल करता है।

MapAtlas Geocoding Autocomplete Endpoint

ऑटोकम्पलीट सजेशन के लिए एंडपॉइंट है:

GET https://api.mapatlas.eu/geocoding/v1/autocomplete?text={query}&key={YOUR_API_KEY}

EU ई-कॉमर्स के लिए ज़रूरी ऑप्शनल पैरामीटर:

ParameterTypeDescription
textstringपार्शियल एड्रेस क्वेरी
focus.point.lonnumberयूज़र का longitude (नज़दीकी परिणाम प्राथमिकता देता है)
focus.point.latnumberयूज़र का latitude (नज़दीकी परिणाम प्राथमिकता देता है)
boundary.countrystringISO 3166-1 alpha-3 कंट्री कोड (जैसे DEU, FRA, NLD)
layersstringपरिणाम प्रकार फ़िल्टर: address, street, locality
sizenumberपरिणामों की संख्या (डिफ़ॉल्ट 10, अधिकतम 20)

एक टिपिकल रिस्पॉन्स:

{
  "type": "FeatureCollection",
  "features": [
    {
      "type": "Feature",
      "geometry": { "type": "Point", "coordinates": [4.9041, 52.3676] },
      "properties": {
        "id": "address:node/1234567",
        "label": "Damrak 1, 1012 LG Amsterdam, Netherlands",
        "name": "Damrak 1",
        "street": "Damrak",
        "housenumber": "1",
        "postalcode": "1012 LG",
        "locality": "Amsterdam",
        "region": "North Holland",
        "country": "Netherlands",
        "country_code": "NL",
        "confidence": 0.98
      }
    }
  ]
}

हर परिणाम स्ट्रक्चर्ड एड्रेस कॉम्पोनेंट के साथ GeoJSON फीचर के रूप में वापस आता है। आपका फॉर्म क्लीन, वैलिडेटेड डेटा सीधे हर फील्ड में इन्सर्ट कर सकता है।

React Autocomplete Hook बनाना

API लॉजिक को एक reusable hook में निकालकर शुरू करें:

// hooks/useAddressAutocomplete.js
import { useState, useEffect, useRef } from 'react';

const API_BASE = 'https://api.mapatlas.eu/geocoding/v1/autocomplete';
const API_KEY  = process.env.NEXT_PUBLIC_MAPATLAS_KEY;
const DEBOUNCE_MS = 300;
const MIN_CHARS   = 3;

export function useAddressAutocomplete(countryCode = null) {
  const [query,       setQuery]       = useState('');
  const [suggestions, setSuggestions] = useState([]);
  const [loading,     setLoading]     = useState(false);
  const [error,       setError]       = useState(null);
  const debounceTimer = useRef(null);

  useEffect(() => {
    if (query.length < MIN_CHARS) {
      setSuggestions([]);
      return;
    }

    clearTimeout(debounceTimer.current);

    debounceTimer.current = setTimeout(async () => {
      setLoading(true);
      setError(null);

      try {
        const url = new URL(API_BASE);
        url.searchParams.set('text', query);
        url.searchParams.set('key', API_KEY);
        url.searchParams.set('size', '6');
        url.searchParams.set('layers', 'address');
        if (countryCode) {
          url.searchParams.set('boundary.country', countryCode);
        }

        const res  = await fetch(url.toString());
        if (!res.ok) throw new Error(`API error: ${res.status}`);

        const data = await res.json();
        setSuggestions(data.features ?? []);
      } catch (err) {
        setError(err.message);
        setSuggestions([]);
      } finally {
        setLoading(false);
      }
    }, DEBOUNCE_MS);

    return () => clearTimeout(debounceTimer.current);
  }, [query, countryCode]);

  return { query, setQuery, suggestions, loading, error };
}

debounce टाइमर केवल तब फायर होता है जब यूज़र 300ms के लिए टाइप करना रोके। MIN_CHARS गार्ड 1-2 कैरेक्टर इनपुट पर API कॉल रोकता है।

Autocomplete कॉम्पोनेंट

// components/AddressAutocomplete.jsx
import { useState, useRef } from 'react';
import { useAddressAutocomplete } from '../hooks/useAddressAutocomplete';

export function AddressAutocomplete({ onSelect, countryCode, placeholder }) {
  const { query, setQuery, suggestions, loading } = useAddressAutocomplete(countryCode);
  const [open,        setOpen]    = useState(false);
  const [highlighted, setHighlighted] = useState(-1);
  const inputRef = useRef(null);

  function handleSelect(feature) {
    const p = feature.properties;
    setQuery(p.label);
    setOpen(false);
    setHighlighted(-1);
    onSelect({
      label:       p.label,
      street:      p.street      ?? '',
      housenumber: p.housenumber ?? '',
      postalcode:  p.postalcode  ?? '',
      locality:    p.locality    ?? '',
      region:      p.region      ?? '',
      country:     p.country     ?? '',
      country_code: p.country_code ?? '',
      coordinates: feature.geometry.coordinates, // [lng, lat]
    });
  }

  function handleKeyDown(e) {
    if (!open || suggestions.length === 0) return;
    if (e.key === 'ArrowDown')  setHighlighted(h => Math.min(h + 1, suggestions.length - 1));
    if (e.key === 'ArrowUp')    setHighlighted(h => Math.max(h - 1, 0));
    if (e.key === 'Enter' && highlighted >= 0) handleSelect(suggestions[highlighted]);
    if (e.key === 'Escape')     setOpen(false);
  }

  return (
    <div style={{ position: 'relative' }}>
      <input
        ref={inputRef}
        type="text"
        value={query}
        placeholder={placeholder ?? 'Start typing your address...'}
        onChange={e => { setQuery(e.target.value); setOpen(true); setHighlighted(-1); }}
        onKeyDown={handleKeyDown}
        onBlur={() => setTimeout(() => setOpen(false), 150)}
        style={{ width: '100%', padding: '10px 12px', fontSize: 16, borderRadius: 6, border: '1px solid #ccc' }}
        autoComplete="off"
        aria-autocomplete="list"
        aria-haspopup="listbox"
        aria-expanded={open && suggestions.length > 0}
      />

      {loading && (
        <span style={{ position: 'absolute', right: 12, top: '50%', transform: 'translateY(-50%)', fontSize: 12, color: '#888' }}>
          Searching…
        </span>
      )}

      {open && suggestions.length > 0 && (
        <ul
          role="listbox"
          style={{
            position: 'absolute', top: '100%', left: 0, right: 0, zIndex: 999,
            background: '#fff', border: '1px solid #ccc', borderTop: 'none',
            borderRadius: '0 0 6px 6px', listStyle: 'none', margin: 0, padding: 0,
            boxShadow: '0 4px 12px rgba(0,0,0,0.1)',
          }}
        >
          {suggestions.map((feature, i) => (
            <li
              key={feature.properties.id}
              role="option"
              aria-selected={i === highlighted}
              onMouseDown={() => handleSelect(feature)}
              onMouseEnter={() => setHighlighted(i)}
              style={{
                padding: '10px 12px',
                cursor: 'pointer',
                fontSize: 14,
                background: i === highlighted ? '#f0f7e6' : '#fff',
                borderBottom: i < suggestions.length - 1 ? '1px solid #f0f0f0' : 'none',
              }}
            >
              {feature.properties.label}
            </li>
          ))}
        </ul>
      )}
    </div>
  );
}

यह कॉम्पोनेंट पूरी कीबोर्ड नेविगेशन (arrow keys, enter, escape), स्क्रीन रीडर के लिए ARIA attributes, और 150ms blur delay संभालता है।

Checkout Form के साथ इंटीग्रेशन

// pages/checkout.jsx
import { useState } from 'react';
import { AddressAutocomplete } from '../components/AddressAutocomplete';

export default function CheckoutPage() {
  const [address, setAddress] = useState({
    street: '', housenumber: '', postalcode: '',
    locality: '', country: '', coordinates: null,
  });

  function handleAddressSelect(selected) {
    setAddress(selected);
    // Coordinates are available for routing/delivery estimation
    console.log('Delivery coordinates:', selected.coordinates);
  }

  return (
    <form>
      <h2>Delivery address</h2>

      <AddressAutocomplete
        onSelect={handleAddressSelect}
        countryCode="NLD"  // Restrict to Netherlands, remove for EU-wide
        placeholder="Start typing your street address..."
      />

      {/* Show structured fields after selection, allow manual edits */}
      {address.street && (
        <div style={{ display: 'grid', gridTemplateColumns: '1fr auto', gap: 8, marginTop: 12 }}>
          <input value={address.street}      onChange={e => setAddress(a => ({ ...a, street: e.target.value }))}      placeholder="Street" />
          <input value={address.housenumber} onChange={e => setAddress(a => ({ ...a, housenumber: e.target.value }))} placeholder="No." style={{ width: 80 }} />
          <input value={address.postalcode}  onChange={e => setAddress(a => ({ ...a, postalcode: e.target.value }))}  placeholder="Postal code" />
          <input value={address.locality}    onChange={e => setAddress(a => ({ ...a, locality: e.target.value }))}    placeholder="City" />
        </div>
      )}

      <button type="submit" style={{ marginTop: 16 }}>
        Continue to payment
      </button>
    </form>
  );
}

ऑटोकम्पलीट के बाद एडिट करने योग्य individual फील्ड दिखाना एक्सेसिबिलिटी और edge cases के लिए ज़रूरी है। यूज़र के असली दरवाज़े के पते में फ्लैट नंबर या एक्सेस कोड हो सकता है जो जियोकोडेड रिज़ल्ट में नहीं होता।

EU एड्रेस फॉर्मेट पर विचार

अलग-अलग EU देशों में एड्रेस कन्वेंशन अलग होते हैं:

जर्मनी (DEU): पहले स्ट्रीट, फिर हाउस नंबर। Hauptstraße 42, 10115 Berlin

फ्रांस (FRA): स्ट्रीट से पहले हाउस नंबर। 42 rue de Rivoli, 75001 Parislabel प्रॉपर्टी देश-उचित फॉर्मेट में पता लौटाती है।

नीदरलैंड्स (NLD): डच पोस्टल कोड 4 डिजिट + 2 बड़े अक्षर हैं, बीच में स्पेस: 1012 LG

बेल्जियम (BEL): द्विभाषी क्षेत्रों में नगर पालिका के आधार पर फ्रेंच या डच में पता मिल सकता है।

MapAtlas Geocoding API इन सभी को सही ढंग से संभालता है।

परफॉर्मेंस पर विचार

ऊपर का इम्प्लीमेंटेशन औसतन 3-4 कैरेक्टर टाइप होने पर एक API कॉल करता है (300ms debounce तेज़ टाइपिंग को absorb करता है)। प्रोडक्शन में, अपने API key को client-side कोड में दिखने से बचाने के लिए एक server-side proxy सेट करें:

// pages/api/autocomplete.js (Next.js API route)
export default async function handler(req, res) {
  const { text, countryCode } = req.query;
  const url = new URL('https://api.mapatlas.eu/geocoding/v1/autocomplete');
  url.searchParams.set('text',  text);
  url.searchParams.set('key',   process.env.MAPATLAS_KEY); // Server-side env var
  url.searchParams.set('size',  '6');
  url.searchParams.set('layers', 'address');
  if (countryCode) url.searchParams.set('boundary.country', countryCode);

  const response = await fetch(url.toString());
  const data     = await response.json();
  res.json(data);
}

फिर hook को MapAtlas API की बजाय /api/autocomplete कॉल करने के लिए अपडेट करें।

सारांश

एक सिंगल एड्रेस ऑटोकम्पलीट फील्ड आपके चेकआउट कन्वर्जन रेट में सार्थक सुधार कर सकती है। इम्प्लीमेंटेशन सीधा है: MapAtlas Geocoding API को debounced fetch, कीबोर्ड नेविगेशन वाला एक छोटा dropdown कॉम्पोनेंट, और चुने हुए रिज़ल्ट से फील्ड भरने वाला फॉर्म इंटीग्रेशन।

मुख्य निर्णय:

  • 300ms पर Debounce करें।
  • 3 कैरेक्टर से पहले रिक्वेस्ट न भेजें।
  • देश से प्रतिबंधित करें अगर आप अपने यूज़र बेस की भूगोल जानते हैं।
  • ऑटोकम्प्लीटेड फील्ड मैनुअल एडिट की अनुमति हमेशा दें।
  • API key को server-side proxy करें प्रोडक्शन में।

एड्रेस फील्ड के साथ पहले मैप इंटीग्रेशन के लिए, How to Add Interactive Maps to Your Website देखें।


MapAtlas API key के लिए मुफ्त साइन अप करें। Geocoding API फ्री टियर में शामिल है, क्रेडिट कार्ड की ज़रूरत नहीं।

अक्सर पूछे जाने वाले प्रश्न

एड्रेस ऑटोकम्पलीट चेकआउट कन्वर्जन को कैसे बेहतर बनाता है?

एड्रेस एंट्री ज़्यादातर चेकआउट फ्लो में सबसे ज़्यादा friction वाला स्टेप है, खासकर मोबाइल पर। ऑटोकम्पलीट इसे 2-3 कीस्ट्रोक और एक टैप तक सीमित कर देता है, फेल डिलीवरी का कारण बनने वाली फॉर्मेट गलतियां दूर करता है, और पता सही से एंटर हुआ या नहीं इसकी चिंता खत्म करता है। शोध लगातार दिखाता है कि ऑटोकम्पलीट के बाद चेकआउट छोड़ना 25-35% कम होता है।

क्या MapAtlas Geocoding API यूरोपीय एड्रेस फॉर्मेट सपोर्ट करता है?

हां। API EU-विशिष्ट फॉर्मेट संभालता है जिसमें जर्मनी में स्ट्रीट के बाद हाउस नंबर का क्रम, फ्रेंच arrondissement, डच 4-अंकीय पोस्टल कोड और सभी EU सदस्य देशों में मल्टी-लैंग्वेज एड्रेस फॉर्मेट शामिल हैं। रिज़ल्ट GeoJSON के रूप में structured एड्रेस कॉम्पोनेंट के साथ मिलते हैं।

ऑटोकम्पलीट के दौरान API कॉल्स बहुत ज़्यादा होने से कैसे बचें?

इनपुट हैंडलर पर 250-300ms का debounce लगाएं ताकि सिर्फ तब request भेजी जाए जब यूज़र टाइप करना बंद कर दे। साथ ही request trigger होने से पहले minimum character threshold (3-4 अक्षर) भी सेट करें। ये दोनों उपाय हर कीस्ट्रोक पर fire करने की तुलना में API कॉल्स लगभग 80% कम करते हैं।

यह उपयोगी लगा? इसे साझा करें।

लेखक के बारे में

Brent van der Heiden

लेखक

Brent van der Heiden

Co-Founder & CEO at MapAtlas

Brent built MapAtlas out of a conviction that developers deserve location APIs with fair pricing and genuine end-user privacy. He writes about geospatial infrastructure, AI search visibility, and how location data powers the products people rely on every day.

सभी लेख देखें
ब्लॉग पर वापस जाएं