]> git.mxchange.org Git - simgear.git/blob - simgear/package/Root.cxx
6783b331ed7bc0a698c62023f71ed16d87dd8932
[simgear.git] / simgear / package / Root.cxx
1
2
3 #include <simgear/package/Root.hxx>
4
5 #include <boost/foreach.hpp>
6 #include <cstring>
7
8 #include <simgear/debug/logstream.hxx>
9 #include <simgear/props/props_io.hxx>
10 #include <simgear/io/HTTPRequest.hxx>
11 #include <simgear/io/HTTPClient.hxx>
12 #include <simgear/misc/sg_dir.hxx>
13 #include <simgear/structure/exception.hxx>
14 #include <simgear/package/Package.hxx>
15 #include <simgear/package/Install.hxx>
16 #include <simgear/package/Catalog.hxx>
17
18 namespace simgear {
19     
20 namespace pkg {
21
22 void Root::setMaxAgeSeconds(int seconds)
23 {
24     m_maxAgeSeconds = seconds;
25 }
26
27 void Root::setHTTPClient(HTTP::Client* aHTTP)
28 {
29     m_http = aHTTP;
30 }
31
32 HTTP::Client* Root::getHTTPClient() const
33 {
34     return m_http;
35 }
36
37 Root::Root(const SGPath& aPath) :
38     m_path(aPath),
39     m_http(NULL),
40     m_maxAgeSeconds(60 * 60 * 24),
41     m_delegate(NULL)
42 {
43     if (getenv("LOCALE")) {
44         m_locale = getenv("LOCALE");
45     }
46     
47     Dir d(aPath);
48     if (!d.exists()) {
49         d.create(0755);
50         return;
51     }
52     
53     BOOST_FOREACH(SGPath c, d.children(Dir::TYPE_DIR)) {
54         Catalog* cat = Catalog::createFromPath(this, c);
55         if (cat) {
56            m_catalogs[cat->id()] = cat;     
57         }
58     } // of child directories iteration
59 }
60
61 Root::~Root()
62 {
63     
64 }
65
66 Catalog* Root::getCatalogById(const std::string& aId) const
67 {
68     CatalogDict::const_iterator it = m_catalogs.find(aId);
69     if (it == m_catalogs.end()) {
70         return NULL;
71     }
72     
73     return it->second;
74 }
75
76 Package* Root::getPackageById(const std::string& aName) const
77 {
78     size_t lastDot = aName.rfind('.');
79     
80     Package* pkg = NULL;
81     if (lastDot == std::string::npos) {
82         // naked package ID
83         CatalogDict::const_iterator it = m_catalogs.begin();
84         for (; it != m_catalogs.end(); ++it) {
85             pkg = it->second->getPackageById(aName);
86             if (pkg) {
87                 return pkg;
88             }
89         }
90         
91         return NULL;
92     }
93     
94     std::string catalogId = aName.substr(0, lastDot);
95     std::string id = aName.substr(lastDot + 1);    
96     Catalog* catalog = getCatalogById(catalogId);
97     if (!catalog) {
98         return NULL;
99     }
100             
101     return catalog->getPackageById(id);
102 }
103
104 CatalogList Root::catalogs() const
105 {
106     CatalogList r;
107     CatalogDict::const_iterator it = m_catalogs.begin();
108     for (; it != m_catalogs.end(); ++it) {
109         r.push_back(it->second);
110     }
111     
112     return r;
113 }
114
115 PackageList
116 Root::packagesMatching(const SGPropertyNode* aFilter) const
117 {
118     PackageList r;
119     
120     CatalogDict::const_iterator it = m_catalogs.begin();
121     for (; it != m_catalogs.end(); ++it) {
122         PackageList r2(it->second->packagesMatching(aFilter));
123         r.insert(r.end(), r2.begin(), r2.end());
124     }
125     
126     return r;
127 }
128
129 PackageList
130 Root::packagesNeedingUpdate() const
131 {
132     PackageList r;
133     
134     CatalogDict::const_iterator it = m_catalogs.begin();
135     for (; it != m_catalogs.end(); ++it) {
136         PackageList r2(it->second->packagesNeedingUpdate());
137         r.insert(r.end(), r2.begin(), r2.end());
138     }
139     
140     return r;
141 }
142
143 void Root::refresh(bool aForce)
144 {
145     CatalogDict::iterator it = m_catalogs.begin();
146     for (; it != m_catalogs.end(); ++it) {
147         if (aForce || (it->second->ageInSeconds() > m_maxAgeSeconds)) {
148             it->second->refresh();
149         }
150     }
151 }
152
153 void Root::setLocale(const std::string& aLocale)
154 {
155     m_locale = aLocale;
156 }
157
158 std::string Root::getLocale() const
159 {
160     return m_locale;
161 }
162
163 void Root::scheduleToUpdate(Install* aInstall)
164 {
165     bool wasEmpty = m_updateDeque.empty();
166     m_updateDeque.push_back(aInstall);
167     if (wasEmpty) {
168         aInstall->startUpdate();
169     }
170 }
171
172 void Root::startInstall(Install* aInstall)
173 {
174     if (m_delegate) {
175         m_delegate->startInstall(aInstall);
176     }
177 }
178
179 void Root::installProgress(Install* aInstall, unsigned int aBytes, unsigned int aTotal)
180 {
181     if (m_delegate) {
182         m_delegate->installProgress(aInstall, aBytes, aTotal);
183     }
184 }
185
186 void Root::startNext(Install* aCurrent)
187 {
188     if (m_updateDeque.front() != aCurrent) {
189         SG_LOG(SG_GENERAL, SG_ALERT, "current install of package not head of the deque");
190     } else {
191         m_updateDeque.pop_front();
192     }
193     
194     if (!m_updateDeque.empty()) {
195         m_updateDeque.front()->startUpdate();
196     }
197 }
198
199 void Root::finishInstall(Install* aInstall)
200 {
201     if (m_delegate) {
202         m_delegate->finishInstall(aInstall);
203     }
204     
205     startNext(aInstall);
206 }
207
208 void Root::failedInstall(Install* aInstall, Delegate::FailureCode aReason)
209 {
210     SG_LOG(SG_GENERAL, SG_ALERT, "failed to install package:" 
211         << aInstall->package()->id() << ":" << aReason);
212     if (m_delegate) {
213         m_delegate->failedInstall(aInstall, aReason);
214     }
215     
216     startNext(aInstall);
217 }
218
219 void Root::catalogRefreshBegin(Catalog* aCat)
220 {
221     m_refreshing.insert(aCat);
222 }
223
224 void Root::catalogRefreshComplete(Catalog* aCat, bool aSuccess)
225 {
226     m_refreshing.erase(aCat);
227     if (m_refreshing.empty()) {
228         if (m_delegate) {
229             m_delegate->refreshComplete();
230         }
231     }
232 }
233
234 } // of namespace pkg
235
236 } // of namespace simgear