1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21 package org.apache.directory.api.ldap.model.ldif.anonymizer;
22
23
24 import java.util.Arrays;
25 import java.util.HashMap;
26 import java.util.Map;
27 import java.util.Set;
28
29 import org.apache.directory.api.ldap.model.entry.Attribute;
30 import org.apache.directory.api.ldap.model.entry.DefaultAttribute;
31 import org.apache.directory.api.ldap.model.entry.StringValue;
32 import org.apache.directory.api.ldap.model.entry.Value;
33 import org.apache.directory.api.ldap.model.exception.LdapInvalidAttributeValueException;
34
35
36
37
38
39
40
41 public class IntegerAnonymizer extends AbstractAnonymizer<String>
42 {
43
44 private Map<Integer, String> latestIntegerMap;
45
46
47
48
49 public IntegerAnonymizer()
50 {
51 latestIntegerMap = new HashMap<>();
52 }
53
54
55
56
57
58
59
60 public IntegerAnonymizer( Map<Integer, String> latestIntegerMap )
61 {
62 if ( latestIntegerMap == null )
63 {
64 this.latestIntegerMap = new HashMap<>();
65 }
66 else
67 {
68 this.latestIntegerMap = latestIntegerMap;
69 }
70 }
71
72
73
74
75 @Override
76 public Attribute anonymize( Map<Value<String>, Value<String>> valueMap, Set<Value<String>> valueSet, Attribute attribute )
77 {
78 Attribute result = new DefaultAttribute( attribute.getAttributeType() );
79
80 for ( Value<?> value : attribute )
81 {
82 if ( value instanceof StringValue )
83 {
84 Value<String> anonymized = valueMap.get( value );
85
86 if ( anonymized != null )
87 {
88 try
89 {
90 result.add( anonymized );
91 }
92 catch ( LdapInvalidAttributeValueException e )
93 {
94
95 }
96 }
97 else
98 {
99 String strValue = value.getNormValue().toString();
100 String newValue = computeNewIntegerValue( strValue );
101
102 try
103 {
104 result.add( newValue );
105 Value<String> anonValue = new StringValue( attribute.getAttributeType(), newValue );
106 valueMap.put( ( Value<String> ) value, anonValue );
107 valueSet.add( anonValue );
108 }
109 catch ( LdapInvalidAttributeValueException e )
110 {
111
112 }
113 }
114 }
115 }
116
117 return result;
118 }
119
120
121
122
123
124 public Map<Integer, String> getLatestIntegerMap()
125 {
126 return latestIntegerMap;
127 }
128
129
130
131
132
133
134 public void setLatestIntegerMap( Map<Integer, String> latestIntegerMap )
135 {
136 this.latestIntegerMap = latestIntegerMap;
137 }
138
139
140
141
142
143
144
145
146 private String computeNewIntegerValue( String valStr )
147 {
148 int length = valStr.length();
149 String latestInteger = latestIntegerMap.get( length );
150
151 if ( latestInteger == null )
152 {
153
154 char[] newValue = new char[length];
155
156 Arrays.fill( newValue, '9' );
157
158 String anonymizedValue = new String( newValue );
159 latestIntegerMap.put( length, anonymizedValue );
160
161 return anonymizedValue;
162 }
163 else
164 {
165
166 char[] latest = latestInteger.toCharArray();
167 boolean overflow = true;
168
169 for ( int i = length - 1; i >= 0; i-- )
170 {
171 if ( latest[i] == '0' )
172 {
173 latest[i] = '9';
174 }
175 else
176 {
177 latest[i]--;
178 overflow = false;
179 break;
180 }
181 }
182
183
184 if ( ( length > 1 ) && ( latest[0] == '0' ) )
185 {
186 throw new RuntimeException( "Overflow for " + valStr );
187 }
188
189 String anonymizedValue = new String( latest );
190
191 if ( overflow )
192 {
193
194 throw new RuntimeException( "Cannot compute a new value for " + anonymizedValue );
195 }
196
197 latestIntegerMap.put( length, anonymizedValue );
198
199 return anonymizedValue;
200 }
201 }
202 }