001/*
002 * oauth2-oidc-sdk
003 *
004 * Copyright 2012-2016, Connect2id Ltd and contributors.
005 *
006 * Licensed under the Apache License, Version 2.0 (the "License"); you may not use
007 * this file except in compliance with the License. You may obtain a copy of the
008 * License at
009 *
010 *    http://www.apache.org/licenses/LICENSE-2.0
011 *
012 * Unless required by applicable law or agreed to in writing, software distributed
013 * under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
014 * CONDITIONS OF ANY KIND, either express or implied. See the License for the
015 * specific language governing permissions and limitations under the License.
016 */
017
018package com.nimbusds.openid.connect.sdk.assurance.claims;
019
020
021import java.io.IOException;
022import java.io.InputStream;
023import java.util.Properties;
024
025import net.jcip.annotations.Immutable;
026
027import com.nimbusds.oauth2.sdk.ParseException;
028import com.nimbusds.oauth2.sdk.util.StringUtils;
029
030
031/**
032 * ISO 3166-3 country code for former countries and territories.
033 */
034@Immutable
035public final class ISO3166_3CountryCode extends CountryCode {
036        
037        
038        private static final long serialVersionUID = 614967184722743546L;
039        
040        
041        /** British Antarctic Territory */
042        public static final ISO3166_3CountryCode BQAQ = new ISO3166_3CountryCode("BQAQ");
043        
044        /** Burma */
045        public static final ISO3166_3CountryCode BUMM = new ISO3166_3CountryCode("BUMM");
046        
047        /** Byelorussian SSR */
048        public static final ISO3166_3CountryCode BYAA = new ISO3166_3CountryCode("BYAA");
049        
050        /** Canton and Enderbury Islands */
051        public static final ISO3166_3CountryCode CTKI = new ISO3166_3CountryCode("CTKI");
052        
053        /** Czechoslovakia */
054        public static final ISO3166_3CountryCode CSHH = new ISO3166_3CountryCode("CSHH");
055        
056        /** Dahomey */
057        public static final ISO3166_3CountryCode DYBJ = new ISO3166_3CountryCode("DYBJ");
058        
059        /** Dronning Maud Land */
060        public static final ISO3166_3CountryCode NQAQ = new ISO3166_3CountryCode("NQAQ");
061        
062        /** East Timor */
063        public static final ISO3166_3CountryCode TPTL = new ISO3166_3CountryCode("TPTL");
064        
065        /** France, Metropolitan */
066        public static final ISO3166_3CountryCode FXFR = new ISO3166_3CountryCode("FXFR");
067        
068        /** French Afars and Issas */
069        public static final ISO3166_3CountryCode AIDJ = new ISO3166_3CountryCode("AIDJ");
070        
071        /** French Southern and Antarctic Territories */
072        public static final ISO3166_3CountryCode FQHH = new ISO3166_3CountryCode("FQHH");
073        
074        /** German Democratic Republic */
075        public static final ISO3166_3CountryCode DDDE = new ISO3166_3CountryCode("DDDE");
076        
077        /** Gilbert Islands */
078        public static final ISO3166_3CountryCode GEHH = new ISO3166_3CountryCode("GEHH");
079        
080        /** Johnston Island */
081        public static final ISO3166_3CountryCode JTUM = new ISO3166_3CountryCode("JTUM");
082        
083        /** Midway Islands */
084        public static final ISO3166_3CountryCode MIUM = new ISO3166_3CountryCode("MIUM");
085        
086        /** Netherlands Antilles */
087        public static final ISO3166_3CountryCode ANHH = new ISO3166_3CountryCode("ANHH");
088        
089        /** Neutral Zone */
090        public static final ISO3166_3CountryCode NTHH = new ISO3166_3CountryCode("NTHH");
091        
092        /** New Hebrides */
093        public static final ISO3166_3CountryCode NHVU = new ISO3166_3CountryCode("NHVU");
094        
095        /** Pacific Islands (Trust Territory) */
096        public static final ISO3166_3CountryCode PCHH = new ISO3166_3CountryCode("PCHH");
097        
098        /** Panama Canal Zone */
099        public static final ISO3166_3CountryCode PZPA = new ISO3166_3CountryCode("PZPA");
100        
101        /** Serbia and Montenegro */
102        public static final ISO3166_3CountryCode CSXX = new ISO3166_3CountryCode("CSXX");
103        
104        /** Sikkim */
105        public static final ISO3166_3CountryCode SKIN = new ISO3166_3CountryCode("SKIN");
106        
107        /** Southern Rhodesia */
108        public static final ISO3166_3CountryCode RHZW = new ISO3166_3CountryCode("RHZW");
109        
110        /** United States Miscellaneous Pacific Islands */
111        public static final ISO3166_3CountryCode PUUM = new ISO3166_3CountryCode("PUUM");
112        
113        /** Upper Volta */
114        public static final ISO3166_3CountryCode HVBF = new ISO3166_3CountryCode("HVBF");
115        
116        /** USSR */
117        public static final ISO3166_3CountryCode SUHH = new ISO3166_3CountryCode("SUHH");
118        
119        /** Viet-Nam, Democratic Republic of */
120        public static final ISO3166_3CountryCode VDVN = new ISO3166_3CountryCode("VDVN");
121        
122        /** Wake Island */
123        public static final ISO3166_3CountryCode WKUM = new ISO3166_3CountryCode("WKUM");
124        
125        /** Yemen, Democratic */
126        public static final ISO3166_3CountryCode YDYE = new ISO3166_3CountryCode("YDYE");
127        
128        /** Yugoslavia */
129        public static final ISO3166_3CountryCode YUCS = new ISO3166_3CountryCode("YUCS");
130        
131        /** Zaire */
132        public static final ISO3166_3CountryCode ZRCD  = new ISO3166_3CountryCode("ZRCD");
133        
134        
135        /**
136         * Creates a new ISO 3166-3 country code. Normalises the code to upper
137         * case.
138         *
139         * @param value The country code value, must be four-letter.
140         */
141        public ISO3166_3CountryCode(final String value) {
142                super(value.toUpperCase());
143                if (value.length() != 4 || !StringUtils.isAlpha(value)) {
144                        throw new IllegalArgumentException("The ISO 3166-3 country code must be 4 letters");
145                }
146        }
147        
148        
149        /**
150         * Returns the former country code (the first component).
151         *
152         * @return The former country code as an ISO 3166-1 alpha-2
153         *         (two-letter) country code.
154         */
155        public ISO3166_1Alpha2CountryCode getFormerCode() {
156                
157                return new ISO3166_1Alpha2CountryCode(getFirstComponentString());
158        }
159        
160        
161        /**
162         * Returns the new country code (the second component), unless the
163         * former country is divided and there is no single successor country
164         * (indicated by an "HH" or "XX" code).
165         *
166         * @return The new country code as an ISO 3166-1 alpha-2 (two-letter)
167         *         country code, {@code null} if the former country is divided.
168         *         and there is no single successor country.
169         */
170        public ISO3166_1Alpha2CountryCode getNewCode() {
171                
172                if ("HH".equals(getSecondComponentString()) || "XX".equals(getSecondComponentString())) {
173                        return null;
174                }
175                
176                return new ISO3166_1Alpha2CountryCode(getSecondComponentString());
177        }
178        
179        
180        /**
181         * Returns the first component (the first two letters) representing the
182         * former country code.
183         *
184         * @return The first component as a string.
185         */
186        public String getFirstComponentString() {
187                
188                return getValue().substring(0, 2);
189        }
190        
191        
192        /**
193         * Returns the second component (the last two letters).
194         *
195         * @return The second component as a string.
196         */
197        public String getSecondComponentString() {
198                
199                return getValue().substring(2, 4);
200        }
201        
202        
203        /**
204         * The {@code iso3166_3-codes.properties} resource.
205         */
206        private static final Properties CODES_RESOURCE = new Properties();
207        
208        
209        /**
210         * Returns the country name if available in the
211         * {@code iso3166_3-codes.properties} resource.
212         *
213         * @return The country name, {@code null} if not available.
214         */
215        public String getCountryName() {
216                
217                if (CODES_RESOURCE.isEmpty()) {
218                        InputStream is = getClass().getClassLoader().getResourceAsStream("iso3166_3-codes.properties");
219                        try {
220                                CODES_RESOURCE.load(is);
221                        } catch (IOException e) {
222                                return null;
223                        }
224                }
225                
226                return CODES_RESOURCE.getProperty(getValue());
227        }
228        
229        
230        @Override
231        public boolean equals(final Object object) {
232                
233                return object instanceof ISO3166_3CountryCode &&
234                        this.toString().equals(object.toString());
235        }
236        
237        
238        /**
239         * Parses an ISO 3166-3 country code.
240         *
241         * @param s The string to parse. Must not be {@code null}.
242         *
243         * @return The ISO 3166-3 country code.
244         *
245         * @throws ParseException If parsing failed.
246         */
247        public static ISO3166_3CountryCode parse(final String s)
248                throws ParseException {
249                
250                try {
251                        return new ISO3166_3CountryCode(s);
252                } catch (IllegalArgumentException e) {
253                        throw new ParseException(e.getMessage());
254                }
255        }
256}