Address autocomplete in React with the Locio package
About 6 minutes. Updated 18 September 2026.
Install the published React client and have an accessible address autocomplete working in a few minutes, with the debouncing, request cancellation and keyboard handling already done and every class name still yours.
There is a guide that builds this by hand, and it is worth reading if you want to know what the moving parts are. This one installs @locio-au/react instead, which is the same thing with the awkward bits already handled.
01Install it
npm install @locio-au/reactReact 18 or newer, as a peer dependency. Nothing else comes with it: no styles, no state library, no icon set.
02Drop the component in
AddressAutocomplete renders a labelled input and a listbox, implements the ARIA combobox pattern so arrow keys, Enter and Escape all work, and hands you the picked address. Results come from /v1/addresses.
// src/CheckoutForm.tsx
import { AddressAutocomplete, addressId, type Address } from "@locio-au/react";
import { useState } from "react";
export function CheckoutForm() {
const [address, setAddress] = useState<Address | null>(null);
return (
<form>
<AddressAutocomplete
publicKey={import.meta.env.VITE_LOCIO_KEY}
label="Delivery address"
onSelect={setAddress}
/>
{address && (
<input type="hidden" name="address_id" value={addressId(address)} />
)}
</form>
);
}Store addressId(address). It is the address's id in its country's register, which in Australia is the G-NAF Address Detail PID, sent under address_detail_pid as well. It is stable across releases for an address that has not changed, where the formatted line is not, so it is the thing to key your own records on rather than the text. addressId rather than address.id: the field is optional on the package's type, because a service one release behind sends only the G-NAF names, and the helper reads whichever arrived.
03Make it look like your form
Every slot takes a class of yours, and styled=false removes the package's own inline styles so there is nothing to override.
// Your classes, on every slot. styled={false} drops the
// package's inline styles so nothing fights your stylesheet.
<AddressAutocomplete
publicKey={import.meta.env.VITE_LOCIO_KEY}
styled={false}
classNames={{
root: "field",
label: "field-label",
input: "field-input",
list: "field-list",
option: "field-option",
status: "field-status",
}}
onSelect={setAddress}
/>04Or take the hook and write your own markup
The component is a thin layer over a hook. The hook does the debounce, cancels the request in flight when the term changes, and keeps a late answer for an earlier prefix from overwriting a newer one.
// When you want your own markup entirely.
import { addressId, useAddressAutocomplete } from "@locio-au/react";
function Search() {
// note and countryCode are what the service said about the country it
// searched: somebody typing from a country with no address data gets no
// results and a sentence saying so, which is the one to show them.
const { term, setTerm, results, status, note, countryCode } = useAddressAutocomplete({
publicKey: import.meta.env.VITE_LOCIO_KEY,
debounceMs: 300,
minLength: 3,
});
return (
<div>
<input value={term} onChange={(e) => setTerm(e.target.value)} />
{status === "searching" && <p>Searching</p>}
{note && <p>{note}</p>}
<ul>
{results.map((a) => (
<li key={addressId(a)}>{a.formatted}</li>
))}
</ul>
{countryCode && <p>Searched {countryCode}</p>}
</div>
);
}What it costs
One unit per request. The default debounce is 300 milliseconds and the default minimum is three characters, so a completed address is usually three or four requests. Refused requests are free.
The key
A public key, always. It carries an origin allow list, so a copy lifted from your page does nothing anywhere else. The client refuses a secret key outright when it sees a browser, rather than letting one reach your users. Create a key.
Related
- Address autocomplete in plain JavaScript
- Address autocomplete in React
- Address autocomplete in Vue with the Locio package
- Address autocomplete in Vue
- Stand up a React site with Australian address search
- Normalise shipping addresses at checkout
- Put a searched address on a map with MapLibre
- Validate and geocode Australian addresses in PHP
- Australian address autocomplete for WooCommerce
- Address validation and geocoding in Go
- Use Locio from Claude Code, Claude Desktop and Cursor
- Give an agent address tools with the Anthropic API
- Clean a spreadsheet of addresses with an agent
- The API reference, with every call in curl, Node, Python, Ruby, Go and PHP.