|
@@ -56,36 +56,31 @@ import lombok.extern.slf4j.Slf4j;
|
56
|
56
|
public class UpdateManagerImpl implements UpdateManager {
|
57
|
57
|
|
58
|
58
|
/** Collection of known update checking strategies. */
|
59
|
|
- private final List<UpdateCheckStrategy> checkers
|
60
|
|
- = new CopyOnWriteArrayList<UpdateCheckStrategy>();
|
|
59
|
+ private final List<UpdateCheckStrategy> checkers = new CopyOnWriteArrayList<>();
|
61
|
60
|
|
62
|
61
|
/** Collection of known update retrieval strategies. */
|
63
|
|
- private final List<UpdateRetrievalStategy> retrievers
|
64
|
|
- = new CopyOnWriteArrayList<UpdateRetrievalStategy>();
|
|
62
|
+ private final List<UpdateRetrievalStategy> retrievers = new CopyOnWriteArrayList<>();
|
65
|
63
|
|
66
|
64
|
/** Collection of known update installation strategies. */
|
67
|
|
- private final List<UpdateInstallationStrategy> installers
|
68
|
|
- = new CopyOnWriteArrayList<UpdateInstallationStrategy>();
|
|
65
|
+ private final List<UpdateInstallationStrategy> installers = new CopyOnWriteArrayList<>();
|
69
|
66
|
|
70
|
|
- /** Map of known component names to their components. */
|
71
|
|
- private final Map<String, UpdateComponent> components
|
72
|
|
- = new HashMap<String, UpdateComponent>();
|
|
67
|
+ /** Map of known component names to their components. Guarded by {@link #componentsLock}. */
|
|
68
|
+ private final Map<String, UpdateComponent> components = new HashMap<>();
|
73
|
69
|
|
74
|
70
|
/** Listener used to proxy retrieval events. */
|
75
|
|
- private final UpdateRetrievalListener retrievalListener
|
76
|
|
- = new RetrievalListener();
|
|
71
|
+ private final UpdateRetrievalListener retrievalListener = new RetrievalListener();
|
77
|
72
|
|
78
|
73
|
/** Listener used to proxy setRetrievalResult events. */
|
79
|
|
- private final UpdateInstallationListener installationListener
|
80
|
|
- = new InstallListener();
|
|
74
|
+ private final UpdateInstallationListener installationListener = new InstallListener();
|
81
|
75
|
|
82
|
76
|
/** Cache of update check results. */
|
83
|
|
- private final Map<UpdateComponent, UpdateCheckResult> checkResults
|
84
|
|
- = new HashMap<UpdateComponent, UpdateCheckResult>();
|
|
77
|
+ private final Map<UpdateComponent, UpdateCheckResult> checkResults = new HashMap<>();
|
85
|
78
|
|
86
|
79
|
/** Cache of retrieval results. */
|
87
|
|
- private final Map<UpdateComponent, UpdateRetrievalResult> retrievalResults
|
88
|
|
- = new HashMap<UpdateComponent, UpdateRetrievalResult>();
|
|
80
|
+ private final Map<UpdateComponent, UpdateRetrievalResult> retrievalResults = new HashMap<>();
|
|
81
|
+
|
|
82
|
+ /** Lock for accessing {@link #components}. */
|
|
83
|
+ private final Object componentsLock = new Object();
|
89
|
84
|
|
90
|
85
|
/** Executor to use to schedule retrieval and installation jobs. */
|
91
|
86
|
private final Executor executor;
|
|
@@ -125,14 +120,19 @@ public class UpdateManagerImpl implements UpdateManager {
|
125
|
120
|
@Override
|
126
|
121
|
public void addComponent(final UpdateComponent component) {
|
127
|
122
|
log.trace("Adding new component: {}", component);
|
128
|
|
- this.components.put(component.getName(), component);
|
|
123
|
+ synchronized (componentsLock) {
|
|
124
|
+ this.components.put(component.getName(), component);
|
|
125
|
+ }
|
129
|
126
|
}
|
130
|
127
|
|
131
|
128
|
/** {@inheritDoc} */
|
132
|
129
|
@Override
|
133
|
130
|
public void removeComponent(final UpdateComponent component) {
|
134
|
131
|
log.trace("Removing component: {}", component);
|
135
|
|
- this.components.remove(component.getName());
|
|
132
|
+ synchronized (componentsLock) {
|
|
133
|
+ this.components.remove(component.getName());
|
|
134
|
+ }
|
|
135
|
+
|
136
|
136
|
this.checkResults.remove(component);
|
137
|
137
|
this.retrievalResults.remove(component);
|
138
|
138
|
}
|
|
@@ -140,7 +140,9 @@ public class UpdateManagerImpl implements UpdateManager {
|
140
|
140
|
/** {@inheritDoc} */
|
141
|
141
|
@Override
|
142
|
142
|
public Collection<UpdateComponent> getComponents() {
|
143
|
|
- return Collections.unmodifiableCollection(this.components.values());
|
|
143
|
+ synchronized (componentsLock) {
|
|
144
|
+ return Collections.unmodifiableCollection(this.components.values());
|
|
145
|
+ }
|
144
|
146
|
}
|
145
|
147
|
|
146
|
148
|
/** {@inheritDoc} */
|
|
@@ -152,27 +154,36 @@ public class UpdateManagerImpl implements UpdateManager {
|
152
|
154
|
/** {@inheritDoc} */
|
153
|
155
|
@Override
|
154
|
156
|
public void checkForUpdates() {
|
155
|
|
- final Collection<Map<UpdateComponent, UpdateCheckResult>> results
|
156
|
|
- = new ArrayList<Map<UpdateComponent, UpdateCheckResult>>();
|
|
157
|
+ final Collection<Map<UpdateComponent, UpdateCheckResult>> results = new ArrayList<>();
|
157
|
158
|
|
158
|
159
|
log.info("Checking for updates for {} components using {} strategies",
|
159
|
160
|
components.size(), checkers.size());
|
160
|
161
|
log.trace("Components: {}", components);
|
161
|
162
|
log.trace("Strategies: {}", checkers);
|
162
|
163
|
|
163
|
|
- final List<UpdateComponent> enabledComponents
|
164
|
|
- = new ArrayList<UpdateComponent>(components.size());
|
165
|
|
-
|
166
|
|
- for (UpdateComponent component : components.values()) {
|
167
|
|
- if (policy.canCheck(component)) {
|
168
|
|
- fireUpdateStatusChanged(component, UpdateStatus.CHECKING, 0);
|
169
|
|
- enabledComponents.add(component);
|
170
|
|
- } else {
|
171
|
|
- log.debug("Checking for updates for {} denied by policy", component.getName());
|
172
|
|
- fireUpdateStatusChanged(component, UpdateStatus.CHECKING_NOT_PERMITTED, 0);
|
|
164
|
+ final List<UpdateComponent> enabledComponents = new ArrayList<>(components.size());
|
|
165
|
+ final List<UpdateComponent> disabledComponents = new ArrayList<>(components.size());
|
|
166
|
+
|
|
167
|
+ synchronized (componentsLock) {
|
|
168
|
+ for (UpdateComponent component : components.values()) {
|
|
169
|
+ if (policy.canCheck(component)) {
|
|
170
|
+ enabledComponents.add(component);
|
|
171
|
+ } else {
|
|
172
|
+ log.debug("Checking for updates for {} denied by policy", component.getName());
|
|
173
|
+ disabledComponents.add(component);
|
|
174
|
+ }
|
173
|
175
|
}
|
174
|
176
|
}
|
175
|
177
|
|
|
178
|
+ // Fire the listeners now we don't care about concurrent modifications.
|
|
179
|
+ for (UpdateComponent component : enabledComponents) {
|
|
180
|
+ fireUpdateStatusChanged(component, UpdateStatus.CHECKING, 0);
|
|
181
|
+ }
|
|
182
|
+
|
|
183
|
+ for (UpdateComponent component : disabledComponents) {
|
|
184
|
+ fireUpdateStatusChanged(component, UpdateStatus.CHECKING_NOT_PERMITTED, 0);
|
|
185
|
+ }
|
|
186
|
+
|
176
|
187
|
for (UpdateCheckStrategy strategy : checkers) {
|
177
|
188
|
results.add(strategy.checkForUpdates(enabledComponents));
|
178
|
189
|
}
|