Repository: joke2k/faker

Issue:
dk_DK output is wrong.
* Faker version: 4.0.2
* OS: MAC

Almost all providers for dk_DK output wrong data. I have attached a list which will make it possible to correct this issue.

Sorry about this danish descriptions, i could not find english versions - possibly use google translator to read.

Thanks

<pre>
#### fake.address() ####
Description: 
https://www.postnord.dk/sende/praktik/udformningafbreve/adressering
https://danmarksadresser.dk/regler-og-vejledning/

Data of street names in denmark
http://dawa.aws.dk/vejstykker?format=json
(csv and json)

Current output:
'36192 Carlo Plains\nNew Samhaven, DC 76441'

Real format:
Streetname streetnumber
zipcode cityname

Correct Example:
Kastanjevej 38
2832 Solvang

#### fake.building_number() ####
Description: Looks ok, but never prepend zeros.
Numbers don’t go higher than 1000

Current output:
'02650'

Real format:
xxxx

Correct Example:
123

#### fake.city() ####
Description:
See https://pastebin.com/NcLj96e7 for a pretty and 
easily accessible list of zipcode => city. (Here is an
alternative: http://www.nr.dk/danmark.html )
Current output does not look danish at all, however 
format is ok

Current output:
'Marianneview'

Real format:
Cityname

Correct Example:
Kalundborg

#### fake.city_prefix() ####
We dont have city-prefix in Denmark

#### fake.city_suffix() ####
# 'land'
We dont have city-suffix in Denmark

fake.country()
# 'Turks and Caicos Islands'
Description: Wrong country names

See a complete list of correct names here:
https://paste.ubuntu.com/p/MCgfvMSgzy/

fake.country_code(representation='alpha-2')
# 'TT'
# Looks correct

fake.military_apo()
# 'PSC 0683, Box 2308'
We dont have that in Denmark

fake.military_dpo()
# 'Unit 2847 Box 2875'
We dont have that in Denmark

fake.military_ship()
# 'USCGC'
We dont have that in Denmark

fake.military_state()
# 'AA'
Not sure what this is

fake.postalcode()
# '42407'
Should be in the format 
####, minimum number is 1000. 
See https://pastebin.com/NcLj96e7 for a complete 
list

fake.postalcode_in_state(state_abbr=None)
# '87238'
We don’t have this in Denmark

fake.postalcode_plus4()
# '32765-7452'
Not sure about this

fake.postcode()
# '89418'
See fake.postalcode()

fake.postcode_in_state(state_abbr=None)
# '73182'
We don’t have this in Denmark

fake.secondary_address()
# 'Apt. 687'
Not sure about this

fake.state()
# 'Alabama'
There are no states in Denmark

fake.state_abbr(include_territories=True)
# 'NM'
There are no states in Denmark

fake.street_address()
# '537 Frandsen Path Suite 609'
See https://www.postnord.dk/sende/praktik/udformningafbreve/
for correct format

fake.street_name()
# 'Jeppesen Well'
See https://www.postnord.dk/sende/praktik/udformningafbreve/
for correct format

fake.street_suffix()
# 'Locks'
We don’t have this in Denmark

fake.zipcode()
# '46840'
See https://pastebin.com/NcLj96e7 for a complete list

fake.zipcode_in_state(state_abbr=None)
# '73129'
There are no states in Denmark

fake.zipcode_plus4()
# '60581-2946'
Not sure about this
</pre>


Discussion:
Hi @bsdis !

The issue is that we don't have an address provider for `dk_DK` at all, and so it's falling back to `en_US`: https://github.com/joke2k/faker/tree/master/faker/providers/address

Feel free to contribute one :) The easiest way is to copy one of the existing ones and make modifications.
Allright, that makes sense. I will look into creating a danish provider :)
@bsdis The Swedish one is decent enough and should be close enough to the Danish format to copy with minimal changes ... 
Is this issue still active? I didn't find any provider for `dk_DK` and would like to help! 

Resolving patch:
diff --git a/faker/providers/address/da_DK/__init__.py b/faker/providers/address/da_DK/__init__.py
new file mode 100644
--- /dev/null
+++ b/faker/providers/address/da_DK/__init__.py
@@ -0,0 +1,107 @@
+from .. import Provider as AddressProvider
+
+
+class Provider(AddressProvider):
+
+    # Building numbers dont go higher than a 1000
+    building_number_formats = ('%##', '%#', '%')
+
+    street_name_formats = ('{{street_prefix}} {{street_suffix}}', )
+
+    street_address_formats = ('{{street_name}} {{building_number}}',)
+
+    street_prefixes = (
+        'Gade', 'Allé', 'Parkere', 'Baggade', 'Gyde', 'Motorvej',
+    )
+
+    street_suffixes = (
+        'Åbenrå', 'Adelgade', 'Lavendelstræde', 'Nygade', 'Pilestræde',
+        'Rigensgade', 'Silkegade', 'Toldbodgade', 'Blekingegade',
+        'Amalievej', 'Bülowsvej', 'Godthåbsvej', 'Howitzvej',
+        'Kingosgade', 'Martinsvej', 'Rolighedsvej', 'Schønbergsgade',
+        'Åboulevard', 'Ewaldsgade', 'Heinesgade', 'Kapelvej',
+    )
+
+    address_formats = ("{{street_address}}\n{{postcode}} {{city}}", )
+
+    # Postcode should be formatted as described in http://www.nr.dk/danmark.html
+    postcode_formats = ('%###', )
+
+    city_formats = ('{{city_name}}', )
+
+    cities = (
+        'Copenhagen', 'Aarhus', 'Odense', 'Aalborg', 'Esbjerg', 'Randers',
+        'Kolding', 'Horsens', 'Vejle', 'Roskilde', 'Herning', 'Hørsholm',
+        'Elsinore', 'Silkeborg', 'Næstved', 'Fredericia', 'Viborg', 'Køge',
+        'Holstebro', 'Taastrup', 'Slagelse', 'Hillerød', 'Holbæk', 'Sønderborg',
+        'Svendborg', 'Hjørring', 'Frederikshavn', 'Nørresundby', 'Ringsted',
+        'Haderslev', 'Stenløse', 'Skive', 'Birkerød', 'Farum', 'Smørumnedre',
+        'Skanderborg', 'Nyborg', 'Nykøbing F', 'Lillerød', 'Kalundborg',
+        'Frederikssund', 'Aabenraa', 'Solrød Strand', 'Ikast', 'Middelfart',
+        'Grenaa', 'Korsør', 'Varde', 'Rønne', 'Thisted',
+    )
+
+    countries = (
+        'Afghanistan', 'Albanien', 'Algeriet', 'Amerikanska Samoa', 'Andorra',
+        'Angola', 'Anguilla', 'Antarktis', 'Antigua och Barbuda', 'Argentina',
+        'Armenien', 'Aruba', 'Ascension', 'Australien', 'Azerbajdzjan',
+        'Bahamas', 'Bahrain', 'Bangladesh', 'Barbados', 'Belarus', 'Belgien',
+        'Belize', 'Benin', 'Bermuda', 'Bhutan', 'Bolivia', 'Bosnien och Hercegovina',
+        'Botswana', 'Brasilien', 'Brittiska Jungfruöarna', 'Brunei',
+        'Bulgarien', 'Burkina Faso', 'Burma', 'Burundi', 'Caymanöarna',
+        'Centralafrikanska republiken', 'Chile', 'Colombia', 'Cooköarna',
+        'Costa Rica', 'Cypern', 'Danmark', 'Diego Garcia', 'Djibouti',
+        'Dominica', 'Dominikanska republiken', 'Ecuador', 'Egypten',
+        'Ekvatorialguinea', 'Elfenbenskusten', 'El Salvador', 'Eritrea',
+        'Estland', 'Etiopien', 'England', 'Falklandsöarna', 'Fiji',
+        'Filippinerna', 'Finland', 'Frankrike', 'Franska Guyana',
+        'Franska Polynesien', 'Färöarna', 'Förenade Arabemiraten', 'Gabon',
+        'Gambia', 'Georgien', 'Ghana', 'Gibraltar', 'Grekland', 'Grenada',
+        'Grönland', 'Guadeloupe', 'Guatemala', 'Guinea', 'Guinea-Bissau',
+        'Guyana', 'Haiti', 'Honduras', 'Hongkong', 'Indien', 'Indonesien',
+        'Irak', 'Iran', 'Irland', 'Island', 'Israel', 'Italien', 'Jamaica',
+        'Japan', 'Jemen', 'Jordanien', 'Kambodja', 'Kamerun', 'Kanada',
+        'Kap Verde', 'Kazakstan', 'Kenya', 'Kina', 'Kirgizistan', 'Kiribati',
+        'Komorerna', 'Kongo-Brazzaville', 'Kongo-Kinshasa', 'Kosovo',
+        'Kroatien', 'Kuba', 'Kuwait', 'Laos', 'Lesotho', 'Lettland', 'Libanon',
+        'Liberia', 'Libyen', 'Liechtenstein', 'Litauen', 'Luxemburg', 'Macao',
+        'Madagaskar', 'Makedonien', 'Malawi', 'Malaysia', 'Maldiverna', 'Mali',
+        'Malta', 'Marianerna', 'Marocko', 'Marshallöarna', 'Martinique',
+        'Mauretanien', 'Mauritius', 'Mayotte', 'Mexiko', 'Midwayöarna',
+        'Mikronesiens federerade stater', 'Moçambique', 'Moldavien', 'Monaco',
+        'Mongoliet', 'Montenegro', 'Montserrat', 'Namibia', 'Nauru',
+        'Nederländerna', 'Nederländska Antillerna', 'Nepal',
+        'Nicaragua', 'Niger', 'Nigeria', 'Niue', 'Nordkorea', 'Nordmarianerna',
+        'Norfolkön', 'Norge', 'Nya Kaledonien', 'Nya Zeeland', 'Oman',
+        'Pakistan', 'Palau', 'Palestina', 'Panama', 'Papua Nya Guinea',
+        'Paraguay', 'Peru', 'Pitcairnöarna', 'Polen', 'Portugal', 'Qatar',
+        'Réunion', 'Rumänien', 'Rwanda', 'Ryssland', 'Saint Kitts och Nevis',
+        'Saint Lucia', 'Saint-Pierre och Miquelon',
+        'Saint Vincent och Grenadinerna', 'Salomonöarna', 'Samoa',
+        'Sankta Helena', 'San Marino', 'São Tomé och Príncipe',
+        'Saudiarabien', 'Schweiz', 'Senegal', 'Serbien', 'Seychellerna',
+        'SierraLeone', 'Singapore', 'Sint Maarten', 'Slovakien', 'Slovenien',
+        'Somalia', 'Spanien', 'Sri Lanka', 'Storbritannien', 'Sudan',
+        'Surinam', 'Sverige', 'Swaziland', 'Sydafrika', 'Sydkorea', 'Sydsudan',
+        'Syrien', 'Tadzjikistan', 'Taiwan', 'Tanzania', 'Tchad', 'Thailand',
+        'Tjeckien', 'Togo', 'Tokelauöarna', 'Tonga', 'Trinidad och Tobago',
+        'Tunisien', 'Turkiet', 'Turkmenistan', 'Turks-och Caicosöarna',
+        'Tuvalu', 'Tyskland', 'Uganda', 'Ukraina', 'Ungern', 'Uruguay', 'USA',
+        'Uzbekistan', 'Vanuatu', 'Vatikanstaten', 'Venezuela', 'Vietnam',
+        'Wake', 'Wallis-och Futunaöarna', 'Zambia', 'Zimbabwe',
+        'Österrike', 'Östtimor',
+    )
+
+    # Known as regions in Denmark
+    states = (
+        'Hovedstaden', 'Midtjylland', 'Nordjylland', 'Sjælland', 'Syddanmark',
+    )
+
+    def street_prefix(self):
+        return self.random_element(self.street_prefixes)
+
+    def city_name(self):
+        return self.random_element(self.cities)
+
+    def state(self):
+        return self.random_element(self.states)


Test patch:
diff --git a/tests/providers/test_address.py b/tests/providers/test_address.py
--- a/tests/providers/test_address.py
+++ b/tests/providers/test_address.py
@@ -7,6 +7,7 @@
 from ukpostcodeparser.parser import parse_uk_postcode
 
 from faker.providers.address.cs_CZ import Provider as CsCzAddressProvider
+from faker.providers.address.da_DK import Provider as DaDkAddressProvider
 from faker.providers.address.de_AT import Provider as DeAtAddressProvider
 from faker.providers.address.de_DE import Provider as DeDeAddressProvider
 from faker.providers.address.el_GR import Provider as ElGrAddressProvider
@@ -110,6 +111,34 @@ def test_city_with_postcode(self, faker, num_samples):
             assert match.group('city') in CsCzAddressProvider.cities
 
 
+class TestDaDk:
+    """Test dk_DK address provider methods"""
+
+    def test_street_prefix(self, faker, num_samples):
+        for _ in range(num_samples):
+            street_prefix = faker.street_prefix()
+            assert isinstance(street_prefix, str)
+            assert street_prefix in DaDkAddressProvider.street_prefixes
+
+    def test_city_name(self, faker, num_samples):
+        for _ in range(num_samples):
+            city = faker.city_name()
+            assert isinstance(city, str)
+            assert city in DaDkAddressProvider.cities
+
+    def test_state(self, faker, num_samples):
+        for _ in range(num_samples):
+            state = faker.state()
+            assert isinstance(state, str)
+            assert state in DaDkAddressProvider.states
+
+    def test_postcode(self, faker, num_samples):
+        for _ in range(num_samples):
+            postcode = faker.postcode()
+            assert isinstance(postcode, str)
+            assert re.fullmatch(r"\d{4}", postcode)
+
+
 class TestDeAt:
     """Test de_AT address provider methods"""