libzypp: zypp/ng/workflows/downloadwf.cc Source File

libzypp 17.36.6

downloadwf.cc
Go to the documentation of this file.
1/*---------------------------------------------------------------------\
2| ____ _ __ __ ___ |
3| |__ / \ / / . \ . \ |
4| / / \ V /| _/ _/ |
5| / /__ | | | | | | |
6| /_____||_| |_| |_| |
7| |
8\---------------------------------------------------------------------*/
9
10#include "downloadwf.h"
11#include <zypp/ng/workflows/logichelpers.h>
12
13#include <utility>
14#include <zypp/ng/Context>
15#include <zypp/ng/workflows/contextfacade.h>
16#include <zypp/ng/workflows/checksumwf.h>
17
18
19#include <zypp-core/fs/PathInfo.h>
20#include <zypp-core/zyppng/pipelines/Algorithm>
21
22#include <zypp-media/ng/Provide>
23#include <zypp-media/ng/ProvideSpec>
24
25namespace zyppng {
26
27 template<typename ZyppContextRefType>
28 CacheProviderContext<ZyppContextRefType>::CacheProviderContext( ZYPP_PRIVATE_CONSTR_ARG, ZyppContextRefType zyppContext, zypp::Pathname destDir )
29 : _zyppContext( std::move(zyppContext) )
30 , _destDir( std::move(destDir) )
31 { }
32
33
34 template<typename ZyppContextRefType>
35 const typename CacheProviderContext<ZyppContextRefType>::ContextRefType &CacheProviderContext<ZyppContextRefType>::zyppContext() const
36 {
37 return _zyppContext;
38 }
39
40
41 template<typename ZyppContextRefType>
42 const zypp::Pathname &CacheProviderContext<ZyppContextRefType>::destDir() const
43 {
44 return _destDir;
45 }
46
47 template<typename ZyppContextRefType>
48 void CacheProviderContext<ZyppContextRefType>::addCacheDir(const zypp::Pathname &p)
49 {
50 _cacheDirs.push_back ( p );
51 }
52
53 template<typename ZyppContextRefType>
54 const std::vector<zypp::Pathname> &CacheProviderContext<ZyppContextRefType>::cacheDirs() const
55 {
56 return _cacheDirs;
57 }
58
59
60 template class CacheProviderContext<ContextRef>;
61 template class CacheProviderContext<SyncContextRef>;
62
63
64 namespace {
65
66 using namespace zyppng::operators;
67
68 class CacheMissException : public zypp::Exception
69 {
70 public:
71 CacheMissException( const zypp::Pathname &filename )
72 : zypp::Exception( zypp::str::Str() << filename << " not found in target cache" ) { }
73 };
74
75 template <class T>
76 struct showme;
77
78 template <class Executor, class OpType>
79 struct ProvideFromCacheOrMediumLogic : public LogicBase<Executor, OpType> {
80 protected:
81
82 ZYPP_ENABLE_LOGIC_BASE(Executor, OpType);
83
84 using CacheProviderContextRefType = std::conditional_t<detail::is_async_op_v<OpType>, AsyncCacheProviderContextRef, SyncCacheProviderContextRef>;
85 using ContextType = typename remove_smart_ptr_t<CacheProviderContextRefType>::ContextType;
86 using ProvideType = typename ContextType::ProvideType;
87 using MediaHandle = typename ProvideType::MediaHandle;
88 using ProvideRes = typename ProvideType::Res;
89
90 public:
91 ProvideFromCacheOrMediumLogic( CacheProviderContextRefType cacheContext, MediaHandle &&medium, zypp::Pathname &&file, ProvideFileSpec &&filespec )
92 : _ctx( std::move(cacheContext) )
93 , _medium( std::move(medium) )
94 , _file(std::move( file ))
95 , _filespec( std::move(filespec) ) {}
96
97 MaybeAsyncRef<expected<zypp::ManagedFile>> execute() {
98
99 return findFileInCache( )
100 | [this]( expected<zypp::ManagedFile> cached ) -> MaybeAsyncRef<expected<zypp::ManagedFile>> {
101 if ( !cached ) {
102 MIL << "Didn't find " << _file << " in the caches, providing from medium" << std::endl;
103
104 // we didn't find it in the caches or the lookup failed, lets provide and check it
105 std::shared_ptr<ProvideType> provider = _ctx->zyppContext()->provider();
106 return provider->provide( _medium, _file, _filespec )
107 | and_then( [this]( ProvideRes res ) {
108 return verifyFile( res.file() )
109 | and_then( [res = res]() {
110 return expected<ProvideRes>::success( std::move(res) );
111 });
112 })
113 | and_then( ProvideType::copyResultToDest( _ctx->zyppContext()->provider(), _ctx->destDir() / _file ) )
114 | and_then( []( zypp::ManagedFile &&file ){
115 file.resetDispose ();
116 return make_expected_success (std::move(file));
117 }) ;
118
119 } else {
120
121 return verifyFile ( cached.get() )
122 | and_then([ this, cachedFile = cached.get() ]() mutable {
123 if ( cachedFile == _ctx->destDir() / _file ) {
124 cachedFile.resetDispose(); // make sure dispose is reset
125 return makeReadyResult( expected<zypp::ManagedFile>::success(std::move(cachedFile) ));
126 }
127
128 const auto &targetPath = _ctx->destDir() / _file;
129 zypp::filesystem::assert_dir( targetPath.dirname () );
130
131 return _ctx->zyppContext()->provider()->copyFile( cachedFile, _ctx->destDir() / _file )
132 | and_then( [cachedFile]( zypp::ManagedFile &&f) { f.resetDispose(); return make_expected_success (std::move(f)); });
133 });
134 }
135 };
136 }
137
138 protected:
143 MaybeAsyncRef<expected<zypp::ManagedFile>> findFileInCache( ) {
144
145 // No checksum - no match
146 if ( _filespec.checksum().empty() )
147 return makeReadyResult( expected<zypp::ManagedFile>::error(std::make_exception_ptr( CacheMissException(_file) )) );
148
149 const auto &confDirs = _ctx->cacheDirs();
150 const auto targetFile = _ctx->destDir() / _file ;
151 std::vector<zypp::Pathname> caches;
152 caches.push_back( _ctx->destDir() );
153 caches.insert( caches.end(), confDirs.begin(), confDirs.end() );
154
155 auto makeSearchPipeline = [this, targetFile]( zypp::Pathname cachePath ){
156 zypp::Pathname cacheFilePath( cachePath / _file );
157 zypp::PathInfo cacheFileInfo( cacheFilePath );
158 if ( !cacheFileInfo.isExist () ) {
159 return makeReadyResult(expected<zypp::ManagedFile>::error( std::make_exception_ptr (CacheMissException(_file)) ));
160 } else {
161 auto provider = _ctx->zyppContext()->provider();
162
163 // calc checksum, but do not use the workflow. Here we don't want to ask the user if a wrong checksum should
164 // be accepted
165 return provider->checksumForFile( cacheFilePath, _filespec.checksum().type() )
166 | and_then([this, cacheFilePath, targetFile]( zypp::CheckSum sum ) {
167
168 auto mgdFile = zypp::ManagedFile( cacheFilePath );
169
170 // if the file is in the target dir, make sure to release it if its not used
171 if ( cacheFilePath == targetFile )
172 mgdFile.setDispose ( zypp::filesystem::unlink );
173
174 if ( sum == _filespec.checksum () ) {
175 // we found the file!
176 return expected<zypp::ManagedFile>::success( std::move(mgdFile) );
177 }
178
179 return expected<zypp::ManagedFile>::error( std::make_exception_ptr (CacheMissException(_file)) );
180 });
181 }
182 };
183
184 auto defVal = expected<zypp::ManagedFile>::error( std::make_exception_ptr (CacheMissException(_file) ) );
185 return std::move(caches) | firstOf( std::move(makeSearchPipeline), std::move(defVal), detail::ContinueUntilValidPredicate() );
186 }
187
188 MaybeAsyncRef<expected<void>> verifyFile ( const zypp::Pathname &dlFilePath ) {
189
190 return zypp::Pathname( dlFilePath )
191 | [this]( zypp::Pathname &&dlFilePath ) {
192 if ( !_filespec.checksum().empty () ) {
193 return CheckSumWorkflow::verifyChecksum( _ctx->zyppContext(), _filespec.checksum (), std::move(dlFilePath) );
194 }
195 return makeReadyResult(expected<void>::success());
196 };
197 // add other verifier here via and_then(), like a signature based one
198 }
199
200 CacheProviderContextRefType _ctx;
201 MediaHandle _medium;
202 zypp::Pathname _file;
203 ProvideFileSpec _filespec;
204 };
205 }
206
207 namespace DownloadWorkflow {
208
209 AsyncOpRef<expected<zypp::ManagedFile> > provideToCacheDir( AsyncCacheProviderContextRef cacheContext, ProvideMediaHandle medium, zypp::Pathname file, ProvideFileSpec filespec )
210 {
211 return SimpleExecutor<ProvideFromCacheOrMediumLogic, AsyncOp<expected<zypp::ManagedFile>>>::run( std::move(cacheContext), std::move(medium), std::move(file), std::move(filespec) );
212 }
213
214 expected<zypp::ManagedFile> provideToCacheDir(SyncCacheProviderContextRef cacheContext, SyncMediaHandle medium, zypp::Pathname file, ProvideFileSpec filespec )
215 {
216 return SimpleExecutor<ProvideFromCacheOrMediumLogic, SyncOp<expected<zypp::ManagedFile>>>::run( std::move(cacheContext), std::move(medium), std::move(file), std::move(filespec) );
217 }
218
219 }
220
221}
checksumwf.h
zypp::CheckSum
Definition CheckSum.h:34
zypp::Exception
Base class for Exception.
Definition Exception.h:147
zypp::filesystem::PathInfo
Wrapper class for stat/lstat.
Definition PathInfo.h:226
zypp::filesystem::Pathname
Pathname.
Definition Pathname.h:47
zyppng::CacheProviderContext
Definition downloadwf.h:28
zyppng::CacheProviderContext::destDir
const zypp::Pathname & destDir() const
Definition downloadwf.cc:42
zyppng::CacheProviderContext::zyppContext
const ContextRefType & zyppContext() const
Definition downloadwf.cc:35
zyppng::CacheProviderContext::_zyppContext
ContextRefType _zyppContext
Definition downloadwf.h:47
zyppng::CacheProviderContext::_cacheDirs
std::vector< zypp::Pathname > _cacheDirs
Definition downloadwf.h:49
zyppng::CacheProviderContext< ContextRef >::_destDir
zypp::Pathname _destDir
Definition downloadwf.h:48
zyppng::CacheProviderContext::ContextRefType
ZyppContextRefType ContextRefType
Definition downloadwf.h:32
zyppng::CacheProviderContext::addCacheDir
void addCacheDir(const zypp::Pathname &p)
Definition downloadwf.cc:48
zyppng::CacheProviderContext::cacheDirs
const std::vector< zypp::Pathname > & cacheDirs() const
Definition downloadwf.cc:54
zyppng::ProvideFileSpec
Definition providespec.h:92
zyppng::ProvideMediaHandle
Definition provide.h:52
zyppng::ProvideRes
A ProvideRes object is a reference counted ownership of a resource in the cache provided by a Provide...
Definition provideres.h:36
zyppng::ProvideRes::file
const zypp::Pathname file() const
Definition provideres.cc:21
zyppng::SyncMediaHandle
Definition mediafacade.h:26
zyppng::expected
Definition expected.h:27
zyppng::expected::success
static expected success(ConsParams &&...params)
Definition expected.h:115
zyppng::expected::error
static expected error(ConsParams &&...params)
Definition expected.h:126
contextfacade.h
downloadwf.h
logichelpers.h
ZYPP_ENABLE_LOGIC_BASE
#define ZYPP_ENABLE_LOGIC_BASE(Executor, OpType)
Definition logichelpers.h:223
std
Definition Arch.h:364
std::conditional_t
typename conditional< B, T, F >::type conditional_t
Definition TypeTraits.h:39
str
String related utilities and Regular expression matching.
zypp::filesystem::unlink
int unlink(const Pathname &path)
Like 'unlink'.
Definition PathInfo.cc:705
zypp::filesystem::assert_dir
int assert_dir(const Pathname &path, unsigned mode)
Like 'mkdir -p'.
Definition PathInfo.cc:324
zypp
Easy-to use interface to the ZYPP dependency resolver.
Definition Application.cc:20
zypp::ManagedFile
AutoDispose< const Pathname > ManagedFile
A Pathname plus associated cleanup code to be executed when path is no longer needed.
Definition ManagedFile.h:27
zypp::_file
Pathname _file
Definition SystemCheck.cc:34
zyppng::CheckSumWorkflow::verifyChecksum
expected< void > verifyChecksum(SyncContextRef zyppCtx, zypp::CheckSum checksum, zypp::Pathname file)
Definition checksumwf.cc:115
zyppng::DownloadWorkflow
Definition downloadwf.cc:207
zyppng::DownloadWorkflow::provideToCacheDir
AsyncOpRef< expected< zypp::ManagedFile > > provideToCacheDir(AsyncCacheProviderContextRef cacheContext, ProvideMediaHandle medium, zypp::Pathname file, ProvideFileSpec filespec)
Definition downloadwf.cc:209
zyppng::operators
Definition asyncresult.h:279
zyppng::operators::and_then
auto and_then(Fun &&function)
Definition expected.h:623
zyppng
Definition MediaCurl2.h:22
zyppng::makeReadyResult
std::conditional_t< isAsync, AsyncOpRef< T >, T > makeReadyResult(T &&result)
Definition asyncop.h:297
zyppng::AsyncOpRef
std::shared_ptr< AsyncOp< T > > AsyncOpRef
Definition asyncop.h:255
zyppng::remove_smart_ptr_t
typename remove_smart_ptr< T >::type remove_smart_ptr_t
Definition type_traits.h:133
zyppng::make_expected_success
static expected< std::decay_t< Type >, Err > make_expected_success(Type &&t)
Definition expected.h:397
zyppng::firstOf
auto firstOf(Transformation &&transformFunc, DefaultType &&def, Predicate &&predicate=detail::ContinueUntilValidPredicate())
Definition algorithm.h:149
zyppng::LogicBase
Definition logichelpers.h:161
zyppng::SimpleExecutor
Definition logichelpers.h:212
zyppng::detail::ContinueUntilValidPredicate
Definition algorithm.h:24
MIL
#define MIL
Definition Logger.h:100
PathInfo.h
ZYPP_PRIVATE_CONSTR_ARG
#define ZYPP_PRIVATE_CONSTR_ARG
Definition zyppglobal.h:160