Wittyshare  0.2
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Pages
WsFileSystemTree.cpp
Go to the documentation of this file.
1 
13 #include "WsFileSystemTree.h"
14 #include <Include/WsGlobalConfig.h>
16 
17 #include <sys/time.h>
18 
19 #include<boost/tokenizer.hpp>
20 #include <boost/thread/thread.hpp>
21 using namespace boost;
22 using namespace std;
23 
24 WsFileSystemTree::WsFileSystemTree(const string& p, bool m):
26  m_rootPath(p),
27  m_monitor(m),
28  m_useCount(0)
29 {
30 }
31 
33 {
34  m_root.reset();
35  m_current.reset();
36  LOG(DEBUG) << "WsFileSystemTree::~WsFileSystemTree() : deleting ";
37 }
38 
40 {
41  /* Create unique stamp */
42  createStamp();
43  LOG(INFO) << "WsFileSystemTree::start() : Building FsTree for path " << m_p;
44  /* Start Crawling */
45  int r = WsDirectoryCrawler::start();
46  if (r == ErrorCode::Failure)
47  LOG(ERROR) << "WsFileSystemTree::start() : Error while building FsTree for path " << m_p;
48  else {
49  LOG(INFO) << "WsFileSystemTree::start() : FsTree built with success for path " << m_p;
50  }
51  return r;
52 }
53 
54 
55 int WsFileSystemTree::applyFile(const path& filePath)
56 {
57  /* Create node for current path */
58  NodePtr n(new WsFileNode(filePath, m_rootPath));
59  /* Create properties for current path */
60  NodePropertiesPtr props(new WsNodeProperties(n.get()->getFullPath(), WsNodeProperties::File));
61  n.get()->setProperties(props);
62  /* Get the last write time of file on disk and set it on the node */
63  std::time_t t = boost::filesystem::last_write_time( filePath ) ;
64  n.get()->setModifyDate(t);
65  n.get()->setSize(boost::filesystem::file_size(filePath));
66  //TODO ADD creation date support on ext4 only
67  //
68  /* if current is NULL, it means we are at the root */
69  if (m_current == 0)
70  m_current = n;
71  else {
72  /* It's not the root so we add the Node to the current node's children file */
73  m_current.get()->addChildFile(n);
74  }
75  if (m_root == 0)
76  m_root = m_current;
77  return ErrorCode::Success;
78 }
79 
80 const path& WsFileSystemTree::getRootPath() const
81 {
82  return m_rootPath;
83 }
84 
85 int WsFileSystemTree::applyDirectory(const path& dirPath)
86 {
87  /* If monitored by gamin is on, add it to the list of monitored files/folders */
88  if (m_monitor) {
89  m_monitorPaths.push_back(dirPath);
90  }
91  WsNodeResources* resources = new WsNodeResources(dirPath);
92  /* Create .config/{nodes, images, templates, ..} if not already here */
94  return ErrorCode::Failure;
95  /* Create a dir node */
96  NodePtr n(new WsDirNode(dirPath, m_rootPath));
97  std::time_t t = boost::filesystem::last_write_time( dirPath ) ;
98  n.get()->setModifyDate(t);
99  dynamic_cast<WsDirNode*>(n.get())->setResources(resources);
100  /* Parse Config of the node */
101  NodePropertiesPtr props(new WsNodeProperties(n.get()->getFullPath(), WsNodeProperties::Dir));
102  /* Create properties directories */
103  props.get()->createPropertiesDirectories();
104  n.get()->setProperties(props);
105  /* if current is NULL, it means we are at the root */
106  if (m_current == 0)
107  m_current = n;
108  else {
109  /* Add the node as a child of the current node */
110  m_current.get()->addChildDirectory(n);
111  m_current = n;
112  }
113  if (m_root == 0)
114  m_root = m_current;
115  return ErrorCode::Success;
116 }
117 
118 void WsFileSystemTree::beginChild(const path& p)
119 {
120  //We need to define it but we don't need to use it
121 }
122 
123 void WsFileSystemTree::endChild(const path& p)
124 {
125  /* after we handle a directory (and all its children) when traversing the tree,
126  we set current to its parent i.e. we go back up in the tree */
127  NodePtr parent = m_current.get()->getParent();
128  if (m_current.get() != 0 && parent.get() != 0 && is_directory(p)) {
129  m_current = parent;
130  }
131 }
132 
134 {
136  return m_root;
137  else {
138  LOG(ERROR) << "WsFileSystemTree::getRoot() : FileSystemTree not loaded" << endl;
139  return NodePtr();
140  }
141 }
142 
144 {
145  //This methods should be deleted and WsAbstractNode::eatPath() should be used instead
147  LOG(ERROR) << "WsFileSystemTree::eatPath() : FileSystemTree not loaded" << endl;
148  return NodePtr();
149  }
150  typedef tokenizer<char_separator<char> >
151  tokenizer;
152  char_separator<char> sep("/");
153  tokenizer tok(p, sep);
154  NodePtr curNode = m_root;
155  for (tokenizer::iterator beg = tok.begin(); beg != tok.end(); ++beg) {
156  NodePtr res = curNode.get()->getNodeByName(*beg);
157  if (res.get() == 0)
158  return res;
159  curNode = res;
160  }
161  return curNode;
162 }
163 
165 {
166  return m_useCount;
167 }
168 
170 {
171  path p = newNode.get()->getPath();
172  NodePtr parent = eatPath(p.parent_path().string());
173  if (parent.get() == 0)
174  return ErrorCode::Failure;
175  /* Parent is here, check if it's a DIR */
176  if ( !parent.get()->isDirectory() )
177  return ErrorCode::Failure;
178  if ( newNode.get()->isRegularFile()) {
179  if ( parent.get()->addChildFile(newNode) == ErrorCode::Failure)
180  return ErrorCode::Failure;
181  } else {
182  if ( parent.get()->addChildDirectory(newNode) == ErrorCode::Failure)
183  return ErrorCode::Failure;
184  }
185  if ( parent.get()->addChildNode(newNode) == ErrorCode::Failure)
186  return ErrorCode::Failure;
187  LOG(DEBUG) << "WsFileSystemTree::insertNode() : Node " << p.string() << " inserted in FileSystemTree";
188  /* Create new stamp */
189  createStamp();
190  return ErrorCode::Success;
191 }
192 
194 {
195  //Not used now because fsdaemon is not multihreaded
196  /*
197  {
198  boost::mutex::scoped_lock lock(m_lMutex);
199  LOG(DEBUG) << "WsFileSystemTree::incrementUseCount() : Incrementing use count of FsTree " << m_stamp << " to " << (m_useCount + 1);
200  if (m_useCount < 0)
201  LOG(ERROR) << "WsFileSystemTree :: FileSystemTree usage is negative!!" << endl;
202  else
203  m_useCount++;
204  }
205  */
206 }
207 
209 {
210  //Not used now because fsdaemon is not multihreaded
211  /*
212  {
213  boost::mutex::scoped_lock lock(m_lMutex);
214  LOG(DEBUG) << "WsFileSystemTree :: Decrementing use count of FsTree " << m_stamp << " to " << (m_useCount - 1);
215  if (m_useCount < 1)
216  LOG(ERROR) << "WsFileSystemTree :: FileSystemTree usage is negative!!" << endl;
217  else
218  m_useCount--;
219  }
220  */
221 }
222 
223 
225 {
226  return m_monitorPaths;
227 }
228 
230 {
231  return m_stamp;
232 }
233 
235 {
236  //Create a random stamp
237  timeval time;
238  gettimeofday(&time, 0);
239  long millis = (time.tv_sec * 1000) + (time.tv_usec / 1000);
240  m_stamp = boost::lexical_cast<string>(millis);
241 }
242 
const std::string & getStamp()
returns the Tree unique stamp
Abstract class used to crawl a directory.
boost::shared_ptr< WsAbstractNode > NodePtr
WsFileSystemTree(const std::string &p, bool m=false)
Constructor for the FileSystemTree object.
std::vector< boost::filesystem::path > m_monitorPaths
#define DEBUG
Definition: WsLogger.h:27
int start()
crawls the diretory and sorts the children. It is called by WsDirectoryCrawler::start() ...
NodePtr getRoot()
returns the root of the WsFileSystemTree
int start()
Start crawling over all the files and directories/subdirectories.
Reprensents a Directory on disk.
Definition: WsDirNode.h:25
const int Failure
Reprensents a File on disk.
Definition: WsFileNode.h:23
Properties of a WsNode.
NodePtr eatPath(const std::string &p)
void endChild(const boost::filesystem::path &p)
this method is called when finished browsing the subdir
const boost::filesystem::path & getRootPath() const
returns the boost::filesystem::path to the base directory where documents are stored ...
int getUseCount()
returns the number of users that are using this fileSystemTree version
int applyDirectory(const boost::filesystem::path &dirPath)
this method is called by browse when the boost::filesystem::path is a folder
#define LOG
Definition: WsLogger.h:22
void incrementUseCount()
increments the number of uses of the tree by 1
#define INFO
Definition: WsLogger.h:32
int applyFile(const boost::filesystem::path &filePath)
this method is called by browse when the boost::filesystem::path is a file
boost::filesystem::path m_rootPath
int createResourcesDirectories()
boost::shared_ptr< WsNodeProperties > NodePropertiesPtr
Structure representing all the fs tree from the root.
int insertNode(NodePtr newNode)
inserts the node in the tree The node is inserted on the right place on the tree depending on it's pa...
const int Success
Resources of a WsNode.
std::vector< boost::filesystem::path > & getMonitorPaths()
returns the std::vector containing the boost::filesystem::path that should be monitored by the WsUpda...
#define ERROR
Definition: WsLogger.h:42
void decrementUseCount()
decrements the numbers of uses by one
void createStamp()
creates unique stamp for the tree
void beginChild(const boost::filesystem::path &p)
this method is called before browsing a subdirectory