tmp
This commit is contained in:
parent
8e150b52c3
commit
5fd14ea4dd
8 changed files with 88 additions and 120 deletions
|
|
@ -8,19 +8,15 @@ class Directory : public Node {
|
|||
public:
|
||||
Directory();
|
||||
Directory(const Directory& node);
|
||||
|
||||
~Directory() override;
|
||||
|
||||
NodeType getType() const override { return DIRECTORY; }
|
||||
[[nodiscard]] std::shared_ptr<Node> clone() const override;
|
||||
|
||||
bool detachNode(const Key& key) override;
|
||||
bool attachNode(const Key &newKey, std::shared_ptr<Node> newNode) override;
|
||||
|
||||
std::shared_ptr<Node> findNode(const std::vector<Key>& path, ui32 currentDepth = 0) override;
|
||||
std::shared_ptr<Node> findNode(const Key& path) override;
|
||||
|
||||
[[nodiscard]] ui64 size() const override;
|
||||
|
||||
bool isDirectory() const override { return true; }
|
||||
|
||||
private:
|
||||
|
|
|
|||
|
|
@ -7,26 +7,13 @@
|
|||
|
||||
// restore path unwindingk
|
||||
// RESTORE LINKS
|
||||
// COPY operator update link targets
|
||||
// Improve error logs
|
||||
// use smart pointers
|
||||
// COPY operator update link targets on copied nodes
|
||||
|
||||
// in-tree node links will report false to those operations and hard nodes deletion
|
||||
// use in node 'is_delete' flag and travers all nodes with link checks
|
||||
// remove mParent mTreeNode links
|
||||
|
||||
// Functionality:
|
||||
// deleting directory - mark all nodes as deleted
|
||||
// traverse and check for links
|
||||
// unlink if those links are outgoing
|
||||
|
||||
// Refactor
|
||||
// - remove code duplication
|
||||
// - Move DirectoryKey inside Node (no need to store pointers from Node to DirectoryTree::Node)
|
||||
// - Merge DirectoryTree::Node and Node (no pointer overhead, requires tree nodes to be consistent, check insertNodeInstead)
|
||||
// - introduce smart pointers
|
||||
// - reconsider switch statements
|
||||
|
||||
|
||||
class FileSystem {
|
||||
public:
|
||||
|
|
|
|||
|
|
@ -8,8 +8,8 @@ public:
|
|||
Link(const Link& node);
|
||||
~Link() override;
|
||||
|
||||
NodeType getType() const override { return LINK; }
|
||||
[[nodiscard]] std::shared_ptr<Node> clone() const override;
|
||||
|
||||
[[nodiscard]] std::shared_ptr<Node> getLink() const;
|
||||
[[nodiscard]] bool isHard() const;
|
||||
|
||||
|
|
@ -17,9 +17,7 @@ public:
|
|||
|
||||
// link on link is not allowed, so no inf looping here
|
||||
std::shared_ptr<Node> findNode(const std::vector<Key>& path, ui32 currentDepth) override;
|
||||
|
||||
void dumpUtil(std::stringstream& ss, const Key& key, ui32 currentDepth, std::vector<bool>& indents) override;
|
||||
|
||||
bool isLink() const override { return true; }
|
||||
|
||||
private:
|
||||
|
|
|
|||
18
inc/Node.hpp
18
inc/Node.hpp
|
|
@ -14,42 +14,32 @@ typedef long i32;
|
|||
|
||||
class Link;
|
||||
|
||||
extern std::string gError;
|
||||
typedef std::string Key;
|
||||
|
||||
class Node {
|
||||
public:
|
||||
enum NodeType { FILE, LINK, DIRECTORY };
|
||||
|
||||
public:
|
||||
Node() = default;
|
||||
Node(const Node& node);
|
||||
virtual ~Node();
|
||||
|
||||
virtual NodeType getType() const { return FILE; }
|
||||
[[nodiscard]] virtual std::shared_ptr<Node> clone() const;
|
||||
|
||||
virtual bool detachNode(const Key& key) { return false; }
|
||||
virtual bool attachNode(const Key &newKey, std::shared_ptr<Node> newNode) { return false; }
|
||||
|
||||
virtual void getMaxDepthUtil(ui32 depth, ui32& maxDepth) const {}
|
||||
|
||||
virtual void dumpUtil(std::stringstream& ss, const Key& key, ui32 currentDepth, std::vector<bool>& indents);
|
||||
|
||||
ui32 getMaxDepth() const;
|
||||
|
||||
void dump(std::stringstream& ss);
|
||||
|
||||
void getNodeStraightPath(const std::shared_ptr<Node>& node, std::vector<std::shared_ptr<Node>>& path) const;
|
||||
|
||||
virtual ui64 size() const { return 0; }
|
||||
|
||||
virtual std::shared_ptr<Node> getTarget();
|
||||
|
||||
virtual std::shared_ptr<Node> findNode(const std::vector<Key>& path, ui32 currentDepth = 0);
|
||||
|
||||
virtual std::shared_ptr<Node> findNode(const Key& path) { return nullptr; }
|
||||
|
||||
bool empty() const { return !size(); }
|
||||
|
||||
static void indent(std::stringstream & ss, ui32 depth, std::vector<bool>& indents);
|
||||
|
||||
virtual bool isDirectory() const { return false; }
|
||||
virtual bool isLink() const { return false; }
|
||||
virtual bool isHard() const { return false; }
|
||||
|
|
|
|||
|
|
@ -2,34 +2,20 @@
|
|||
#include "Directory.hpp"
|
||||
|
||||
#include <sstream>
|
||||
#include <cassert>
|
||||
#include <algorithm>
|
||||
|
||||
Directory::Directory() {
|
||||
}
|
||||
Directory::Directory() = default;
|
||||
|
||||
Directory::~Directory() = default;
|
||||
|
||||
bool Directory::attachNode(const Key &newKey, std::shared_ptr<Node> newNode) {
|
||||
auto iterNode = mMembers.find(newKey);
|
||||
|
||||
if (iterNode != mMembers.end()) {
|
||||
auto existingNode = iterNode->second;
|
||||
if (!(false && newNode->empty() && existingNode->empty())) {
|
||||
gError = "Such node already exists";
|
||||
return false;
|
||||
}
|
||||
return false; // exit silently
|
||||
}
|
||||
|
||||
assert(mMembers.find(newKey) == mMembers.end());
|
||||
mMembers.insert({ newKey, newNode });
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Directory::detachNode(const Key& key) {
|
||||
auto removeNode = mMembers.find(key);
|
||||
if (removeNode == mMembers.end()) {
|
||||
gError = "Invalid path";
|
||||
return false;
|
||||
}
|
||||
assert(mMembers.find(key) != mMembers.end());
|
||||
|
||||
//if (removeNode->key.incomingLinksHard || removeNode->key.incomingLinksDynamic) {
|
||||
// gError = "Cannot modify node with incoming hard links";
|
||||
|
|
@ -99,11 +85,6 @@ Directory::Directory(const Directory &node) : Node(node) {
|
|||
}
|
||||
}
|
||||
|
||||
Directory::~Directory() {
|
||||
for (const auto& node : mMembers) {
|
||||
// delete node.second;
|
||||
}
|
||||
}
|
||||
|
||||
std::shared_ptr<Node> Directory::clone() const {
|
||||
auto out = std::make_shared<Directory>(*this);
|
||||
|
|
|
|||
|
|
@ -8,6 +8,8 @@
|
|||
#include <cassert>
|
||||
#include <algorithm>
|
||||
|
||||
static std::string gError;
|
||||
|
||||
FileSystem::FileSystem() {
|
||||
root = std::make_shared<Directory>();
|
||||
currentDirectory = root;
|
||||
|
|
@ -65,14 +67,19 @@ bool FileSystem::makeDirectory(const Path& path) {
|
|||
return false;
|
||||
}
|
||||
|
||||
auto directory = std::make_shared<Directory>();
|
||||
|
||||
if (!parentNode->attachNode(path.getFilename(), directory)) {
|
||||
gError = "File or link with such name already exists";
|
||||
return false;
|
||||
auto existingNode = parentNode->findNode(path.getFilename());
|
||||
if (existingNode) {
|
||||
if (!(existingNode->getType() == Node::DIRECTORY && existingNode->empty())) {
|
||||
gError = "File or link with such name already exists";
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
auto directory = std::make_shared<Directory>();
|
||||
directory->mParent = parentNode;
|
||||
|
||||
assert(parentNode->attachNode(path.getFilename(), directory));
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
@ -89,13 +96,63 @@ bool FileSystem::makeFile(const Path& path) {
|
|||
return false;
|
||||
}
|
||||
|
||||
auto existingNode = parentNode->findNode(path.getFilename());
|
||||
if (existingNode) {
|
||||
if (!(existingNode->getType() == Node::FILE && existingNode->empty())) {
|
||||
gError = "Directory with such name already exists";
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
auto newFile = std::make_shared<Node>();
|
||||
if (!parentNode->attachNode(path.getFilename(), newFile)) {
|
||||
gError = "Directory with such name already exists";
|
||||
newFile->mParent = parentNode;
|
||||
|
||||
assert(parentNode->attachNode(path.getFilename(), newFile));
|
||||
return true;
|
||||
}
|
||||
|
||||
bool FileSystem::makeLink(const Path& source, const Path& target, bool isDynamic) {
|
||||
if (source.getDepth() < 1 || source.isInvalid()) {
|
||||
gError = "Invalid source path";
|
||||
return false;
|
||||
}
|
||||
|
||||
newFile->mParent = parentNode;
|
||||
auto parentNodeSource = getNode(source, true);
|
||||
if (!parentNodeSource) {
|
||||
gError = "Invalid source path";
|
||||
return false;
|
||||
}
|
||||
|
||||
auto parentNodeTarget = getNode(target, false);
|
||||
if (!parentNodeTarget) {
|
||||
gError = "Invalid target path";
|
||||
return false;
|
||||
}
|
||||
|
||||
auto sourceNode = parentNodeSource->findNode(source.getFilename());
|
||||
if (!sourceNode) {
|
||||
gError = "Invalid source path";
|
||||
return false;
|
||||
}
|
||||
|
||||
if (sourceNode->isLink()) {
|
||||
gError = "Link on link is not allowed";
|
||||
return false;
|
||||
}
|
||||
|
||||
const Key& key = source.getFilename();
|
||||
|
||||
if (parentNodeTarget->findNode(key)) {
|
||||
gError = "Node with such name already exists";
|
||||
return false;
|
||||
}
|
||||
|
||||
auto newLink = std::shared_ptr<Node>(new Link(sourceNode, !isDynamic));
|
||||
newLink->mParent = parentNodeTarget;
|
||||
|
||||
assert(parentNodeTarget->attachNode(key, newLink));
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
@ -210,8 +267,9 @@ bool FileSystem::copyNode(const Path& source, const Path& target) {
|
|||
}
|
||||
|
||||
auto clonedNode = sourceNode->clone();
|
||||
assert(parentNodeTarget->attachNode(key, clonedNode));
|
||||
clonedNode->mParent = parentNodeTarget;
|
||||
assert(parentNodeTarget->attachNode(key, clonedNode));
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
@ -241,59 +299,20 @@ bool FileSystem::moveNode(const Path &source, const Path &target) {
|
|||
|
||||
const Key& key = source.getFilename();
|
||||
|
||||
if (parentNodeTarget->findNode(key)) {
|
||||
gError = "Node with such name already exists in the target directory";
|
||||
return false;
|
||||
}
|
||||
|
||||
if (sourceNode->isHard()) {
|
||||
gError = "Node contains incoming hard links";
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!parentNodeTarget->attachNode(key, sourceNode)) {
|
||||
gError = "Node with such name already exists";
|
||||
return false;
|
||||
}
|
||||
assert(parentNodeTarget->attachNode(key, sourceNode));
|
||||
assert(parentNodeSource->detachNode(key));
|
||||
|
||||
sourceNode->mParent = parentNodeTarget;
|
||||
assert(parentNodeSource->detachNode(key));
|
||||
return true;
|
||||
}
|
||||
|
||||
bool FileSystem::makeLink(const Path& source, const Path& target, bool isDynamic) {
|
||||
if (source.getDepth() < 1 || source.isInvalid()) {
|
||||
gError = "Invalid source path";
|
||||
return false;
|
||||
}
|
||||
|
||||
auto parentNodeSource = getNode(source, true);
|
||||
if (!parentNodeSource) {
|
||||
gError = "Invalid source path";
|
||||
return false;
|
||||
}
|
||||
|
||||
auto parentNodeTarget = getNode(target, false);
|
||||
if (!parentNodeTarget) {
|
||||
gError = "Invalid target path";
|
||||
return false;
|
||||
}
|
||||
|
||||
auto sourceNode = parentNodeSource->findNode(source.getFilename());
|
||||
if (!sourceNode) {
|
||||
gError = "Invalid source path";
|
||||
return false;
|
||||
}
|
||||
|
||||
if (sourceNode->isLink()) {
|
||||
gError = "Link on link is not allowed";
|
||||
return false;
|
||||
}
|
||||
|
||||
const Key& key = source.getFilename();
|
||||
|
||||
auto newLink = std::shared_ptr<Node>(new Link(sourceNode, !isDynamic));
|
||||
if (!parentNodeTarget->attachNode(key, newLink)) {
|
||||
gError = "Node with such name already exists";
|
||||
return false;
|
||||
}
|
||||
|
||||
newLink->mParent = parentNodeTarget;
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -92,7 +92,7 @@ Interpreter::Interpreter() {
|
|||
}
|
||||
|
||||
void Interpreter::reportError(const std::string& description) {
|
||||
std::cout << "ERROR : " << description << "\n\n";
|
||||
std::cout << "ERROR: " << description << "\n\n";
|
||||
}
|
||||
|
||||
void Interpreter::printHelp() {
|
||||
|
|
|
|||
|
|
@ -6,9 +6,6 @@
|
|||
#include <cassert>
|
||||
#include <algorithm>
|
||||
|
||||
std::string gError;
|
||||
bool gDebug = true;
|
||||
|
||||
Node::Node(const Node &node) {}
|
||||
|
||||
Node::~Node() {
|
||||
|
|
@ -54,7 +51,7 @@ void Node::dump(std::stringstream& ss) {
|
|||
void Node::dumpUtil(std::stringstream& ss, const Key& key, ui32 currentDepth, std::vector<bool>& indents) {
|
||||
indent(ss, currentDepth, indents);
|
||||
ss << key;
|
||||
if (gDebug) ss << " [file]";
|
||||
ss << " [file]";
|
||||
ss << "\n";
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue