{"id":27019306,"url":"https://github.com/opencagedata/address-formatting","last_synced_at":"2025-12-18T06:17:51.687Z","repository":{"id":20600584,"uuid":"23881516","full_name":"OpenCageData/address-formatting","owner":"OpenCageData","description":"templates to format geographic addresses","archived":false,"fork":false,"pushed_at":"2025-04-01T10:15:04.000Z","size":904,"stargazers_count":408,"open_issues_count":5,"forks_count":89,"subscribers_count":23,"default_branch":"master","last_synced_at":"2025-04-12T01:07:12.167Z","etag":null,"topics":["addresses","formatting","i18n"],"latest_commit_sha":null,"homepage":null,"language":"Perl","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/OpenCageData.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE.txt","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":"SECURITY.md","support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2014-09-10T16:09:56.000Z","updated_at":"2025-04-01T10:15:07.000Z","dependencies_parsed_at":"2023-02-12T21:31:36.347Z","dependency_job_id":"9766b8dc-70f4-43bb-9d89-0a143fd56fe2","html_url":"https://github.com/OpenCageData/address-formatting","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/OpenCageData%2Faddress-formatting","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/OpenCageData%2Faddress-formatting/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/OpenCageData%2Faddress-formatting/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/OpenCageData%2Faddress-formatting/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/OpenCageData","download_url":"https://codeload.github.com/OpenCageData/address-formatting/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248501861,"owners_count":21114683,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["addresses","formatting","i18n"],"created_at":"2025-04-04T17:27:10.938Z","updated_at":"2025-12-18T06:17:46.623Z","avatar_url":"https://github.com/OpenCageData.png","language":"Perl","funding_links":[],"categories":[],"sub_categories":[],"readme":"# address formatting\n\n### Overview\n\nThis project contains templates and test cases for address formats used in territories around the world. The templates can then be processed in any programming language ([see below for list of processors](#processing-logic)).\n\n### Build Status\n\n[![Build Status](https://github.com/OpenCageData/address-formatting/actions/workflows/ci.yml/badge.svg)](https://github.com/OpenCageData/address-formatting/actions/workflows/ci.yml)\n\n### An example:\n\nGiven a set of address parts like\n\n     house_number:  17\n     road:          Rue du Médecin-Colonel Calbairac\n     neighbourhood: Lafourguette\n     suburb:        Toulouse Ouest\n     postcode:      31000\n     city:          Toulouse\n     county:        Toulouse\n     state:         Midi-Pyrénées\n     country:       France\n     country_code:  FR\n\nwe want to write logic to compile an address in the format consumers expect\n\n    17 Rue du Médecin-Colonel Calbairac\n    31000 Toulouse\n    France\n\n### Why would you want to do this?\n\nThe intended use case is database or geocoding systems (forward, reverse, autocomplete) where we know both the country of the address and the language of the user/reader. The address is displayed to a consumer (for example in an app) and not used to print on an envelope for actual postal delivery. We use it to format output from the [OpenCage Geocoding API](https://opencagedata.com/api).\n\n### Which addresses are we talking about?\n\nWe have to deal with\n\n   * incomplete data\n   * anything with a name (peaks, bridges, bus stops)\n\nUnlike [physical post (office) mail](http://www.bitboost.com/ref/international-address-formats.html) we don't have to deal with\n\n   * apartment/flat number, floor numbers\n   * PO boxes\n   * translating the language of the (destination) address. Whatever language is input is output. \n  \n### Processing logic\n\nOur goal with this repository is a series of (programming) language independent templates. Those templates can then be processed by whatever software you like. \n\nThere are open-source implementations in\n\n  * [Android library](https://github.com/woheller69/AndroidAddressFormatter)\n  * [Elixir](https://github.com/dkuku/ex_address_formatting)\n  * [Go](https://github.com/timonmasberg/address-formatter)\n  * [Java](https://github.com/placemarkt/address-formatter-java)\n  * [Javascript](https://github.com/fragaria/address-formatter)\n  * [Kotlin](https://github.com/bettermile/address-formatter-kotlin)\n  * [Perl](https://metacpan.org/release/Geo-Address-Formatter)\n  * [PHP](https://github.com/predicthq/address-formatter-php)\n  * [Python (no longer maintained)](https://github.com/pudo/addressformatting/tree/master)\n  * [Ruby](https://github.com/mirubiri/address_composer)\n  * [Rust (no longer maintained)](https://github.com/antoine-de/address-formatter-rs)\n  * [Scala](https://github.com/ben-willis/address-formatter)\n\nWe would love more language implementations. The more people who use the templates, the more likely bugs will be reported. \nIf you write a processor, please submit a pull request adding it to the list. Thanks. \n\n### International coverage\n\nAs of March 2024 coverage is:\n\n    We are aware of 251 territories\n    We have at least one test for 251 (100%) territories\n    We have rules for 251 (100%) territories\n    0 (0%) territories have neither rules nor tests\n    \nThis output is generated by `bin/coverage.pl`    \n\nWe need more language specific abbreviations. Please see `conf/abbreviations`. Pull requests gladly received. \n\nA detailed breakdown of test and configuration coverage can be found by running `bin/coverage.pl -d`. A list of all known territories is in `conf/country_codes.yaml`\n\n_Please note: the list is simple all officially assigned [ISO 3166-1 alpha-2 codes](https://en.wikipedia.org/wiki/ISO_3166-1_alpha-2#Officially_assigned_code_elements), and is not a political statement on whether or not these territories are or are not or should or should not be political states._\n\n### File format\n\nThe files are in [YAML](http://yaml.org/) format. The templates are written in [Mustache](http://mustache.github.io/). Both formats are human readable, strict, solve escaping and support comments. YAML allows references (called \"ankers\") to avoid copy\u0026paste, Mustache allows sub-templates (called \"partials\").\n\n### How to add your country/territory\n\n1. edit the .yaml testcase for the country/territory in `testcases/countries`. The file names correspond to the appropriate ISO 3166-1 alpha-2 code - see `conf/country_codes.yaml`\n  * a good way to get sample data is:\n      * find an addressed location (house, business, etc) in your\n        target territory in OpenStreetMap\n      * get the coordinates (lat, long) of the location\n      * put the coordinates into the [OpenCage Geocoding API demo page](https://opencagedata.com/demo)\n      * look at the resulting JSON in the *Raw Response* tab\n\n2. edit `conf/countries/worldwide.yaml`\n  * Possibly your country/territory uses an existing generic format as\n    defined at the top of the file. If so, great, just map you\n    country_code to the generic template. You may still want to add\n    clean up code (see the entry for `DE` as an example).\n  * If not you need to define a new generic rule set\n      * possibly you will need to define new state/region mappings in `conf/state_codes.yaml`\n\n3. to test you will now need to process the .yaml test via a processer\n   (see above) and ensure the input leads to the desired output.\n\nIf in doubt, please get in touch by submitting an issue. \n\n### Formatting rules\n\nCurrently we support the following formatting rules:\n\n* `replace:` regex that operates on the input values, useful for removing bureaucratic cruft like \"London Borough of \". Note if you define the regex starting with format _X=_, for example _city=_ it should operate only on values with that key\n* `postformat_replace:` regex that operates on the final output\n* `add_component:` with a value of the form `component=XXXX`\n* `change_country:` change the country value of the input, useful for dependent territories. Can include a substitution like `$state` so that that component value is then inserted into the new country value. See `testcases/countries/sh.yaml` for an example.\n* `use_country:` use the formating configuration of another country, useful for dependent territories to avoid duplicating configuration\n\n### The future\n\nMore tests! For every rule about addresses there are exceptions and edge cases to consider. More test cases are always needed.\n\nPlanned features:\n\n  * basic error checking, for example ignore things which obviously can not be postcodes\n  * define rules for postcode format specifically\n\nWe welcome your pull requests. Together we can address the world!\n\n### License\n\nThis project is licensed under the MIT License - see the [LICENSE.txt](LICENSE.txt) file for details\n\n### Additional resources\n\nIf you are working with addresses you may need [lists of random addresses/postcodes/coordinates](https://opencagedata.com/tools/address-lists) (either in general or for specific countries) for testing.\n\n### Further reading on the challenge of address\n\nHere's [our blog post anouncing this project](https://blog.opencagedata.com/post/99059889253/good-looking-addresses-solving-the-berlin-berlin) and the motivations behind it.\n\nYou may enjoy Michael Tandy's [Falsehoods Programmers Believe about Addresses](http://www.mjt.me.uk/posts/falsehoods-programmers-believe-about-addresses/).\n\nIf it's actual address data you're after, check out [OpenStreetMap](https://www.openstreetmap.org) and [OpenAddresses](http://openaddresses.io/).\n\nIf you want to turn longitude, latitude into well formatted addresses or placenames, well that's what a geocoder does. Check out ours: [OpenCage Geocoder](https://opencagedata.com).\n\nIf all this convinces you that address are evil, please check out [what3words](http://what3words.com) which allows you to dispense with them entirely. \n\n### Who is OpenCage GmbH?\n\n\u003ca href=\"https://opencagedata.com\"\u003e\u003cimg src=\"opencage_logo_300_150.png\"\u003e\u003c/a\u003e\n\nWe run a worldwide [geocoding API](https://opencagedata.com/api) and [geosearch](https://opencagedata.com/geosearch) service based on open data. \nLearn more [about us](https://opencagedata.com/about). \n\nWe also organize [Geomob](https://thegeomob.com), a series of regular meetups for location based service creators, where we do our best to highlight geoinnovation. If you like geo stuff, you will probably enjoy [the Geomob podcast](https://thegeomob.com/podcast/).\n\n\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fopencagedata%2Faddress-formatting","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fopencagedata%2Faddress-formatting","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fopencagedata%2Faddress-formatting/lists"}