1 /*---------------------------------------------------------------------\
3 | |__ / \ / / . \ . \ |
8 \---------------------------------------------------------------------*/
9 /** \file zypp/media/MediaAccess.h
12 #ifndef ZYPP_MEDIA_MEDIAACCESS_H
13 #define ZYPP_MEDIA_MEDIAACCESS_H
20 #include "zypp/base/ReferenceCounted.h"
21 #include "zypp/base/NonCopyable.h"
22 #include "zypp/base/PtrTypes.h"
23 #include "zypp/base/Deprecated.h"
25 #include "zypp/Pathname.h"
26 #include "zypp/PathInfo.h"
28 #include "zypp/media/MediaException.h"
29 #include "zypp/media/MediaSource.h"
38 ///////////////////////////////////////////////////////////////////
40 // CLASS NAME : MediaAccess
42 * @short Handle access to a medium
44 * The concrete @ref MediaHandler for a certain url is created
45 * on @ref open and deleted on @close.
47 * The inteface here basically checks whether the handler exists,
48 * then forwards the request to @ref MediaHandler.
50 class MediaAccess : public base::ReferenceCounted, private base::NonCopyable
53 typedef intrusive_ptr<MediaAccess> Ptr;
54 typedef intrusive_ptr<const MediaAccess> constPtr;
58 static const Pathname _noPath;
61 * handler for 'physical' media
64 MediaHandler * _handler;
66 friend class MediaManager;
67 friend class MediaManager_Impl;
69 AttachedMedia attachedMedia() const;
71 bool isSharedMedia() const;
74 bool dependsOnParent() const;
75 bool dependsOnParent(MediaAccessId parentId,
76 bool exactIdMatch) const;
86 * open url. If preferred_attach_point is given,
87 * try to use it as attach point.
89 * <b>Caution:</b> The medium can choose a different attach point.
90 * Only getAttachPoint() knows the real attach point.
92 * \throws MediaException
95 void open( const Url& url, const Pathname & preferred_attach_point = "" );
98 * True if media is open.
100 bool isOpen() const { return( _handler != 0 ); }
103 * Hint if files are downloaded or not.
104 * @return True, if the files are downloaded.
106 bool downloads() const;
109 * Hint if files will be downloaded when using the
110 * specified media \p url.
112 * @note This hint is based on the \p url scheme
113 * only and does not imply, that the URL is valid.
115 * @param url The media URL to check.
116 * @return True, if the files are downloaded.
119 bool downloads(const Url &url);
121 * Hint whether the media can provide volatile contents
123 * @note This hint is based on the \p url scheme
124 * only and does not imply, that the URL is valid.
126 * @param url The media URL to check.
127 * @return True, if the files are downloaded.
130 bool canBeVolatile(const Url &url);
133 * Used Protocol if media is opened, otherwise 'unknown'.
135 std::string protocol() const;
138 * Url if media is opened, otherwise empty.
145 * \throws MediaException
153 * Use concrete handler to attach the media.
155 * @param next try next available device in turn until end of device
156 * list is reached (for media which are accessible through multiple
157 * devices like cdroms).
159 * \throws MediaException
162 void attach(bool next = false);
165 * True if media is attached.
167 * \throws MediaException
170 bool isAttached() const;
172 bool hasMoreDevices() const;
175 * Return the local directory that corresponds to medias url,
176 * no matter if media isAttached or not. Files requested will
177 * be available at 'localRoot() + filename' or better
178 * 'localPath( filename )'.
180 * If media is not open an empty pathname is returned.
182 Pathname localRoot() const;
185 * Short for 'localRoot() + pathname', but returns an empty
186 * pathname if media is not open.
188 * Files provided will be available at 'localPath(filename)'.
190 Pathname localPath( const Pathname & pathname ) const;
193 Use concrete handler to disconnect the media.
195 This is useful for media which e.g. holds open a connection to a
196 server like FTP. After calling disconnect() the media object still is
197 valid and files are present.
199 After calling disconnect() it's not possible to call provideFile() or
200 provideDir() anymore.
202 * \throws MediaException
208 * Use concrete handler to release the media.
209 * @param ejectDev Device to eject. None if empty.
211 * \throws MediaException
214 void release( const std::string & ejectDev = "" );
217 * Use concrete handler to provide file denoted by path below
218 * 'attach point'. Filename is interpreted relative to the
219 * attached url and a path prefix is preserved.
221 * @param cached If cached is set to true, the function checks, if
222 * the file already exists and doesn't download it again
223 * if it does. Currently only the existence is checked,
224 * no other file attributes.
225 * @param checkonly If this and 'cached' are set to true only the
226 * existence of the file is checked but it's not
227 * downloaded. If 'cached' is unset an errer is
230 * \throws MediaException
233 void provideFile( const Pathname & filename, bool cached = false, bool checkonly = false ) const;
236 * Remove filename below attach point IFF handler downloads files
237 * to the local filesystem. Never remove anything from media.
239 * \throws MediaException
242 void releaseFile( const Pathname & filename ) const;
245 * Use concrete handler to provide directory denoted
246 * by path below 'attach point' (not recursive!).
247 * 'dirname' is interpreted relative to the
248 * attached url and a path prefix is preserved.
250 * \throws MediaException
253 void provideDir( const Pathname & dirname ) const;
256 * Use concrete handler to provide directory tree denoted
257 * by path below 'attach point' (recursive!!).
258 * 'dirname' is interpreted relative to the
259 * attached url and a path prefix is preserved.
261 * \throws MediaException
264 void provideDirTree( const Pathname & dirname ) const;
267 * Remove directory tree below attach point IFF handler downloads files
268 * to the local filesystem. Never remove anything from media.
270 * \throws MediaException
273 void releaseDir( const Pathname & dirname ) const;
276 * Remove pathname below attach point IFF handler downloads files
277 * to the local filesystem. Never remove anything from media.
279 * If pathname denotes a directory it is recursively removed.
280 * If pathname is empty or '/' everything below the attachpoint
281 * is recursively removed.
283 * \throws MediaException
286 void releasePath( const Pathname & pathname ) const;
291 * Return content of directory on media via retlist. If dots is false
292 * entries starting with '.' are not reported.
294 * The request is forwarded to the concrete handler,
295 * which may atempt to retieve the content e.g. via 'readdir'
297 * <B>Caution:</B> This is not supported by all media types.
298 * Be prepared to handle E_not_supported_by_media.
300 * \throws MediaException
303 void dirInfo( std::list<std::string> & retlist,
304 const Pathname & dirname, bool dots = true ) const;
307 * Basically the same as dirInfo above. The content is returned as
308 * filesystem::DirContent, which includes name and filetype of each directory
309 * entry. Retrieving the filetype usg. requires an additional ::stat call for
310 * each entry, thus it's more expensive than a simple readdir.
312 * <B>Caution:</B> This is not supported by all media types.
313 * Be prepared to handle E_not_supported_by_media.
315 * \throws MediaException
318 void dirInfo( filesystem::DirContent & retlist,
319 const Pathname & dirname, bool dots = true ) const;
322 * check if a file exists
324 * Asserted that url is a file and not a dir.
326 * \throws MediaException
329 bool doesFileExist( const Pathname & filename ) const;
334 virtual ~MediaAccess();
338 virtual std::ostream & dumpOn( std::ostream & str ) const;
342 * Get file from location at specified by URL and copy it to
345 * @param from Source URL
346 * @param to Destination file name
348 * \throws MediaException
351 void getFile( const Url &from, const Pathname &to );
356 * Helper class that provides file on construction
357 * and cleans up on destruction.
359 * <b>Caution:</b> There's no synchronisation between multiple
360 * FileProvider instances, that provide the same file from the
361 * same media. If the first one goes out of scope, the file is
362 * cleaned. It's just a convenience for 'access and forgett'.
364 * <b>Caution:</b> We should either store the reference MediaAccess'
365 * MediaHandler here (for this MediaHandler must become a
366 * ref counting pointer class), or we need more info from MediaHandler
367 * (whether he's downloading to the local fs. If not, no releasefile
369 * Currently we can not releaseFile after the media was closed
370 * (it's passed to the handler, which is deleted on close).
372 * \throws MediaBadFilenameException
373 * \throws MediaException
376 FileProvider( const FileProvider & ); // no copy
377 FileProvider & operator=( const FileProvider & ); // no assign
379 MediaAccess::constPtr _media;
381 Pathname _local_file;
384 * \throws MediaException
386 FileProvider( MediaAccess::constPtr media_r, const Pathname & file_r )
391 if ( _file.empty() ) {
392 ZYPP_THROW(MediaBadFilenameException(_file.asString()));
393 } else if ( _media ) {
395 _media->provideFile( _file );
396 _local_file = _media->localPath( _file );
398 catch (const MediaException & excpt_r)
400 ZYPP_CAUGHT(excpt_r);
402 ZYPP_RETHROW(excpt_r);
411 _media->releaseFile( _file );
413 catch (const MediaException &excpt_r)
415 ZYPP_CAUGHT(excpt_r);
417 catch(...) {} // No exception from dtor!
424 * If no error, expect operator() to return the local
425 * Pathname of the provided file.
427 Pathname localFile() const { return _local_file; }
430 * Return the local Pathname of the provided file or
431 * an empty Pathname on error.
433 Pathname operator()() const {
435 return _media->localPath( _file );
441 std::ostream & operator<<( std::ostream & str, const MediaAccess & obj );
443 ///////////////////////////////////////////////////////////////////
448 #endif // ZYPP_MEDIA_MEDIAACCESS_H