1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30 package dk.sosi.seal.pki;
31
32 import java.util.HashMap;
33 import java.util.HashSet;
34 import java.util.Map;
35 import java.util.Set;
36
37
38
39
40
41
42
43
44
45
46
47 public class DistinguishedName {
48 private static final String COMMONNAME = "cn";
49
50 private static final String COUNTRY = "c";
51
52 private static final Map<String, String> oidNameToCanonicalOidName = new HashMap<String, String>();
53
54 private static final String ORGANIZATION = "o";
55
56 private static final String ORGANIZATIONALUNIT = "ou";
57
58 private static final String SERIALNUMBER = "serialNumber";
59
60 private static final String STATE = "st";
61 static {
62 oidNameToCanonicalOidName.put(COMMONNAME, COMMONNAME);
63 oidNameToCanonicalOidName.put("commonName", COMMONNAME);
64 oidNameToCanonicalOidName.put("CN", COMMONNAME);
65
66 oidNameToCanonicalOidName.put(ORGANIZATIONALUNIT, ORGANIZATIONALUNIT);
67 oidNameToCanonicalOidName.put("OU", ORGANIZATIONALUNIT);
68
69 oidNameToCanonicalOidName.put(ORGANIZATION, ORGANIZATION);
70 oidNameToCanonicalOidName.put("O", ORGANIZATION);
71
72 oidNameToCanonicalOidName.put(SERIALNUMBER, SERIALNUMBER);
73 oidNameToCanonicalOidName.put(SERIALNUMBER.toUpperCase(), SERIALNUMBER);
74 oidNameToCanonicalOidName.put("SN", SERIALNUMBER);
75
76 oidNameToCanonicalOidName.put(COUNTRY, COUNTRY);
77 oidNameToCanonicalOidName.put("C", COUNTRY);
78
79 oidNameToCanonicalOidName.put("ST", STATE);
80 }
81
82 private String distinguishedName;
83
84 private final Map<String, Set<String>> oidToValue = new HashMap<String, Set<String>>();
85
86
87
88
89
90
91
92
93
94 public DistinguishedName(String distinguishedName) throws PKIException {
95 super();
96
97 this.distinguishedName = distinguishedName;
98 parse();
99 }
100
101 public boolean equals(Object obj) {
102 if(!(obj instanceof DistinguishedName)) {
103 return false;
104 }
105 DistinguishedName other = (DistinguishedName)obj;
106 return other.oidToValue.equals(this.oidToValue);
107 }
108
109 public String getCommonName() {
110 return getSingleValueByKey(COMMONNAME);
111 }
112
113 public String getCountry() {
114 return getSingleValueByKey(COUNTRY);
115 }
116
117 public String getOrganization() {
118 return getSingleValueByKey(ORGANIZATION);
119 }
120
121 public String getOrganizationalUnit() {
122 return getSingleValueByKey(ORGANIZATIONALUNIT);
123 }
124
125 public Set<String> getOrganizationalUnits() {
126 return getMultiValueByKey(ORGANIZATIONALUNIT);
127 }
128
129 public String getSubjectSerialNumber() {
130 return getSingleValueByKey(SERIALNUMBER);
131 }
132
133 public int hashCode() {
134 return oidToValue.hashCode();
135 }
136
137 private void addRDN(String name, String value) {
138 String attr = oidNameToCanonicalOidName.get(name);
139 if(oidToValue.containsKey(attr)) {
140 oidToValue.get(attr).add(value);
141 } else {
142 HashSet<String> values = new HashSet<String>();
143 values.add(value);
144 oidToValue.put(attr, values);
145 }
146 }
147
148 private Set<String> getMultiValueByKey(String key) {
149 Set<String> val = oidToValue.get(key);
150 if(val == null) {
151 return null;
152 }
153 return val;
154 }
155
156 private String getSingleValueByKey(String key) {
157 Set<String> val = oidToValue.get(key);
158 if(val == null) {
159 return null;
160 }
161 return val.iterator().next();
162 }
163
164 private void parse() {
165 String[] rdns = distinguishedName.split(",");
166
167 for (int i = 0; i < rdns.length; i++) {
168
169 if(rdns[i].indexOf('"') > 0 && !rdns[i].endsWith("\"")) {
170 rdns[i + 1] = rdns[i] + "," + rdns[i + 1];
171 } else {
172 String[] fields;
173 fields = rdns[i].split("[ ]?\\+[ ]?");
174 if(fields.length > 1) {
175 for (int j = 0; j < fields.length; j++) {
176 parseRDN(fields[j]);
177 }
178 } else {
179 parseRDN(rdns[i]);
180 }
181 }
182 }
183
184 }
185
186 private void parseRDN(String rdn) throws PKIException {
187 String[] parts = rdn.split("=");
188 String name = parts[0].trim();
189 String value = parts[1];
190 if(oidNameToCanonicalOidName.get(name) != null) {
191 addRDN(name, value);
192 } else {
193 throw new PKIException("Failed to parse DN: Unknown attribute: " + name);
194 }
195 }
196 }