Add IMDb CLI downloader to test the IMDb downloader
[cinaest] / src / imdb / imdb-downloader-cli.vala
1 using GLib;
2
3 class IMDbDownloaderCLI : Object, IMDbDownloader {
4         MainLoop loop;
5         Cancellable cancellable;
6         bool running;
7         uint source_id;
8         unowned IMDbSqlite sqlite;
9 //      string mirrors[] = {
10 //              "ftp.fu-berlin.de/pub/misc/movies/database/"
11 //      };
12         string url;
13         int flags;
14         int percent_finished;
15
16         delegate void ParseLineFunction (string line);
17
18         construct {
19                 loop = new MainLoop (null, false);
20                 cancellable = new Cancellable ();
21         }
22
23         // IMDbDownloader implementation
24
25         public void download (string mirror, int _flags) throws DBus.Error {
26                 if (running) {
27                         stdout.printf ("Download in progress. Abort.\n");
28                         return;
29                 }
30                 running = true;
31                 if (source_id != 0) {
32                         Source.remove (source_id);
33                 }
34
35                 stdout.printf ("Download started (%x).", flags);
36                 progress (0);
37                 url = "ftp://anonymous@" + mirror;
38                 flags = _flags;
39                 try {
40                         Thread.create(download_thread, false);
41                 } catch (ThreadError e) {
42                         critical ("Failed to create download thread\n");
43                         return;
44                 }
45         }
46
47         public void cancel () throws DBus.Error {
48                 cancellable.cancel ();
49         }
50
51         public string[] get_mirrors () throws DBus.Error {
52                 return null;
53         }
54
55         // Private methods
56
57         private bool do_download () {
58                 download ("ftp.fu-berlin.de/pub/misc/movies/database/", MOVIES | GENRES | RATINGS | AKAS | PLOTS);
59
60                 return false;
61         }
62
63         private void* download_thread () {
64                 description_changed ("Connecting to FTP ...");
65                 progress (0);
66                 percent_finished = 0;
67
68                 var cache_dir = Path.build_filename (Environment.get_user_cache_dir (), "cinaest");
69                 DirUtils.create_with_parents (cache_dir, 0770);
70
71                 var _sqlite = new IMDbSqlite (Path.build_filename (cache_dir, "imdb.db"));
72                 sqlite = _sqlite;
73                 _sqlite.clear ();
74
75                 try {
76                         var movie_parser = new MovieLineParser (sqlite);
77                         var genre_parser = new GenreLineParser (sqlite);
78                         var rating_parser = new RatingLineParser (sqlite);
79                         var aka_parser = new AkaLineParser (sqlite);
80                         var plot_parser = new PlotLineParser (sqlite);
81
82                         var downloader = new IMDbFtpDownloader (cancellable);
83                         downloader.progress_changed.connect (on_progress_changed);
84
85                         if (MOVIES in flags) {
86                                 description_changed ("Downloading movie list ...");
87                                 downloader.download (url + "movies.list.gz", movie_parser);
88                         }
89                         percent_finished = 20;
90                         if (GENRES in flags) {
91                                 description_changed ("Downloading genre data ...");
92                                 downloader.download (url + "genres.list.gz", genre_parser);
93                         }
94                         percent_finished = 40;
95                         if (RATINGS in flags) {
96                                 description_changed ("Downloading rating data ...");
97                                 downloader.download (url + "ratings.list.gz", rating_parser);
98                         }
99                         percent_finished = 60;
100                         if (AKAS in flags) {
101                                 description_changed ("Downloading alternative titles ...");
102                                 downloader.download (url + "aka-titles.list.gz", aka_parser);
103                         }
104                         percent_finished = 80;
105                         if (PLOTS in flags) {
106                                 description_changed ("Downloading plots ...");
107                                 downloader.download (url + "plot.list.gz", plot_parser);
108                         }
109                 } catch (Error e2) {
110                         if (e2 is IOError.CANCELLED)
111                                 stdout.printf ("Download cancelled.\n");
112                         else
113                                 warning ("Failed to open/read stream: %s\n", e2.message);
114                 }
115
116                 description_changed ("Creating indices ...");
117                 if (AKAS in flags)
118                         sqlite.create_aka_index ();
119                 if (MOVIES in flags)
120                         sqlite.create_votes_index ();
121
122                 if (!cancellable.is_cancelled ()) {
123                         stdout.printf ("Download complete.\n");
124                         progress (100);
125                 }
126
127                 sqlite = null;
128                 running = false;
129
130                 timeout_quit ();
131
132                 return null;
133         }
134
135         private void on_progress_changed (int percent) {
136                 progress (percent_finished + percent / 5);
137                 stdout.printf ("%d %%\r", percent_finished + percent / 5);
138                 stdout.flush ();
139         }
140
141         private void timeout_quit () {
142                 source_id = Timeout.add (3000, quit);
143         }
144
145         private bool quit () {
146                 loop.quit ();
147
148                 // One-shot only
149                 return false;
150         }
151
152         public void run () {
153                 loop.run ();
154         }
155
156         public static void main () {
157                 Curl.global_init (Curl.GLOBAL_DEFAULT);
158
159                 // Start server
160                 var downloader = new IMDbDownloaderCLI ();
161
162                 Idle.add (downloader.do_download);
163                 downloader.run ();
164
165                 Curl.global_cleanup ();
166         }
167 }