Implement notification on USK update
[jFCPlib.git] / src / main / java / net / pterodactylus / fcp / quelaton / ActiveSubscriptions.java
1 package net.pterodactylus.fcp.quelaton;
2
3 import java.util.ArrayList;
4 import java.util.Collections;
5 import java.util.HashMap;
6 import java.util.List;
7 import java.util.Map;
8 import java.util.concurrent.ExecutionException;
9 import java.util.function.Consumer;
10 import java.util.function.Supplier;
11
12 import net.pterodactylus.fcp.FcpAdapter;
13 import net.pterodactylus.fcp.FcpConnection;
14 import net.pterodactylus.fcp.FcpListener;
15 import net.pterodactylus.fcp.Priority;
16 import net.pterodactylus.fcp.SubscribeUSK;
17 import net.pterodactylus.fcp.SubscribedUSKUpdate;
18
19 /**
20  * Maintains a record of active subscriptions.
21  *
22  * @author <a href="mailto:bombe@freenetproject.org">David ‘Bombe’ Roden</a>
23  */
24 public class ActiveSubscriptions {
25
26         private final Map<String, RemoteUskSubscription> subscriptions = Collections.synchronizedMap(new HashMap<>());
27
28         public void renew(Consumer<FcpListener> fcpEventSender, Supplier<SubscribeUskCommand> subscribeUskCommandSupplier)
29         throws ExecutionException, InterruptedException {
30                 fcpEventSender.accept(createFcpListener());
31                 for (UskSubscription uskSubscription : subscriptions.values()) {
32                         subscribeUskCommandSupplier.get().uri(uskSubscription.getUri()).execute().get();
33                 }
34         }
35
36         private FcpListener createFcpListener() {
37                 return new FcpAdapter() {
38                         @Override
39                         public void receivedSubscribedUSKUpdate(
40                                 FcpConnection fcpConnection, SubscribedUSKUpdate subscribedUSKUpdate) {
41                                 String identifier = subscribedUSKUpdate.getIdentifier();
42                                 RemoteUskSubscription uskSubscription = subscriptions.get(identifier);
43                                 if (uskSubscription == null) {
44                                         /* TODO - log warning? */
45                                         return;
46                                 }
47                                 uskSubscription.foundUpdate(subscribedUSKUpdate.getEdition());
48                         }
49                 };
50         }
51
52         public UskSubscription createUskSubscription(SubscribeUSK subscribeUSK) {
53                 RemoteUskSubscription remoteUskSubscription =
54                         new RemoteUskSubscription(subscribeUSK.getIdentifier(), subscribeUSK.getUri(), subscribeUSK.isActive(),
55                                 subscribeUSK.isSparse(), subscribeUSK.getPriority(), subscribeUSK.getActivePriority(),
56                                 subscribeUSK.isRealTime(), subscribeUSK.isIgnoreDateHints());
57                 subscriptions.put(subscribeUSK.getIdentifier(), remoteUskSubscription);
58                 return remoteUskSubscription;
59         }
60
61         private static class RemoteUskSubscription implements UskSubscription {
62
63                 private final String identifier;
64                 private final String uri;
65                 private final boolean active;
66                 private final boolean sparse;
67                 private final Priority priority;
68                 private final Priority activePriority;
69                 private final boolean realTime;
70                 private final boolean ignoreDateHints;
71                 private final List<UskUpdater> uskUpdaters = Collections.synchronizedList(new ArrayList<>());
72
73                 private RemoteUskSubscription(
74                         String identifier, String uri, boolean active, boolean sparse, Priority priority, Priority activePriority,
75                         boolean realTime, boolean ignoreDateHints) {
76                         this.identifier = identifier;
77                         this.uri = uri;
78                         this.active = active;
79                         this.sparse = sparse;
80                         this.priority = priority;
81                         this.activePriority = activePriority;
82                         this.realTime = realTime;
83                         this.ignoreDateHints = ignoreDateHints;
84                 }
85
86                 @Override
87                 public String getUri() {
88                         return uri;
89                 }
90
91                 @Override
92                 public void onUpdate(UskUpdater uskUpdater) {
93                         uskUpdaters.add(uskUpdater);
94                 }
95
96                 private void foundUpdate(int edition) {
97                         for (UskUpdater uskUpdater : uskUpdaters) {
98                                 uskUpdater.uskUpdated(edition);
99                         }
100                 }
101
102         }
103
104 }