1
1
package qz .ui .component ;
2
2
3
- import org .joor .Reflect ;
4
3
import qz .auth .Certificate ;
5
4
import qz .common .Constants ;
6
5
import qz .ui .Themeable ;
7
6
8
7
import javax .swing .*;
9
8
import java .awt .*;
10
- import java .time .Instant ;
9
+ import java .awt .event .*;
10
+ import java .time .*;
11
11
import java .time .temporal .ChronoUnit ;
12
+ import java .util .TimeZone ;
13
+ import java .util .function .Function ;
14
+
15
+ import static qz .auth .Certificate .*;
12
16
13
17
/**
14
18
* Created by Tres on 2/22/2015.
15
19
* Displays Certificate information in a JTable
16
20
*/
17
21
public class CertificateTable extends DisplayTable implements Themeable {
22
+ private Certificate cert ;
23
+
24
+ private static final TimeZone DEFAULT_TIME_ZONE = TimeZone .getTimeZone ("UTC" );
25
+ private static final TimeZone ALTERNATE_TIME_ZONE = TimeZone .getDefault ();
26
+ private Instant warn ;
27
+ private Instant now ;
18
28
19
- /**
20
- * Certificate fields to be displayed (and the corresponding function to Reflect upon)
21
- */
22
29
enum CertificateField {
23
- ORGANIZATION ("Organization" , " getOrganization" ),
24
- COMMON_NAME ("Common Name" , " getCommonName" ),
25
- TRUSTED ("Trusted" , " isTrusted" ),
26
- VALID_FROM ("Valid From" , " getValidFrom" ),
27
- VALID_TO ("Valid To" , " getValidTo" ),
28
- FINGERPRINT ("Fingerprint" , " getFingerprint" );
30
+ ORGANIZATION ("Organization" , ( Certificate cert ) -> cert . getOrganization () ),
31
+ COMMON_NAME ("Common Name" , ( Certificate cert ) -> cert . getCommonName () ),
32
+ TRUSTED ("Trusted" , ( Certificate cert ) -> cert . isTrusted () ),
33
+ VALID_FROM ("Valid From" , ( Certificate cert ) -> cert . getValidFrom () ),
34
+ VALID_TO ("Valid To" , ( Certificate cert ) -> cert . getValidTo () ),
35
+ FINGERPRINT ("Fingerprint" , ( Certificate cert ) -> cert . getFingerprint () );
29
36
30
37
String description ;
31
- String callBack ;
38
+ Function <Certificate , Object > getter ;
39
+ TimeZone timeZone = DEFAULT_TIME_ZONE ; // Date fields only
32
40
33
- CertificateField (String description , String callBack ) {
41
+ CertificateField (String description , Function < Certificate , Object > getter ) {
34
42
this .description = description ;
35
- this .callBack = callBack ;
43
+ this .getter = getter ;
36
44
}
37
45
38
- /**
39
- * Returns the <code>String</code> value associated with this certificate field
40
- *
41
- * @return Certificate field such as "commonName"
42
- */
43
46
public String getValue (Certificate cert ) {
44
- if (cert == null ) {
45
- return "" ;
46
- }
47
-
48
- Reflect reflect = Reflect .on (cert ).call (callBack );
49
- Object value = reflect == null ? null :reflect .get ();
50
- if (value == null ) {
51
- return "" ;
47
+ String certFieldValue = getter .apply (cert ).toString ();
48
+ switch (this ) {
49
+ case VALID_FROM :
50
+ case VALID_TO :
51
+ if (!certFieldValue .equals ("Not Provided" )) {
52
+ try {
53
+ // Parse the date string as UTC (Z/GMT)
54
+ ZonedDateTime utcTime = LocalDateTime .from (DATE_PARSE .parse (certFieldValue )).atZone (ZoneOffset .UTC );
55
+ // Shift to the new timezone
56
+ ZonedDateTime zonedTime = Instant .from (utcTime ).atZone (timeZone .toZoneId ());
57
+ // Append a short timezone name e.g. "EST"
58
+ return DATE_PARSE .format (zonedTime ) + " " + timeZone .getDisplayName (false , TimeZone .SHORT );
59
+ } catch (DateTimeException ignore ) {}
60
+ }
61
+ // fallthrough
62
+ default :
63
+ return certFieldValue ;
52
64
}
53
- return value .toString ();
54
65
}
55
66
56
67
@ Override
@@ -65,16 +76,47 @@ public String getDescription() {
65
76
public static int size () {
66
77
return values ().length ;
67
78
}
68
- }
69
79
70
- private Certificate cert ;
71
-
72
- private Instant warn ;
73
- private Instant now ;
80
+ public void toggleTimeZone () {
81
+ switch (this ) {
82
+ case VALID_TO :
83
+ case VALID_FROM :
84
+ this .timeZone = (timeZone == DEFAULT_TIME_ZONE ? ALTERNATE_TIME_ZONE :DEFAULT_TIME_ZONE );
85
+ break ;
86
+ default :
87
+ throw new UnsupportedOperationException ("TimeZone is only supported for date fields" );
88
+ }
89
+ }
90
+ }
74
91
75
92
public CertificateTable (IconCache iconCache ) {
76
93
super (iconCache );
77
94
setDefaultRenderer (Object .class , new CertificateTableCellRenderer ());
95
+ addMouseListener (new MouseAdapter () {
96
+ Point loc = new Point (-1 , -1 );
97
+
98
+ @ Override
99
+ public void mousePressed (MouseEvent e ) {
100
+ super .mousePressed (e );
101
+ JTable target = (JTable )e .getSource ();
102
+ int x = target .getSelectedColumn ();
103
+ int y = target .getSelectedRow ();
104
+ // Only trigger after the cell is click AND highlighted.
105
+ if (loc .distance (x , y ) == 0 ) {
106
+ CertificateField rowKey = (CertificateField )target .getValueAt (y , 0 );
107
+ switch (rowKey ) {
108
+ case VALID_FROM :
109
+ case VALID_TO :
110
+ rowKey .toggleTimeZone ();
111
+ refreshComponents ();
112
+ changeSelection (y , x , false , false );
113
+ break ;
114
+ }
115
+ }
116
+ loc .setLocation (x , y );
117
+ }
118
+ });
119
+
78
120
}
79
121
80
122
public void setCertificate (Certificate cert ) {
@@ -116,7 +158,6 @@ public void autoSize() {
116
158
super .autoSize (CertificateField .size (), 2 );
117
159
}
118
160
119
-
120
161
/** Custom cell renderer for JTable to allow colors and styles not directly available in a JTable */
121
162
private class CertificateTableCellRenderer extends StyledTableCellRenderer {
122
163
@@ -126,7 +167,22 @@ public Component getTableCellRendererComponent(JTable table, Object value, boole
126
167
127
168
// First Column
128
169
if (value instanceof CertificateField ) {
129
- label = stylizeLabel (STATUS_NORMAL , label , isSelected );
170
+ switch ((CertificateField )value ) {
171
+ case VALID_FROM :
172
+ boolean futureExpiration = cert .getValidFromDate ().isAfter (now );
173
+ label = stylizeLabel (futureExpiration ? STATUS_WARNING :STATUS_NORMAL , label , isSelected , "future inception" );
174
+ break ;
175
+ case VALID_TO :
176
+ boolean expiresSoon = cert .getValidToDate ().isBefore (warn );
177
+ boolean expired = cert .getValidToDate ().isBefore (now );
178
+ String reason = expired ? "expired" :(expiresSoon ? "expires soon" :null );
179
+
180
+ label = stylizeLabel (expiresSoon || expired ? STATUS_WARNING :STATUS_NORMAL , label , isSelected , reason );
181
+ break ;
182
+ default :
183
+ label = stylizeLabel (STATUS_NORMAL , label , isSelected );
184
+ break ;
185
+ }
130
186
if (iconCache != null ) {
131
187
label .setIcon (iconCache .getIcon (IconCache .Icon .FIELD_ICON ));
132
188
}
@@ -153,17 +209,14 @@ public Component getTableCellRendererComponent(JTable table, Object value, boole
153
209
return stylizeLabel (!cert .isValid ()? STATUS_WARNING :STATUS_TRUSTED , label , isSelected );
154
210
case VALID_FROM :
155
211
boolean futureExpiration = cert .getValidFromDate ().isAfter (now );
156
- return stylizeLabel (futureExpiration ? STATUS_WARNING :STATUS_NORMAL , label , isSelected , "future inception" );
212
+ return stylizeLabel (futureExpiration ? STATUS_WARNING :STATUS_NORMAL , label , isSelected );
157
213
case VALID_TO :
158
214
boolean expiresSoon = cert .getValidToDate ().isBefore (warn );
159
215
boolean expired = cert .getValidToDate ().isBefore (now );
160
- String reason = expired ? "expired" :(expiresSoon ? "expires soon" :null );
161
- return stylizeLabel (expiresSoon || expired ? STATUS_WARNING :STATUS_NORMAL , label , isSelected , reason );
216
+ return stylizeLabel (expiresSoon || expired ? STATUS_WARNING :STATUS_NORMAL , label , isSelected );
162
217
default :
163
218
return stylizeLabel (STATUS_NORMAL , label , isSelected );
164
219
}
165
220
}
166
-
167
221
}
168
-
169
222
}
0 commit comments