Add “get” command to command reader.
[xudocci.git] / src / main / java / net / pterodactylus / xdcc / ui / stdin / CommandReader.java
1 /*
2  * XdccDownloader - CommandReader.java - Copyright © 2013 David Roden
3  *
4  * This program is free software: you can redistribute it and/or modify
5  * it under the terms of the GNU General Public License as published by
6  * the Free Software Foundation, either version 3 of the License, or
7  * (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
16  */
17
18 package net.pterodactylus.xdcc.ui.stdin;
19
20 import java.io.BufferedReader;
21 import java.io.Reader;
22 import java.io.Writer;
23 import java.util.Collections;
24 import java.util.List;
25
26 import net.pterodactylus.irc.DccReceiver;
27 import net.pterodactylus.xdcc.core.Core;
28 import net.pterodactylus.xdcc.data.Bot;
29 import net.pterodactylus.xdcc.data.Pack;
30
31 import com.google.common.collect.Lists;
32 import com.google.common.primitives.Ints;
33 import com.google.common.util.concurrent.AbstractExecutionThreadService;
34
35 /**
36  * Command interface for arbitrary {@link Reader}s.
37  *
38  * @author <a href="mailto:bombe@pterodactylus.net">David ‘Bombe’ Roden</a>
39  */
40 public class CommandReader extends AbstractExecutionThreadService {
41
42         /** The core being controlled. */
43         private final Core core;
44
45         /** The reader to read commands from. */
46         private final BufferedReader reader;
47
48         /** The writer to write the results to. */
49         private final Writer writer;
50
51         /**
52          * Creates a new command reader.
53          *
54          * @param core
55          *              The core being controlled
56          * @param reader
57          *              The reader to read commands from
58          * @param writer
59          *              The write to write results to
60          */
61         public CommandReader(Core core, Reader reader, Writer writer) {
62                 this.core = core;
63                 this.reader = new BufferedReader(reader);
64                 this.writer = writer;
65         }
66
67         //
68         // ABSTRACTEXECUTIONTHREADSERVICE METHODS
69         //
70
71         @Override
72         protected void run() throws Exception {
73                 String lastLine = "";
74                 String line;
75                 final List<Result> lastResult = Lists.newArrayList();
76                 while ((line = reader.readLine()) != null) {
77                         if (line.equals("")) {
78                                 line = lastLine;
79                         }
80                         String[] words = line.split(" +");
81                         if (words[0].equalsIgnoreCase("search")) {
82                                 lastResult.clear();
83                                 for (Bot bot : core.bots()) {
84                                         for (Pack pack : bot) {
85                                                 boolean found = true;
86                                                 for (int wordIndex = 1; wordIndex < words.length; ++wordIndex) {
87                                                         if (words[wordIndex].startsWith("-") && pack.name().toLowerCase().contains(words[wordIndex].toLowerCase().substring(1))) {
88                                                                 found = false;
89                                                                 break;
90                                                         }
91                                                         if (!words[wordIndex].startsWith("-") && !pack.name().toLowerCase().contains(words[wordIndex].toLowerCase())) {
92                                                                 found = false;
93                                                                 break;
94                                                         }
95                                                 }
96                                                 if (found) {
97                                                         lastResult.add(new Result(bot, pack));
98                                                 }
99                                         }
100                                 }
101                                 Collections.sort(lastResult);
102                                 int counter = 0;
103                                 for (Result result : lastResult) {
104                                         writer.write(String.format("[%d] %s (%s) from %s (#%s) on %s\n", counter++, result.pack().name(), result.pack().size(), result.bot().name(), result.pack().id(), result.bot().network().name()));
105                                 }
106                                 writer.write("End of Search.\n");
107                         } else if (words[0].equalsIgnoreCase("dcc")) {
108                                 int counter = 0;
109                                 for (DccReceiver dccReceiver : core.dccReceivers()) {
110                                         writer.write(String.format("[%d] %s (%s, %d%%%s)\n", counter++, dccReceiver.filename(), dccReceiver.size(), dccReceiver.progress() * 100 / dccReceiver.size(), dccReceiver.isRunning() ? "" : ", finished"));
111                                 }
112                                 writer.write("End of DCCs.\n");
113                         } else if (words[0].equalsIgnoreCase("get")) {
114                                 Integer index = Ints.tryParse(words[1]);
115                                 if ((index != null) && (index < lastResult.size())) {
116                                         core.fetch(lastResult.get(index).bot(), lastResult.get(index).pack());
117                                 }
118                         }
119
120                         lastLine = line;
121                         writer.flush();
122                 }
123         }
124
125         /** Container for result information. */
126         private static class Result implements Comparable<Result> {
127
128                 /** The bot carrying the pack. */
129                 private final Bot bot;
130
131                 /** The pack. */
132                 private final Pack pack;
133
134                 /**
135                  * Creates a new result.
136                  *
137                  * @param bot
138                  *              The bot carrying the pack
139                  * @param pack
140                  *              The pack
141                  */
142                 private Result(Bot bot, Pack pack) {
143                         this.bot = bot;
144                         this.pack = pack;
145                 }
146
147                 //
148                 // ACCESSORS
149                 //
150
151                 /**
152                  * Returns the bot carrying the pack.
153                  *
154                  * @return The bot carrying the pack
155                  */
156                 public Bot bot() {
157                         return bot;
158                 }
159
160                 /**
161                  * Returns the pack.
162                  *
163                  * @return The pack
164                  */
165                 public Pack pack() {
166                         return pack;
167                 }
168
169                 //
170                 // COMPARABLE METHODS
171                 //
172
173                 @Override
174                 public int compareTo(Result result) {
175                         return pack().name().compareToIgnoreCase(result.pack().name());
176                 }
177
178         }
179
180 }