Tracking — entry 005 of 10
PostalPinCode
PostalPinCode.in mirrors India Post's PIN code directory as a simple keyless REST API, returning post-office name, branch type, delivery status, and district/state/circle hierarchy for any 6-digit PIN or by post-office branch name. Responses are plain JSON with no signup, rate-limit tier, or API key required. It's run as a free public-data convenience layer rather than a commercial product.
PostalPinCode.in is a free, keyless REST wrapper around India Post's own PIN code directory: given a 6-digit PIN or a post-office branch name, it returns the matching post office(s) with delivery status and district/state/circle/region hierarchy. Its own "Limits" section states plainly "There is no limits of API requests," and no signup or key is required for either endpoint.
GreatAPIs Score
Auth quickstart
- No API key required. A live GET against api.postalpincode.in needs no headers or query params beyond the PIN or branch name in the path, and no rate-limit header appeared on any probe this run — matching the docs' own "There is no limits of API requests" claim.
Your key is stored only in this browser (localStorage) and sent directly to the API — never to greatapis.
Look up post offices for a PIN code
GEThttps://api.postalpincode.in/pincode/682001
[{"Message":"Number of pincode(s) found:1","Status":"Success","PostOffice":[{"Name":"Kochi","Description":null,"BranchType":"Head Post Office","DeliveryStatus":"Delivery","Circle":"Kerala","District":"Ernakulam","Division":"Ernakulam","Region":"Kochi","Block":"Kochi","State":"Kerala","Country":"India","Pincode":"682001"}]}]Developer reference
https://api.postalpincode.inGotchas & limits
- The live response wraps the whole envelope in a one-element JSON array — `[{"Message":...,"Status":...,"PostOffice":[...]}]` — even though the API's own docs page (postalpincode.in/Api-Details) shows the identical fields as a bare object with no wrapping array. Code that expects the documented shape needs to index `[0]` first (confirmed live this run against both /pincode and /postoffice).
- Nothing ever fails with a non-2xx HTTP status — branch on the body, never on the transport code. Both a well-formed but unassigned 6-digit PIN (`GET /pincode/999999`) and a malformed non-numeric segment (`GET /pincode/abcdef`) return **HTTP 200**; only the body shape differs. The former gives the docs' own documented error envelope, `[{"Message":"No records found","Status":"Error","PostOffice":null}]`; the latter gives an undocumented one with no `PostOffice` key at all — `[{"Status":"404","Message":"The requested resource is not found","RequestUri":"https://api.postalpincode.in:443/pincode/abcdef"}]`, where that `404` is a *string inside the JSON*, not the HTTP status. `/pincode/12`, `/pincode/1100011` and a bare `/pincode/` are all HTTP 200 too (all measured live this run; a control request through the same egress path did return a real HTTP 404, so this is the API's behaviour and not a proxy artifact).
- Plain `http://` is hard-blocked rather than redirected: a live `GET http://api.postalpincode.in/pincode/682001` returned HTTP 403 Forbidden with no `Location` header — callers must use `https://` from the very first request (confirmed live this run).
- The second documented endpoint, `GET /postoffice/{branchName}`, matches on post-office branch name rather than PIN — so it's the one that discovers a PIN you don't already know, where `/pincode/{pin}` requires you to supply it up front. A live `GET /postoffice/New%20Delhi` returned 2 matches whose `Name` values are `New Delhi ` (note the trailing space, and no `G.P.O.` suffix — that word only shows up in its `Division`, `New Delhi GPO`) and `New Delhi South Ext-II`, carrying `Pincode` `110001` and `110049` respectively. Its `Message` also reads `Number of Post office(s) found:2` here, while the `/pincode` lookup words the same field `Number of pincode(s) found:1` — don't parse either string.
- `access-control-allow-origin: *` is returned only when the request actually carries an `Origin` header — a live GET sent without one came back with no CORS header at all, while the same GET plus `Origin` echoed `*` on both the success and the error probe above. A live OPTIONS preflight to the same path returned no CORS headers either, just a plain `Allow`/`Public` method list. In practice that's fine, because a browser always sends `Origin` on a cross-origin request: safe to call from browser JS as long as it stays a simple GET with no custom headers that would force a preflight.