- Implemented isSharedMedia() method returning
[platform/upstream/libzypp.git] / zypp / media / MediaAccess.cc
1 /*---------------------------------------------------------------------\
2 |                          ____ _   __ __ ___                          |
3 |                         |__  / \ / / . \ . \                         |
4 |                           / / \ V /|  _/  _/                         |
5 |                          / /__ | | | | | |                           |
6 |                         /_____||_| |_| |_|                           |
7 |                                                                      |
8 \---------------------------------------------------------------------*/
9 /** \file zypp/media/MediaAccess.cc
10  *
11 */
12
13 #include <ctype.h>
14
15 #include <iostream>
16
17 #include "zypp/base/Logger.h"
18
19 #include "zypp/media/MediaException.h"
20 #include "zypp/media/MediaAccess.h"
21 #include "zypp/media/MediaHandler.h"
22
23 #include "zypp/media/MediaNFS.h"
24 #include "zypp/media/MediaCD.h"
25 #include "zypp/media/MediaDIR.h"
26 #include "zypp/media/MediaDISK.h"
27 #include "zypp/media/MediaSMB.h"
28 #include "zypp/media/MediaCIFS.h"
29 #include "zypp/media/MediaCurl.h"
30
31 using namespace std;
32
33 namespace zypp {
34   namespace media {
35
36 ///////////////////////////////////////////////////////////////////
37 //
38 //      CLASS NAME : MediaAccess
39 //
40 ///////////////////////////////////////////////////////////////////
41
42 const Pathname MediaAccess::_noPath; // empty path
43
44 ///////////////////////////////////////////////////////////////////
45 // constructor
46 MediaAccess::MediaAccess ()
47     : _handler (0)
48 {
49 }
50
51 // destructor
52 MediaAccess::~MediaAccess()
53 {
54   try
55     {
56       close(); // !!! make sure handler gets properly deleted.
57     }
58   catch(...) {}
59 }
60
61 AttachedMedia
62 MediaAccess::attachedMedia() const
63 {
64         return _handler ? _handler->attachedMedia()
65                         : AttachedMedia();
66 }
67
68 bool
69 MediaAccess::isSharedMedia() const
70 {
71         return _handler ? _handler->isSharedMedia()
72                         : false;
73 }
74
75 // open URL
76 void
77 MediaAccess::open (const Url& url, const Pathname & preferred_attach_point)
78 {
79     if(!url.isValid()) {
80         MIL << "Url is not valid" << endl;
81         ZYPP_THROW(MediaBadUrlException(url));
82     }
83
84     close();
85
86     std::string scheme = url.getScheme();
87
88     MIL << "Trying scheme '" << scheme << "'" << endl;
89
90     if (scheme == "cd" || scheme == "dvd")
91         _handler = new MediaCD (url,preferred_attach_point);
92     else if (scheme == "nfs")
93         _handler = new MediaNFS (url,preferred_attach_point);
94 //    else if (scheme == "iso")
95 //        _handler = new MediaISO (url,preferred_attach_point);
96     else if (scheme == "file" || scheme == "dir")
97         _handler = new MediaDIR (url,preferred_attach_point);
98     else if (scheme == "hd")
99         _handler = new MediaDISK (url,preferred_attach_point);
100     else if (scheme == "smb")
101         _handler = new MediaSMB (url,preferred_attach_point);
102     else if (scheme == "cifs")
103         _handler = new MediaCIFS (url,preferred_attach_point);
104     else if (scheme == "ftp" || scheme == "http" || scheme == "https")
105         _handler = new MediaCurl (url,preferred_attach_point);
106     else
107     {
108         ZYPP_THROW(MediaUnsupportedUrlSchemeException(url));
109     }
110
111     // check created handler
112     if ( !_handler ){
113       ERR << "Failed to create media handler" << endl;
114       ZYPP_THROW(MediaSystemException(url, "Failed to create media handler"));
115     }
116
117     MIL << "Opened: " << *this << endl;
118 }
119
120 // Type of media if open, otherwise NONE.
121 std::string
122 MediaAccess::protocol() const
123 {
124   if ( !_handler )
125     return "unknown";
126
127   return _handler->protocol();
128 }
129
130 ///////////////////////////////////////////////////////////////////
131 //
132 //
133 //      METHOD NAME : MediaAccess::url
134 //      METHOD TYPE : Url
135 //
136 Url MediaAccess::url() const
137 {
138   if ( !_handler )
139     return Url();
140
141   return _handler->url();
142 }
143
144 // close handler
145 void
146 MediaAccess::close ()
147 {
148   ///////////////////////////////////////////////////////////////////
149   // !!! make shure handler gets properly deleted.
150   // I.e. release attached media before deleting the handler.
151   ///////////////////////////////////////////////////////////////////
152   if ( _handler ) {
153     try {
154       _handler->release();
155     }
156     catch (const MediaException & excpt_r)
157     {
158       ZYPP_CAUGHT(excpt_r);
159       WAR << "Close: " << *this << " (" << excpt_r << ")" << endl;
160       ZYPP_RETHROW(excpt_r);
161     }
162     MIL << "Close: " << *this << " (OK)" << endl;
163     delete _handler;
164     _handler = 0;
165   }
166 }
167
168
169 // attach media
170 void MediaAccess::attach (bool next)
171 {
172   if ( !_handler ) {
173     ZYPP_THROW(MediaNotOpenException("attach"));
174   }
175   _handler->attach(next);
176 }
177
178 // True if media is open and attached.
179 bool
180 MediaAccess::isAttached() const
181 {
182   return( _handler && _handler->isAttached() );
183 }
184
185 // local directory that corresponds to medias url
186 // If media is not open an empty pathname.
187 const Pathname &
188 MediaAccess::localRoot() const
189 {
190   if ( !_handler )
191     return _noPath;
192
193   return _handler->localRoot();
194 }
195
196 // Short for 'localRoot() + pathname', but returns an empty
197 // * pathname if media is not open.
198 Pathname
199 MediaAccess::localPath( const Pathname & pathname ) const
200 {
201   if ( !_handler )
202     return _noPath;
203
204   return _handler->localPath( pathname );
205 }
206
207 void
208 MediaAccess::disconnect()
209 {
210   if ( !_handler )
211     ZYPP_THROW(MediaNotOpenException("disconnect"));
212
213   _handler->disconnect();
214 }
215
216 // release attached media
217 void
218 MediaAccess::release( bool eject )
219 {
220   if ( !_handler )
221     return;
222
223   _handler->release( eject );
224 }
225
226
227 // provide file denoted by path to attach dir
228 //
229 // filename is interpreted relative to the attached url
230 // and a path prefix is preserved to destination
231 void
232 MediaAccess::provideFile( const Pathname & filename, bool cached, bool checkonly) const
233 {
234   if ( cached ) {
235     PathInfo pi( localPath( filename ) );
236     if ( pi.isExist() )
237       return;
238   }
239
240   if(checkonly)
241     ZYPP_THROW(MediaFileNotFoundException(url(), filename));
242
243   if ( !_handler ) {
244     ZYPP_THROW(MediaNotOpenException("provideFile(" + filename.asString() + ")"));
245   }
246
247   _handler->provideFile( filename );
248 }
249
250 void
251 MediaAccess::releaseFile( const Pathname & filename ) const
252 {
253   if ( !_handler )
254     return;
255
256   _handler->releaseFile( filename );
257 }
258
259 // provide directory tree denoted by path to attach dir
260 //
261 // dirname is interpreted relative to the attached url
262 // and a path prefix is preserved to destination
263 void
264 MediaAccess::provideDir( const Pathname & dirname ) const
265 {
266   if ( !_handler ) {
267     ZYPP_THROW(MediaNotOpenException("provideDir(" + dirname.asString() + ")"));
268   }
269
270   _handler->provideDir( dirname );
271 }
272
273 void
274 MediaAccess::provideDirTree( const Pathname & dirname ) const
275 {
276   if ( !_handler ) {
277     ZYPP_THROW(MediaNotOpenException("provideDirTree(" + dirname.asString() + ")"));
278   }
279
280   _handler->provideDirTree( dirname );
281 }
282
283 void
284 MediaAccess::releaseDir( const Pathname & dirname ) const
285 {
286   if ( !_handler )
287     return;
288
289   _handler->releaseDir( dirname );
290 }
291
292 void
293 MediaAccess::releasePath( const Pathname & pathname ) const
294 {
295   if ( !_handler )
296     return;
297
298   _handler->releasePath( pathname );
299 }
300
301 // Return content of directory on media
302 void
303 MediaAccess::dirInfo( list<string> & retlist, const Pathname & dirname, bool dots ) const
304 {
305   retlist.clear();
306
307   if ( !_handler ) {
308     ZYPP_THROW(MediaNotOpenException("dirInfo(" + dirname.asString() + ")"));
309   }
310
311   _handler->dirInfo( retlist, dirname, dots );
312 }
313
314 // Return content of directory on media
315 void
316 MediaAccess::dirInfo( filesystem::DirContent & retlist, const Pathname & dirname, bool dots ) const
317 {
318   retlist.clear();
319
320   if ( !_handler ) {
321     ZYPP_THROW(MediaNotOpenException("dirInfo(" + dirname.asString() + ")"));
322   }
323
324   _handler->dirInfo( retlist, dirname, dots );
325 }
326
327 std::ostream &
328 MediaAccess::dumpOn( std::ostream & str ) const
329 {
330   if ( !_handler )
331     return str << "MediaAccess( closed )";
332
333   str << _handler->protocol() << "(" << *_handler << ")";
334   return str;
335 }
336
337 void MediaAccess::getFile( const Url &from, const Pathname &to )
338 {
339   DBG << "From: " << from << endl << "To: " << to << endl;
340
341   Pathname path = from.getPathData();
342   Pathname dir = path.dirname();
343   string base = path.basename();
344
345   Url u = from;
346   u.setPathData( dir.asString() );
347
348   MediaAccess media;
349
350   try {
351     media.open( u );
352     media.attach();
353     media._handler->provideFileCopy( base, to );
354     media.release();
355   }
356   catch (const MediaException & excpt_r)
357   {
358     ZYPP_RETHROW(excpt_r);
359   }
360 }
361     std::ostream & operator<<( std::ostream & str, const MediaAccess & obj )
362     { return obj.dumpOn( str ); }
363
364 ///////////////////////////////////////////////////////////////////
365   } // namespace media
366 } // namespace zypp