Medical Imaging Interaction Toolkit  2018.4.99-87d68d9f
Medical Imaging Interaction Toolkit
usModuleResource.cpp
Go to the documentation of this file.
1 /*============================================================================
2 
3  Library: CppMicroServices
4 
5  Copyright (c) German Cancer Research Center (DKFZ)
6  All rights reserved.
7 
8  Licensed under the Apache License, Version 2.0 (the "License");
9  you may not use this file except in compliance with the License.
10  You may obtain a copy of the License at
11 
12  http://www.apache.org/licenses/LICENSE-2.0
13 
14  Unless required by applicable law or agreed to in writing, software
15  distributed under the License is distributed on an "AS IS" BASIS,
16  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  See the License for the specific language governing permissions and
18  limitations under the License.
19 
20 ============================================================================*/
21 
22 
23 #include "usModuleResource.h"
24 
25 #include "usAtomicInt_p.h"
26 #include "usModuleResourceContainer_p.h"
27 #include "usModuleInfo.h"
28 
29 #include <string>
30 
31 US_BEGIN_NAMESPACE
32 
33 class ModuleResourcePrivate
34 {
35 
36 public:
37 
38  ModuleResourcePrivate(const ModuleResourceContainer* rc)
39  : resourceContainer(rc)
40  , ref(1)
41  {}
42 
43  void InitFilePath(const std::string& file);
44 
45  const ModuleResourceContainer* const resourceContainer;
46 
47  ModuleResourceContainer::Stat stat;
48 
49  std::string fileName;
50  std::string path;
51 
52  mutable std::vector<std::string> children;
53  mutable std::vector<uint32_t> childNodes;
54 
58  AtomicInt ref;
59 };
60 
61 void ModuleResourcePrivate::InitFilePath(const std::string& file)
62 {
63  std::string normalizedFile = file;
64  if (normalizedFile.empty() || normalizedFile[0] != '/')
65  {
66  normalizedFile = '/' + normalizedFile;
67  }
68 
69  std::string rawPath;
70  std::size_t index = normalizedFile.find_last_of('/');
71  if (index == std::string::npos)
72  {
73  fileName = normalizedFile;
74  }
75  else if (index < normalizedFile.size()-1)
76  {
77  fileName = normalizedFile.substr(index+1);
78  rawPath = normalizedFile.substr(0,index+1);
79  }
80  else
81  {
82  rawPath = normalizedFile;
83  }
84 
85  // remove duplicate /
86  std::string::value_type lastChar = 0;
87  for (std::size_t i = 0; i < rawPath.size(); ++i)
88  {
89  if (rawPath[i] == '/' && lastChar == '/')
90  {
91  continue;
92  }
93  lastChar = rawPath[i];
94  path.push_back(lastChar);
95  }
96  if (path.empty())
97  {
98  path.push_back('/');
99  }
100 }
101 
102 ModuleResource::ModuleResource()
103  : d(new ModuleResourcePrivate(nullptr))
104 {
105 }
106 
108  : d(resource.d)
109 {
110  d->ref.Ref();
111 }
112 
113 ModuleResource::ModuleResource(const std::string& file, const ModuleResourceContainer& resourceContainer)
114  : d(new ModuleResourcePrivate(&resourceContainer))
115 {
116  d->InitFilePath(file);
117 
118  d->stat.filePath = d->resourceContainer->GetModuleInfo()->name + d->path + d->fileName;
119 
120  d->resourceContainer->GetStat(d->stat);
121 }
122 
123 ModuleResource::ModuleResource(int index, const ModuleResourceContainer& resourceContainer)
124  : d(new ModuleResourcePrivate(&resourceContainer))
125 {
126  d->resourceContainer->GetStat(index, d->stat);
127  d->InitFilePath(d->stat.filePath.substr(d->resourceContainer->GetModuleInfo()->name.size()));
128 }
129 
131 {
132  if (!d->ref.Deref())
133  delete d;
134 }
135 
137 {
138  ModuleResourcePrivate* curr_d = d;
139  d = resource.d;
140  d->ref.Ref();
141 
142  if (!curr_d->ref.Deref())
143  delete curr_d;
144 
145  return *this;
146 }
147 
148 bool ModuleResource::operator <(const ModuleResource& resource) const
149 {
150  return this->GetResourcePath() < resource.GetResourcePath();
151 }
152 
153 bool ModuleResource::operator ==(const ModuleResource& resource) const
154 {
155  return d->resourceContainer == resource.d->resourceContainer &&
156  this->GetResourcePath() == resource.GetResourcePath();
157 }
158 
159 bool ModuleResource::operator !=(const ModuleResource &resource) const
160 {
161  return !(*this == resource);
162 }
163 
165 {
166  return d->resourceContainer && d->resourceContainer->IsValid() && d->stat.index > -1;
167 }
168 
169 ModuleResource::operator bool_type() const
170 {
171  return IsValid() ? &ModuleResource::d : nullptr;
172 }
173 
174 std::string ModuleResource::GetName() const
175 {
176  return d->fileName;
177 }
178 
179 std::string ModuleResource::GetPath() const
180 {
181  return d->path;
182 }
183 
185 {
186  return d->path + d->fileName;
187 }
188 
189 std::string ModuleResource::GetBaseName() const
190 {
191  return d->fileName.substr(0, d->fileName.find_first_of('.'));
192 }
193 
195 {
196  return d->fileName.substr(0, d->fileName.find_last_of('.'));
197 }
198 
199 std::string ModuleResource::GetSuffix() const
200 {
201  std::size_t index = d->fileName.find_last_of('.');
202  return index < d->fileName.size()-1 ? d->fileName.substr(index+1) : std::string("");
203 }
204 
206 {
207  std::size_t index = d->fileName.find_first_of('.');
208  return index < d->fileName.size()-1 ? d->fileName.substr(index+1) : std::string("");
209 }
210 
212 {
213  return d->stat.isDir;
214 }
215 
217 {
218  return !d->stat.isDir;
219 }
220 
221 std::vector<std::string> ModuleResource::GetChildren() const
222 {
223  if (!IsValid() || !IsDir()) return d->children;
224 
225  if (d->children.empty())
226  {
227  d->resourceContainer->GetChildren(d->stat.filePath, true,
228  d->children, d->childNodes);
229  }
230  return d->children;
231 }
232 
233 std::vector<ModuleResource> ModuleResource::GetChildResources() const
234 {
235  std::vector<ModuleResource> childResources;
236 
237  if (!IsValid() || !IsDir()) return childResources;
238 
239  if (d->childNodes.empty())
240  {
241  d->resourceContainer->GetChildren(this->GetResourcePath(), true,
242  d->children, d->childNodes);
243  }
244 
245  for (std::vector<uint32_t>::const_iterator iter = d->childNodes.begin(),
246  iterEnd = d->childNodes.end(); iter != iterEnd; ++iter)
247  {
248  childResources.push_back(ModuleResource(static_cast<int>(*iter), *d->resourceContainer));
249  }
250  return childResources;
251 }
252 
254 {
255  return d->stat.uncompressedSize;
256 }
257 
259 {
260  return d->stat.modifiedTime;
261 }
262 
263 std::size_t ModuleResource::Hash() const
264 {
265  using namespace US_HASH_FUNCTION_NAMESPACE;
266  return US_HASH_FUNCTION(std::string, d->resourceContainer->GetModuleInfo()->name + this->GetResourcePath());
267 }
268 
269 void* ModuleResource::GetData() const
270 {
271  if (!IsValid()) return nullptr;
272 
273  void* data = d->resourceContainer->GetData(d->stat.index);
274  if (data == nullptr)
275  {
276  US_WARN << "Error uncompressing resource data for " << this->GetResourcePath() << " from "
277  << d->resourceContainer->GetModuleInfo()->location;
278  }
279  return data;
280 }
281 
282 US_END_NAMESPACE
283 
284 US_USE_NAMESPACE
285 
286 std::ostream& operator<<(std::ostream& os, const ModuleResource& resource)
287 {
288  return os << resource.GetResourcePath();
289 }
std::string GetCompleteBaseName() const
ModuleResource & operator=(const ModuleResource &resource)
std::vector< std::string > GetChildren() const
time_t GetLastModified() const
std::string GetCompleteSuffix() const
bool operator!=(const ModuleResource &resource) const
std::string GetBaseName() const
bool operator==(const ModuleResource &resource) const
std::vector< ModuleResource > GetChildResources() const
US_Core_EXPORT std::ostream & operator<<(std::ostream &os, ModuleEvent::Type eventType)
std::string GetSuffix() const
friend class ModuleResourceContainer
std::string GetPath() const
std::string GetResourcePath() const
bool operator<(const ModuleResource &resource) const
US_MSVC_POP_WARNING US_HASH_FUNCTION_NAMESPACE_BEGIN return US_HASH_FUNCTION(us::ServiceRegistrationBasePrivate *, arg.d)
std::string GetName() const