View Javadoc
1   // =================== DO NOT EDIT THIS FILE ====================
2   //  Generated by Modello Velocity from merger.vm
3   //  template, any modifications will be overwritten.
4   // ==============================================================
5   package org.apache.maven.settings.v4;
6   
7   import java.io.ObjectStreamException;
8   import java.util.AbstractList;
9   import java.util.ArrayList;
10  import java.util.Collection;
11  import java.util.HashMap;
12  import java.util.Iterator;
13  import java.util.LinkedHashMap;
14  import java.util.List;
15  import java.util.Map;
16  import java.util.Objects;
17  import java.util.function.BinaryOperator;
18  import java.util.function.Function;
19  import java.util.stream.Collectors;
20  
21  import org.apache.maven.api.annotations.Generated;
22  import org.apache.maven.api.xml.XmlNode;
23  import org.apache.maven.api.settings.TrackableBase;
24  import org.apache.maven.api.settings.IdentifiableBase;
25  import org.apache.maven.api.settings.Settings;
26  import org.apache.maven.api.settings.Proxy;
27  import org.apache.maven.api.settings.Server;
28  import org.apache.maven.api.settings.Mirror;
29  import org.apache.maven.api.settings.Profile;
30  import org.apache.maven.api.settings.Activation;
31  import org.apache.maven.api.settings.RepositoryBase;
32  import org.apache.maven.api.settings.Repository;
33  import org.apache.maven.api.settings.RepositoryPolicy;
34  import org.apache.maven.api.settings.ActivationProperty;
35  import org.apache.maven.api.settings.ActivationOS;
36  import org.apache.maven.api.settings.ActivationFile;
37  import org.apache.maven.api.settings.InputLocation;
38  import org.apache.maven.api.settings.InputSource;
39  
40  @Generated
41  public class SettingsMerger {
42  
43      private final boolean deepMerge;
44  
45      public SettingsMerger() {
46          this(true);
47      }
48  
49      public SettingsMerger(boolean deepMerge) {
50          this.deepMerge = deepMerge;
51      }
52  
53      /**
54       * Merges the specified source object into the given target object.
55       *
56       * @param target The target object whose existing contents should be merged with the source, must not be
57       *            <code>null</code>.
58       * @param source The (read-only) source object that should be merged into the target object, may be
59       *            <code>null</code>.
60       * @param sourceDominant A flag indicating whether either the target object or the source object provides the
61       *            dominant data.
62       * @param hints A set of key-value pairs that customized merger implementations can use to carry domain-specific
63       *            information along, may be <code>null</code>.
64       */
65      public Settings merge(Settings target, Settings source, boolean sourceDominant, Map<?, ?> hints) {
66          Objects.requireNonNull(target, "target cannot be null");
67          if (source == null) {
68              return target;
69          }
70          Map<Object, Object> context = new HashMap<>();
71          if (hints != null) {
72              context.putAll(hints);
73          }
74          return mergeSettings(target, source, sourceDominant, context);
75      }
76  
77      protected TrackableBase mergeTrackableBase(TrackableBase target, TrackableBase source, boolean sourceDominant, Map<Object, Object> context) {
78          TrackableBase.Builder builder = TrackableBase.newBuilder(target);
79          mergeTrackableBase(builder, target, source, sourceDominant, context);
80          return builder.build();
81      }
82  
83      protected void mergeTrackableBase(TrackableBase.Builder builder, TrackableBase target, TrackableBase source, boolean sourceDominant, Map<Object, Object> context) {
84      }
85  
86  
87      protected IdentifiableBase mergeIdentifiableBase(IdentifiableBase target, IdentifiableBase source, boolean sourceDominant, Map<Object, Object> context) {
88          IdentifiableBase.Builder builder = IdentifiableBase.newBuilder(target);
89          mergeIdentifiableBase(builder, target, source, sourceDominant, context);
90          return builder.build();
91      }
92  
93      protected void mergeIdentifiableBase(IdentifiableBase.Builder builder, IdentifiableBase target, IdentifiableBase source, boolean sourceDominant, Map<Object, Object> context) {
94          mergeTrackableBase(builder, target, source, sourceDominant, context);
95          mergeIdentifiableBase_Id(builder, target, source, sourceDominant, context);
96      }
97  
98      protected void mergeIdentifiableBase_Id(IdentifiableBase.Builder builder, IdentifiableBase target, IdentifiableBase source, boolean sourceDominant, Map<Object, Object> context) {
99          String src = source.getId();
100         String tgt = target.getId();
101         if (src != null && (sourceDominant || tgt == null)) {
102             builder.id(src);
103             builder.location("id", source.getLocation("id"));
104         }
105     }
106 
107     protected Settings mergeSettings(Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
108         Settings.Builder builder = Settings.newBuilder(target);
109         mergeSettings(builder, target, source, sourceDominant, context);
110         return builder.build();
111     }
112 
113     protected void mergeSettings(Settings.Builder builder, Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
114         mergeTrackableBase(builder, target, source, sourceDominant, context);
115         mergeSettings_LocalRepository(builder, target, source, sourceDominant, context);
116         mergeSettings_InteractiveMode(builder, target, source, sourceDominant, context);
117         mergeSettings_UsePluginRegistry(builder, target, source, sourceDominant, context);
118         mergeSettings_Offline(builder, target, source, sourceDominant, context);
119         mergeSettings_Proxies(builder, target, source, sourceDominant, context);
120         mergeSettings_Servers(builder, target, source, sourceDominant, context);
121         mergeSettings_Mirrors(builder, target, source, sourceDominant, context);
122         mergeSettings_Repositories(builder, target, source, sourceDominant, context);
123         mergeSettings_PluginRepositories(builder, target, source, sourceDominant, context);
124         mergeSettings_Profiles(builder, target, source, sourceDominant, context);
125         mergeSettings_ActiveProfiles(builder, target, source, sourceDominant, context);
126         mergeSettings_PluginGroups(builder, target, source, sourceDominant, context);
127     }
128 
129     protected void mergeSettings_LocalRepository(Settings.Builder builder, Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
130         String src = source.getLocalRepository();
131         String tgt = target.getLocalRepository();
132         if (src != null && (sourceDominant || tgt == null)) {
133             builder.localRepository(src);
134             builder.location("localRepository", source.getLocation("localRepository"));
135         }
136     }
137     protected void mergeSettings_InteractiveMode(Settings.Builder builder, Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
138         if (sourceDominant) {
139             builder.interactiveMode(source.isInteractiveMode());
140         }
141     }
142     protected void mergeSettings_UsePluginRegistry(Settings.Builder builder, Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
143         if (sourceDominant) {
144             builder.usePluginRegistry(source.isUsePluginRegistry());
145         }
146     }
147     protected void mergeSettings_Offline(Settings.Builder builder, Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
148         if (sourceDominant) {
149             builder.offline(source.isOffline());
150         }
151     }
152     protected void mergeSettings_Proxies(Settings.Builder builder, Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
153         if (deepMerge) {
154             builder.proxies(merge(target.getProxies(), source.getProxies(), getProxyKey(),
155                     (t, s) -> mergeProxy(t, s, sourceDominant, context)));
156         } else {
157             builder.proxies(merge(target.getProxies(), source.getProxies(), sourceDominant, getProxyKey()));
158         }
159     }
160     protected void mergeSettings_Servers(Settings.Builder builder, Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
161         if (deepMerge) {
162             builder.servers(merge(target.getServers(), source.getServers(), getServerKey(),
163                     (t, s) -> mergeServer(t, s, sourceDominant, context)));
164         } else {
165             builder.servers(merge(target.getServers(), source.getServers(), sourceDominant, getServerKey()));
166         }
167     }
168     protected void mergeSettings_Mirrors(Settings.Builder builder, Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
169         if (deepMerge) {
170             builder.mirrors(merge(target.getMirrors(), source.getMirrors(), getMirrorKey(),
171                     (t, s) -> mergeMirror(t, s, sourceDominant, context)));
172         } else {
173             builder.mirrors(merge(target.getMirrors(), source.getMirrors(), sourceDominant, getMirrorKey()));
174         }
175     }
176     protected void mergeSettings_Repositories(Settings.Builder builder, Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
177         if (deepMerge) {
178             builder.repositories(merge(target.getRepositories(), source.getRepositories(), getRepositoryKey(),
179                     (t, s) -> mergeRepository(t, s, sourceDominant, context)));
180         } else {
181             builder.repositories(merge(target.getRepositories(), source.getRepositories(), sourceDominant, getRepositoryKey()));
182         }
183     }
184     protected void mergeSettings_PluginRepositories(Settings.Builder builder, Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
185         if (deepMerge) {
186             builder.pluginRepositories(merge(target.getPluginRepositories(), source.getPluginRepositories(), getRepositoryKey(),
187                     (t, s) -> mergeRepository(t, s, sourceDominant, context)));
188         } else {
189             builder.pluginRepositories(merge(target.getPluginRepositories(), source.getPluginRepositories(), sourceDominant, getRepositoryKey()));
190         }
191     }
192     protected void mergeSettings_Profiles(Settings.Builder builder, Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
193         if (deepMerge) {
194             builder.profiles(merge(target.getProfiles(), source.getProfiles(), getProfileKey(),
195                     (t, s) -> mergeProfile(t, s, sourceDominant, context)));
196         } else {
197             builder.profiles(merge(target.getProfiles(), source.getProfiles(), sourceDominant, getProfileKey()));
198         }
199     }
200     protected void mergeSettings_ActiveProfiles(Settings.Builder builder, Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
201         builder.activeProfiles(merge(target.getActiveProfiles(), source.getActiveProfiles(), sourceDominant, e -> e));
202     }
203     protected void mergeSettings_PluginGroups(Settings.Builder builder, Settings target, Settings source, boolean sourceDominant, Map<Object, Object> context) {
204         builder.pluginGroups(merge(target.getPluginGroups(), source.getPluginGroups(), sourceDominant, e -> e));
205     }
206 
207     protected Proxy mergeProxy(Proxy target, Proxy source, boolean sourceDominant, Map<Object, Object> context) {
208         Proxy.Builder builder = Proxy.newBuilder(target);
209         mergeProxy(builder, target, source, sourceDominant, context);
210         return builder.build();
211     }
212 
213     protected void mergeProxy(Proxy.Builder builder, Proxy target, Proxy source, boolean sourceDominant, Map<Object, Object> context) {
214         mergeIdentifiableBase(builder, target, source, sourceDominant, context);
215         mergeProxy_ActiveString(builder, target, source, sourceDominant, context);
216         mergeProxy_Protocol(builder, target, source, sourceDominant, context);
217         mergeProxy_Username(builder, target, source, sourceDominant, context);
218         mergeProxy_Password(builder, target, source, sourceDominant, context);
219         mergeProxy_PortString(builder, target, source, sourceDominant, context);
220         mergeProxy_Host(builder, target, source, sourceDominant, context);
221         mergeProxy_NonProxyHosts(builder, target, source, sourceDominant, context);
222     }
223 
224     protected void mergeProxy_Id(Proxy.Builder builder, Proxy target, Proxy source, boolean sourceDominant, Map<Object, Object> context) {
225         String src = source.getId();
226         String tgt = target.getId();
227         if (src != null && (sourceDominant || tgt == null)) {
228             builder.id(src);
229             builder.location("id", source.getLocation("id"));
230         }
231     }
232     protected void mergeProxy_ActiveString(Proxy.Builder builder, Proxy target, Proxy source, boolean sourceDominant, Map<Object, Object> context) {
233         String src = source.getActiveString();
234         String tgt = target.getActiveString();
235         if (src != null && (sourceDominant || tgt == null)) {
236             builder.activeString(src);
237             builder.location("activeString", source.getLocation("activeString"));
238         }
239     }
240     protected void mergeProxy_Protocol(Proxy.Builder builder, Proxy target, Proxy source, boolean sourceDominant, Map<Object, Object> context) {
241         String src = source.getProtocol();
242         String tgt = target.getProtocol();
243         if (src != null && (sourceDominant || tgt == null)) {
244             builder.protocol(src);
245             builder.location("protocol", source.getLocation("protocol"));
246         }
247     }
248     protected void mergeProxy_Username(Proxy.Builder builder, Proxy target, Proxy source, boolean sourceDominant, Map<Object, Object> context) {
249         String src = source.getUsername();
250         String tgt = target.getUsername();
251         if (src != null && (sourceDominant || tgt == null)) {
252             builder.username(src);
253             builder.location("username", source.getLocation("username"));
254         }
255     }
256     protected void mergeProxy_Password(Proxy.Builder builder, Proxy target, Proxy source, boolean sourceDominant, Map<Object, Object> context) {
257         String src = source.getPassword();
258         String tgt = target.getPassword();
259         if (src != null && (sourceDominant || tgt == null)) {
260             builder.password(src);
261             builder.location("password", source.getLocation("password"));
262         }
263     }
264     protected void mergeProxy_PortString(Proxy.Builder builder, Proxy target, Proxy source, boolean sourceDominant, Map<Object, Object> context) {
265         String src = source.getPortString();
266         String tgt = target.getPortString();
267         if (src != null && (sourceDominant || tgt == null)) {
268             builder.portString(src);
269             builder.location("portString", source.getLocation("portString"));
270         }
271     }
272     protected void mergeProxy_Host(Proxy.Builder builder, Proxy target, Proxy source, boolean sourceDominant, Map<Object, Object> context) {
273         String src = source.getHost();
274         String tgt = target.getHost();
275         if (src != null && (sourceDominant || tgt == null)) {
276             builder.host(src);
277             builder.location("host", source.getLocation("host"));
278         }
279     }
280     protected void mergeProxy_NonProxyHosts(Proxy.Builder builder, Proxy target, Proxy source, boolean sourceDominant, Map<Object, Object> context) {
281         String src = source.getNonProxyHosts();
282         String tgt = target.getNonProxyHosts();
283         if (src != null && (sourceDominant || tgt == null)) {
284             builder.nonProxyHosts(src);
285             builder.location("nonProxyHosts", source.getLocation("nonProxyHosts"));
286         }
287     }
288 
289     protected Server mergeServer(Server target, Server source, boolean sourceDominant, Map<Object, Object> context) {
290         Server.Builder builder = Server.newBuilder(target);
291         mergeServer(builder, target, source, sourceDominant, context);
292         return builder.build();
293     }
294 
295     protected void mergeServer(Server.Builder builder, Server target, Server source, boolean sourceDominant, Map<Object, Object> context) {
296         mergeIdentifiableBase(builder, target, source, sourceDominant, context);
297         mergeServer_Username(builder, target, source, sourceDominant, context);
298         mergeServer_Password(builder, target, source, sourceDominant, context);
299         mergeServer_PrivateKey(builder, target, source, sourceDominant, context);
300         mergeServer_Passphrase(builder, target, source, sourceDominant, context);
301         mergeServer_FilePermissions(builder, target, source, sourceDominant, context);
302         mergeServer_DirectoryPermissions(builder, target, source, sourceDominant, context);
303         mergeServer_Configuration(builder, target, source, sourceDominant, context);
304     }
305 
306     protected void mergeServer_Id(Server.Builder builder, Server target, Server source, boolean sourceDominant, Map<Object, Object> context) {
307         String src = source.getId();
308         String tgt = target.getId();
309         if (src != null && (sourceDominant || tgt == null)) {
310             builder.id(src);
311             builder.location("id", source.getLocation("id"));
312         }
313     }
314     protected void mergeServer_Username(Server.Builder builder, Server target, Server source, boolean sourceDominant, Map<Object, Object> context) {
315         String src = source.getUsername();
316         String tgt = target.getUsername();
317         if (src != null && (sourceDominant || tgt == null)) {
318             builder.username(src);
319             builder.location("username", source.getLocation("username"));
320         }
321     }
322     protected void mergeServer_Password(Server.Builder builder, Server target, Server source, boolean sourceDominant, Map<Object, Object> context) {
323         String src = source.getPassword();
324         String tgt = target.getPassword();
325         if (src != null && (sourceDominant || tgt == null)) {
326             builder.password(src);
327             builder.location("password", source.getLocation("password"));
328         }
329     }
330     protected void mergeServer_PrivateKey(Server.Builder builder, Server target, Server source, boolean sourceDominant, Map<Object, Object> context) {
331         String src = source.getPrivateKey();
332         String tgt = target.getPrivateKey();
333         if (src != null && (sourceDominant || tgt == null)) {
334             builder.privateKey(src);
335             builder.location("privateKey", source.getLocation("privateKey"));
336         }
337     }
338     protected void mergeServer_Passphrase(Server.Builder builder, Server target, Server source, boolean sourceDominant, Map<Object, Object> context) {
339         String src = source.getPassphrase();
340         String tgt = target.getPassphrase();
341         if (src != null && (sourceDominant || tgt == null)) {
342             builder.passphrase(src);
343             builder.location("passphrase", source.getLocation("passphrase"));
344         }
345     }
346     protected void mergeServer_FilePermissions(Server.Builder builder, Server target, Server source, boolean sourceDominant, Map<Object, Object> context) {
347         String src = source.getFilePermissions();
348         String tgt = target.getFilePermissions();
349         if (src != null && (sourceDominant || tgt == null)) {
350             builder.filePermissions(src);
351             builder.location("filePermissions", source.getLocation("filePermissions"));
352         }
353     }
354     protected void mergeServer_DirectoryPermissions(Server.Builder builder, Server target, Server source, boolean sourceDominant, Map<Object, Object> context) {
355         String src = source.getDirectoryPermissions();
356         String tgt = target.getDirectoryPermissions();
357         if (src != null && (sourceDominant || tgt == null)) {
358             builder.directoryPermissions(src);
359             builder.location("directoryPermissions", source.getLocation("directoryPermissions"));
360         }
361     }
362     protected void mergeServer_Configuration(Server.Builder builder, Server target, Server source, boolean sourceDominant, Map<Object, Object> context) {
363         XmlNode src = source.getConfiguration();
364         if (src != null) {
365             XmlNode tgt = target.getConfiguration();
366             if (tgt == null) {
367                 builder.configuration(src);
368                 builder.location("configuration", source.getLocation("configuration"));
369             } else if (sourceDominant) {
370                 builder.configuration(src.merge(tgt));
371                 builder.location("configuration", target.getLocation("configuration"));
372             } else {
373                 builder.configuration(tgt.merge(src));
374                 builder.location("configuration", null);
375             }
376         }
377     }
378 
379     protected Mirror mergeMirror(Mirror target, Mirror source, boolean sourceDominant, Map<Object, Object> context) {
380         Mirror.Builder builder = Mirror.newBuilder(target);
381         mergeMirror(builder, target, source, sourceDominant, context);
382         return builder.build();
383     }
384 
385     protected void mergeMirror(Mirror.Builder builder, Mirror target, Mirror source, boolean sourceDominant, Map<Object, Object> context) {
386         mergeIdentifiableBase(builder, target, source, sourceDominant, context);
387         mergeMirror_MirrorOf(builder, target, source, sourceDominant, context);
388         mergeMirror_Name(builder, target, source, sourceDominant, context);
389         mergeMirror_Url(builder, target, source, sourceDominant, context);
390         mergeMirror_Layout(builder, target, source, sourceDominant, context);
391         mergeMirror_MirrorOfLayouts(builder, target, source, sourceDominant, context);
392         mergeMirror_Blocked(builder, target, source, sourceDominant, context);
393     }
394 
395     protected void mergeMirror_Id(Mirror.Builder builder, Mirror target, Mirror source, boolean sourceDominant, Map<Object, Object> context) {
396         String src = source.getId();
397         String tgt = target.getId();
398         if (src != null && (sourceDominant || tgt == null)) {
399             builder.id(src);
400             builder.location("id", source.getLocation("id"));
401         }
402     }
403     protected void mergeMirror_MirrorOf(Mirror.Builder builder, Mirror target, Mirror source, boolean sourceDominant, Map<Object, Object> context) {
404         String src = source.getMirrorOf();
405         String tgt = target.getMirrorOf();
406         if (src != null && (sourceDominant || tgt == null)) {
407             builder.mirrorOf(src);
408             builder.location("mirrorOf", source.getLocation("mirrorOf"));
409         }
410     }
411     protected void mergeMirror_Name(Mirror.Builder builder, Mirror target, Mirror source, boolean sourceDominant, Map<Object, Object> context) {
412         String src = source.getName();
413         String tgt = target.getName();
414         if (src != null && (sourceDominant || tgt == null)) {
415             builder.name(src);
416             builder.location("name", source.getLocation("name"));
417         }
418     }
419     protected void mergeMirror_Url(Mirror.Builder builder, Mirror target, Mirror source, boolean sourceDominant, Map<Object, Object> context) {
420         String src = source.getUrl();
421         String tgt = target.getUrl();
422         if (src != null && (sourceDominant || tgt == null)) {
423             builder.url(src);
424             builder.location("url", source.getLocation("url"));
425         }
426     }
427     protected void mergeMirror_Layout(Mirror.Builder builder, Mirror target, Mirror source, boolean sourceDominant, Map<Object, Object> context) {
428         String src = source.getLayout();
429         String tgt = target.getLayout();
430         if (src != null && (sourceDominant || tgt == null)) {
431             builder.layout(src);
432             builder.location("layout", source.getLocation("layout"));
433         }
434     }
435     protected void mergeMirror_MirrorOfLayouts(Mirror.Builder builder, Mirror target, Mirror source, boolean sourceDominant, Map<Object, Object> context) {
436         String src = source.getMirrorOfLayouts();
437         String tgt = target.getMirrorOfLayouts();
438         if (src != null && (sourceDominant || tgt == null)) {
439             builder.mirrorOfLayouts(src);
440             builder.location("mirrorOfLayouts", source.getLocation("mirrorOfLayouts"));
441         }
442     }
443     protected void mergeMirror_Blocked(Mirror.Builder builder, Mirror target, Mirror source, boolean sourceDominant, Map<Object, Object> context) {
444         if (sourceDominant) {
445             builder.blocked(source.isBlocked());
446         }
447     }
448 
449     protected Profile mergeProfile(Profile target, Profile source, boolean sourceDominant, Map<Object, Object> context) {
450         Profile.Builder builder = Profile.newBuilder(target);
451         mergeProfile(builder, target, source, sourceDominant, context);
452         return builder.build();
453     }
454 
455     protected void mergeProfile(Profile.Builder builder, Profile target, Profile source, boolean sourceDominant, Map<Object, Object> context) {
456         mergeIdentifiableBase(builder, target, source, sourceDominant, context);
457         mergeProfile_Activation(builder, target, source, sourceDominant, context);
458         mergeProfile_Properties(builder, target, source, sourceDominant, context);
459         mergeProfile_Repositories(builder, target, source, sourceDominant, context);
460         mergeProfile_PluginRepositories(builder, target, source, sourceDominant, context);
461     }
462 
463     protected void mergeProfile_Id(Profile.Builder builder, Profile target, Profile source, boolean sourceDominant, Map<Object, Object> context) {
464         String src = source.getId();
465         String tgt = target.getId();
466         if (src != null && (sourceDominant || tgt == null)) {
467             builder.id(src);
468             builder.location("id", source.getLocation("id"));
469         }
470     }
471     protected void mergeProfile_Activation(Profile.Builder builder, Profile target, Profile source, boolean sourceDominant, Map<Object, Object> context) {
472         Activation src = source.getActivation();
473         if (src != null) {
474             Activation tgt = target.getActivation();
475             if (tgt == null) {
476                 tgt = Activation.newInstance(false);
477             }
478             Activation merged = mergeActivation(tgt, src, sourceDominant, context);
479             builder.activation(merged);
480             if (target.getActivation() == null) {
481                 builder.location("activation", source.getLocation("activation"));
482             } else if (merged != tgt) {
483                 builder.location("activation", new InputLocation(-1, -1));
484             }
485         }
486     }
487     protected void mergeProfile_Properties(Profile.Builder builder, Profile target, Profile source, boolean sourceDominant, Map<Object, Object> context) {
488         Map<String, String> src = source.getProperties();
489         if (!src.isEmpty()) {
490             Map<String, String> tgt = target.getProperties();
491             if (tgt.isEmpty()) {
492                 builder.properties(src);
493                 builder.location("properties", source.getLocation("properties"));
494             } else {
495                 Map<String, String> merged = new HashMap<>();
496                 merged.putAll(sourceDominant ? target.getProperties() : source.getProperties());
497                 merged.putAll(sourceDominant ? source.getProperties() : target.getProperties());
498                 builder.properties(merged);
499                 builder.location("properties", InputLocation.merge(target.getLocation("properties"), source.getLocation("properties"), sourceDominant));
500             }
501         }
502     }
503     protected void mergeProfile_Repositories(Profile.Builder builder, Profile target, Profile source, boolean sourceDominant, Map<Object, Object> context) {
504         if (deepMerge) {
505             builder.repositories(merge(target.getRepositories(), source.getRepositories(), getRepositoryKey(),
506                     (t, s) -> mergeRepository(t, s, sourceDominant, context)));
507         } else {
508             builder.repositories(merge(target.getRepositories(), source.getRepositories(), sourceDominant, getRepositoryKey()));
509         }
510     }
511     protected void mergeProfile_PluginRepositories(Profile.Builder builder, Profile target, Profile source, boolean sourceDominant, Map<Object, Object> context) {
512         if (deepMerge) {
513             builder.pluginRepositories(merge(target.getPluginRepositories(), source.getPluginRepositories(), getRepositoryKey(),
514                     (t, s) -> mergeRepository(t, s, sourceDominant, context)));
515         } else {
516             builder.pluginRepositories(merge(target.getPluginRepositories(), source.getPluginRepositories(), sourceDominant, getRepositoryKey()));
517         }
518     }
519 
520     protected Activation mergeActivation(Activation target, Activation source, boolean sourceDominant, Map<Object, Object> context) {
521         Activation.Builder builder = Activation.newBuilder(target);
522         mergeActivation(builder, target, source, sourceDominant, context);
523         return builder.build();
524     }
525 
526     protected void mergeActivation(Activation.Builder builder, Activation target, Activation source, boolean sourceDominant, Map<Object, Object> context) {
527         mergeActivation_ActiveByDefault(builder, target, source, sourceDominant, context);
528         mergeActivation_Jdk(builder, target, source, sourceDominant, context);
529         mergeActivation_Os(builder, target, source, sourceDominant, context);
530         mergeActivation_Property(builder, target, source, sourceDominant, context);
531         mergeActivation_File(builder, target, source, sourceDominant, context);
532         mergeActivation_Packaging(builder, target, source, sourceDominant, context);
533         mergeActivation_Condition(builder, target, source, sourceDominant, context);
534     }
535 
536     protected void mergeActivation_ActiveByDefault(Activation.Builder builder, Activation target, Activation source, boolean sourceDominant, Map<Object, Object> context) {
537         if (sourceDominant) {
538             builder.activeByDefault(source.isActiveByDefault());
539         }
540     }
541     protected void mergeActivation_Jdk(Activation.Builder builder, Activation target, Activation source, boolean sourceDominant, Map<Object, Object> context) {
542         String src = source.getJdk();
543         String tgt = target.getJdk();
544         if (src != null && (sourceDominant || tgt == null)) {
545             builder.jdk(src);
546             builder.location("jdk", source.getLocation("jdk"));
547         }
548     }
549     protected void mergeActivation_Os(Activation.Builder builder, Activation target, Activation source, boolean sourceDominant, Map<Object, Object> context) {
550         ActivationOS src = source.getOs();
551         if (src != null) {
552             ActivationOS tgt = target.getOs();
553             if (tgt == null) {
554                 tgt = ActivationOS.newInstance(false);
555             }
556             ActivationOS merged = mergeActivationOS(tgt, src, sourceDominant, context);
557             builder.os(merged);
558             if (target.getOs() == null) {
559                 builder.location("os", source.getLocation("os"));
560             } else if (merged != tgt) {
561                 builder.location("os", new InputLocation(-1, -1));
562             }
563         }
564     }
565     protected void mergeActivation_Property(Activation.Builder builder, Activation target, Activation source, boolean sourceDominant, Map<Object, Object> context) {
566         ActivationProperty src = source.getProperty();
567         if (src != null) {
568             ActivationProperty tgt = target.getProperty();
569             if (tgt == null) {
570                 tgt = ActivationProperty.newInstance(false);
571             }
572             ActivationProperty merged = mergeActivationProperty(tgt, src, sourceDominant, context);
573             builder.property(merged);
574             if (target.getProperty() == null) {
575                 builder.location("property", source.getLocation("property"));
576             } else if (merged != tgt) {
577                 builder.location("property", new InputLocation(-1, -1));
578             }
579         }
580     }
581     protected void mergeActivation_File(Activation.Builder builder, Activation target, Activation source, boolean sourceDominant, Map<Object, Object> context) {
582         ActivationFile src = source.getFile();
583         if (src != null) {
584             ActivationFile tgt = target.getFile();
585             if (tgt == null) {
586                 tgt = ActivationFile.newInstance(false);
587             }
588             ActivationFile merged = mergeActivationFile(tgt, src, sourceDominant, context);
589             builder.file(merged);
590             if (target.getFile() == null) {
591                 builder.location("file", source.getLocation("file"));
592             } else if (merged != tgt) {
593                 builder.location("file", new InputLocation(-1, -1));
594             }
595         }
596     }
597     protected void mergeActivation_Packaging(Activation.Builder builder, Activation target, Activation source, boolean sourceDominant, Map<Object, Object> context) {
598         String src = source.getPackaging();
599         String tgt = target.getPackaging();
600         if (src != null && (sourceDominant || tgt == null)) {
601             builder.packaging(src);
602             builder.location("packaging", source.getLocation("packaging"));
603         }
604     }
605     protected void mergeActivation_Condition(Activation.Builder builder, Activation target, Activation source, boolean sourceDominant, Map<Object, Object> context) {
606         String src = source.getCondition();
607         String tgt = target.getCondition();
608         if (src != null && (sourceDominant || tgt == null)) {
609             builder.condition(src);
610             builder.location("condition", source.getLocation("condition"));
611         }
612     }
613 
614     protected RepositoryBase mergeRepositoryBase(RepositoryBase target, RepositoryBase source, boolean sourceDominant, Map<Object, Object> context) {
615         RepositoryBase.Builder builder = RepositoryBase.newBuilder(target);
616         mergeRepositoryBase(builder, target, source, sourceDominant, context);
617         return builder.build();
618     }
619 
620     protected void mergeRepositoryBase(RepositoryBase.Builder builder, RepositoryBase target, RepositoryBase source, boolean sourceDominant, Map<Object, Object> context) {
621         mergeIdentifiableBase(builder, target, source, sourceDominant, context);
622         mergeRepositoryBase_Name(builder, target, source, sourceDominant, context);
623         mergeRepositoryBase_Url(builder, target, source, sourceDominant, context);
624         mergeRepositoryBase_Layout(builder, target, source, sourceDominant, context);
625     }
626 
627     protected void mergeRepositoryBase_Id(RepositoryBase.Builder builder, RepositoryBase target, RepositoryBase source, boolean sourceDominant, Map<Object, Object> context) {
628         String src = source.getId();
629         String tgt = target.getId();
630         if (src != null && (sourceDominant || tgt == null)) {
631             builder.id(src);
632             builder.location("id", source.getLocation("id"));
633         }
634     }
635     protected void mergeRepositoryBase_Name(RepositoryBase.Builder builder, RepositoryBase target, RepositoryBase source, boolean sourceDominant, Map<Object, Object> context) {
636         String src = source.getName();
637         String tgt = target.getName();
638         if (src != null && (sourceDominant || tgt == null)) {
639             builder.name(src);
640             builder.location("name", source.getLocation("name"));
641         }
642     }
643     protected void mergeRepositoryBase_Url(RepositoryBase.Builder builder, RepositoryBase target, RepositoryBase source, boolean sourceDominant, Map<Object, Object> context) {
644         String src = source.getUrl();
645         String tgt = target.getUrl();
646         if (src != null && (sourceDominant || tgt == null)) {
647             builder.url(src);
648             builder.location("url", source.getLocation("url"));
649         }
650     }
651     protected void mergeRepositoryBase_Layout(RepositoryBase.Builder builder, RepositoryBase target, RepositoryBase source, boolean sourceDominant, Map<Object, Object> context) {
652         String src = source.getLayout();
653         String tgt = target.getLayout();
654         if (src != null && (sourceDominant || tgt == null)) {
655             builder.layout(src);
656             builder.location("layout", source.getLocation("layout"));
657         }
658     }
659 
660     protected Repository mergeRepository(Repository target, Repository source, boolean sourceDominant, Map<Object, Object> context) {
661         Repository.Builder builder = Repository.newBuilder(target);
662         mergeRepository(builder, target, source, sourceDominant, context);
663         return builder.build();
664     }
665 
666     protected void mergeRepository(Repository.Builder builder, Repository target, Repository source, boolean sourceDominant, Map<Object, Object> context) {
667         mergeRepositoryBase(builder, target, source, sourceDominant, context);
668         mergeRepository_Releases(builder, target, source, sourceDominant, context);
669         mergeRepository_Snapshots(builder, target, source, sourceDominant, context);
670     }
671 
672     protected void mergeRepository_Id(Repository.Builder builder, Repository target, Repository source, boolean sourceDominant, Map<Object, Object> context) {
673         String src = source.getId();
674         String tgt = target.getId();
675         if (src != null && (sourceDominant || tgt == null)) {
676             builder.id(src);
677             builder.location("id", source.getLocation("id"));
678         }
679     }
680     protected void mergeRepository_Name(Repository.Builder builder, Repository target, Repository source, boolean sourceDominant, Map<Object, Object> context) {
681         String src = source.getName();
682         String tgt = target.getName();
683         if (src != null && (sourceDominant || tgt == null)) {
684             builder.name(src);
685             builder.location("name", source.getLocation("name"));
686         }
687     }
688     protected void mergeRepository_Url(Repository.Builder builder, Repository target, Repository source, boolean sourceDominant, Map<Object, Object> context) {
689         String src = source.getUrl();
690         String tgt = target.getUrl();
691         if (src != null && (sourceDominant || tgt == null)) {
692             builder.url(src);
693             builder.location("url", source.getLocation("url"));
694         }
695     }
696     protected void mergeRepository_Layout(Repository.Builder builder, Repository target, Repository source, boolean sourceDominant, Map<Object, Object> context) {
697         String src = source.getLayout();
698         String tgt = target.getLayout();
699         if (src != null && (sourceDominant || tgt == null)) {
700             builder.layout(src);
701             builder.location("layout", source.getLocation("layout"));
702         }
703     }
704     protected void mergeRepository_Releases(Repository.Builder builder, Repository target, Repository source, boolean sourceDominant, Map<Object, Object> context) {
705         RepositoryPolicy src = source.getReleases();
706         if (src != null) {
707             RepositoryPolicy tgt = target.getReleases();
708             if (tgt == null) {
709                 tgt = RepositoryPolicy.newInstance(false);
710             }
711             RepositoryPolicy merged = mergeRepositoryPolicy(tgt, src, sourceDominant, context);
712             builder.releases(merged);
713             if (target.getReleases() == null) {
714                 builder.location("releases", source.getLocation("releases"));
715             } else if (merged != tgt) {
716                 builder.location("releases", new InputLocation(-1, -1));
717             }
718         }
719     }
720     protected void mergeRepository_Snapshots(Repository.Builder builder, Repository target, Repository source, boolean sourceDominant, Map<Object, Object> context) {
721         RepositoryPolicy src = source.getSnapshots();
722         if (src != null) {
723             RepositoryPolicy tgt = target.getSnapshots();
724             if (tgt == null) {
725                 tgt = RepositoryPolicy.newInstance(false);
726             }
727             RepositoryPolicy merged = mergeRepositoryPolicy(tgt, src, sourceDominant, context);
728             builder.snapshots(merged);
729             if (target.getSnapshots() == null) {
730                 builder.location("snapshots", source.getLocation("snapshots"));
731             } else if (merged != tgt) {
732                 builder.location("snapshots", new InputLocation(-1, -1));
733             }
734         }
735     }
736 
737     protected RepositoryPolicy mergeRepositoryPolicy(RepositoryPolicy target, RepositoryPolicy source, boolean sourceDominant, Map<Object, Object> context) {
738         RepositoryPolicy.Builder builder = RepositoryPolicy.newBuilder(target);
739         mergeRepositoryPolicy(builder, target, source, sourceDominant, context);
740         return builder.build();
741     }
742 
743     protected void mergeRepositoryPolicy(RepositoryPolicy.Builder builder, RepositoryPolicy target, RepositoryPolicy source, boolean sourceDominant, Map<Object, Object> context) {
744         mergeRepositoryPolicy_Enabled(builder, target, source, sourceDominant, context);
745         mergeRepositoryPolicy_UpdatePolicy(builder, target, source, sourceDominant, context);
746         mergeRepositoryPolicy_ChecksumPolicy(builder, target, source, sourceDominant, context);
747     }
748 
749     protected void mergeRepositoryPolicy_Enabled(RepositoryPolicy.Builder builder, RepositoryPolicy target, RepositoryPolicy source, boolean sourceDominant, Map<Object, Object> context) {
750         if (sourceDominant) {
751             builder.enabled(source.isEnabled());
752         }
753     }
754     protected void mergeRepositoryPolicy_UpdatePolicy(RepositoryPolicy.Builder builder, RepositoryPolicy target, RepositoryPolicy source, boolean sourceDominant, Map<Object, Object> context) {
755         String src = source.getUpdatePolicy();
756         String tgt = target.getUpdatePolicy();
757         if (src != null && (sourceDominant || tgt == null)) {
758             builder.updatePolicy(src);
759             builder.location("updatePolicy", source.getLocation("updatePolicy"));
760         }
761     }
762     protected void mergeRepositoryPolicy_ChecksumPolicy(RepositoryPolicy.Builder builder, RepositoryPolicy target, RepositoryPolicy source, boolean sourceDominant, Map<Object, Object> context) {
763         String src = source.getChecksumPolicy();
764         String tgt = target.getChecksumPolicy();
765         if (src != null && (sourceDominant || tgt == null)) {
766             builder.checksumPolicy(src);
767             builder.location("checksumPolicy", source.getLocation("checksumPolicy"));
768         }
769     }
770 
771     protected ActivationProperty mergeActivationProperty(ActivationProperty target, ActivationProperty source, boolean sourceDominant, Map<Object, Object> context) {
772         ActivationProperty.Builder builder = ActivationProperty.newBuilder(target);
773         mergeActivationProperty(builder, target, source, sourceDominant, context);
774         return builder.build();
775     }
776 
777     protected void mergeActivationProperty(ActivationProperty.Builder builder, ActivationProperty target, ActivationProperty source, boolean sourceDominant, Map<Object, Object> context) {
778         mergeActivationProperty_Name(builder, target, source, sourceDominant, context);
779         mergeActivationProperty_Value(builder, target, source, sourceDominant, context);
780     }
781 
782     protected void mergeActivationProperty_Name(ActivationProperty.Builder builder, ActivationProperty target, ActivationProperty source, boolean sourceDominant, Map<Object, Object> context) {
783         String src = source.getName();
784         String tgt = target.getName();
785         if (src != null && (sourceDominant || tgt == null)) {
786             builder.name(src);
787             builder.location("name", source.getLocation("name"));
788         }
789     }
790     protected void mergeActivationProperty_Value(ActivationProperty.Builder builder, ActivationProperty target, ActivationProperty source, boolean sourceDominant, Map<Object, Object> context) {
791         String src = source.getValue();
792         String tgt = target.getValue();
793         if (src != null && (sourceDominant || tgt == null)) {
794             builder.value(src);
795             builder.location("value", source.getLocation("value"));
796         }
797     }
798 
799     protected ActivationOS mergeActivationOS(ActivationOS target, ActivationOS source, boolean sourceDominant, Map<Object, Object> context) {
800         ActivationOS.Builder builder = ActivationOS.newBuilder(target);
801         mergeActivationOS(builder, target, source, sourceDominant, context);
802         return builder.build();
803     }
804 
805     protected void mergeActivationOS(ActivationOS.Builder builder, ActivationOS target, ActivationOS source, boolean sourceDominant, Map<Object, Object> context) {
806         mergeActivationOS_Name(builder, target, source, sourceDominant, context);
807         mergeActivationOS_Family(builder, target, source, sourceDominant, context);
808         mergeActivationOS_Arch(builder, target, source, sourceDominant, context);
809         mergeActivationOS_Version(builder, target, source, sourceDominant, context);
810     }
811 
812     protected void mergeActivationOS_Name(ActivationOS.Builder builder, ActivationOS target, ActivationOS source, boolean sourceDominant, Map<Object, Object> context) {
813         String src = source.getName();
814         String tgt = target.getName();
815         if (src != null && (sourceDominant || tgt == null)) {
816             builder.name(src);
817             builder.location("name", source.getLocation("name"));
818         }
819     }
820     protected void mergeActivationOS_Family(ActivationOS.Builder builder, ActivationOS target, ActivationOS source, boolean sourceDominant, Map<Object, Object> context) {
821         String src = source.getFamily();
822         String tgt = target.getFamily();
823         if (src != null && (sourceDominant || tgt == null)) {
824             builder.family(src);
825             builder.location("family", source.getLocation("family"));
826         }
827     }
828     protected void mergeActivationOS_Arch(ActivationOS.Builder builder, ActivationOS target, ActivationOS source, boolean sourceDominant, Map<Object, Object> context) {
829         String src = source.getArch();
830         String tgt = target.getArch();
831         if (src != null && (sourceDominant || tgt == null)) {
832             builder.arch(src);
833             builder.location("arch", source.getLocation("arch"));
834         }
835     }
836     protected void mergeActivationOS_Version(ActivationOS.Builder builder, ActivationOS target, ActivationOS source, boolean sourceDominant, Map<Object, Object> context) {
837         String src = source.getVersion();
838         String tgt = target.getVersion();
839         if (src != null && (sourceDominant || tgt == null)) {
840             builder.version(src);
841             builder.location("version", source.getLocation("version"));
842         }
843     }
844 
845     protected ActivationFile mergeActivationFile(ActivationFile target, ActivationFile source, boolean sourceDominant, Map<Object, Object> context) {
846         ActivationFile.Builder builder = ActivationFile.newBuilder(target);
847         mergeActivationFile(builder, target, source, sourceDominant, context);
848         return builder.build();
849     }
850 
851     protected void mergeActivationFile(ActivationFile.Builder builder, ActivationFile target, ActivationFile source, boolean sourceDominant, Map<Object, Object> context) {
852         mergeActivationFile_Missing(builder, target, source, sourceDominant, context);
853         mergeActivationFile_Exists(builder, target, source, sourceDominant, context);
854     }
855 
856     protected void mergeActivationFile_Missing(ActivationFile.Builder builder, ActivationFile target, ActivationFile source, boolean sourceDominant, Map<Object, Object> context) {
857         String src = source.getMissing();
858         String tgt = target.getMissing();
859         if (src != null && (sourceDominant || tgt == null)) {
860             builder.missing(src);
861             builder.location("missing", source.getLocation("missing"));
862         }
863     }
864     protected void mergeActivationFile_Exists(ActivationFile.Builder builder, ActivationFile target, ActivationFile source, boolean sourceDominant, Map<Object, Object> context) {
865         String src = source.getExists();
866         String tgt = target.getExists();
867         if (src != null && (sourceDominant || tgt == null)) {
868             builder.exists(src);
869             builder.location("exists", source.getLocation("exists"));
870         }
871     }
872 
873 
874     protected KeyComputer<TrackableBase> getTrackableBaseKey() {
875         return v -> v;
876     }
877     protected KeyComputer<IdentifiableBase> getIdentifiableBaseKey() {
878         return v -> v;
879     }
880     protected KeyComputer<Settings> getSettingsKey() {
881         return v -> v;
882     }
883     protected KeyComputer<Proxy> getProxyKey() {
884         return v -> v;
885     }
886     protected KeyComputer<Server> getServerKey() {
887         return v -> v;
888     }
889     protected KeyComputer<Mirror> getMirrorKey() {
890         return v -> v;
891     }
892     protected KeyComputer<Profile> getProfileKey() {
893         return v -> v;
894     }
895     protected KeyComputer<Activation> getActivationKey() {
896         return v -> v;
897     }
898     protected KeyComputer<RepositoryBase> getRepositoryBaseKey() {
899         return v -> v;
900     }
901     protected KeyComputer<Repository> getRepositoryKey() {
902         return v -> v;
903     }
904     protected KeyComputer<RepositoryPolicy> getRepositoryPolicyKey() {
905         return v -> v;
906     }
907     protected KeyComputer<ActivationProperty> getActivationPropertyKey() {
908         return v -> v;
909     }
910     protected KeyComputer<ActivationOS> getActivationOSKey() {
911         return v -> v;
912     }
913     protected KeyComputer<ActivationFile> getActivationFileKey() {
914         return v -> v;
915     }
916 
917     /**
918      * Use to compute keys for data structures
919      * @param <T> the data structure type
920      */
921     @FunctionalInterface
922     public interface KeyComputer<T> extends Function<T, Object> {
923     }
924 
925     /**
926      * Merge two lists
927      */
928     public static <T> List<T> merge(List<T> tgt, List<T> src, boolean sourceDominant, KeyComputer<T> computer) {
929         return merge(tgt, src, computer, (t, s) -> sourceDominant ? s : t);
930     }
931 
932     public static <T> List<T> merge(List<T> tgt, List<T> src, KeyComputer<T> computer, BinaryOperator<T> remapping) {
933         if (src.isEmpty()) {
934             return tgt;
935         }
936 
937         MergingList<T> list;
938         if (tgt instanceof MergingList) {
939             list = (MergingList<T>) tgt;
940         } else {
941             list = new MergingList<>(computer, src.size() + tgt.size());
942             list.mergeAll(tgt, (t, s) -> s);
943         }
944 
945         list.mergeAll(src, remapping);
946         return list;
947     }
948 
949     /**
950      * Merging list
951      * @param <V>
952      */
953     private static class MergingList<V> extends AbstractList<V> implements java.io.Serializable {
954 
955         private final KeyComputer<V> keyComputer;
956         private Map<Object, V> map;
957         private List<V> list;
958 
959         MergingList(KeyComputer<V> keyComputer, int initialCapacity) {
960             this.map = new LinkedHashMap<>(initialCapacity);
961             this.keyComputer = keyComputer;
962         }
963 
964         Object writeReplace() throws ObjectStreamException {
965             return new ArrayList<>(this);
966         }
967 
968         @Override
969         public Iterator<V> iterator() {
970             if (map != null) {
971                 return map.values().iterator();
972             } else {
973                 return list.iterator();
974             }
975         }
976 
977         void mergeAll(Collection<V> vs, BinaryOperator<V> remapping) {
978             if (map == null) {
979                 map = list.stream().collect(Collectors.toMap(keyComputer,
980                     Function.identity(),
981                     null,
982                     LinkedHashMap::new));
983                 list = null;
984             }
985 
986             if (vs instanceof MergingList && ((MergingList<V>) vs).map != null) {
987                 for (Map.Entry<Object, V> e : ((MergingList<V>) vs).map.entrySet()) {
988                     Object key = e.getKey();
989                     V v = e.getValue();
990                     map.merge(key, v, remapping);
991                 }
992             } else {
993                 for (V v : vs) {
994                     Object key = keyComputer.apply(v);
995                     map.merge(key, v, remapping);
996                 }
997             }
998         }
999 
1000         @Override
1001         public boolean contains(Object o) {
1002             if (map != null) {
1003                 return map.containsValue(o);
1004             } else {
1005                 return list.contains(o);
1006             }
1007         }
1008 
1009         private List<V> asList() {
1010             if (list == null) {
1011                 list = new ArrayList<>(map.values());
1012                 map = null;
1013             }
1014             return list;
1015         }
1016 
1017         @Override
1018         public void add(int index, V element) {
1019             asList().add(index, element);
1020         }
1021 
1022         @Override
1023         public V remove(int index) {
1024             return asList().remove(index);
1025         }
1026 
1027         @Override
1028         public V get(int index) {
1029             return asList().get(index);
1030         }
1031 
1032         @Override
1033         public int size() {
1034             if (map != null) {
1035                 return map.size();
1036             } else {
1037                 return list.size();
1038             }
1039         }
1040     }
1041 }