Create logic structure with files
There is no way to get the items contained in a Directory once they have been added.



Your base class defines:

public abstract Directory AddDirectory(string name);
public abstract void AddFile(string name, IFileBuilder fileBuilder);
public abstract void Remove(FileSystemItem item);


These methods only make sense for a Directory. The fact that one of your two subclasses has to throw an InvalidOperationException for each of these abstract methods is an indication that they should not be part of the base class. Even worse, someone who has a reference to a FileSystemItem has no way of knowing if calling one of these methods is safe without explicitly checking the actual type of the instance.

Note: Iterating over the contents of a directory (mentioned above) is another operation that only makes sense for a Directory. It would be best to let FileSystemItem define the core properties, but not try to force the aspects that don't work for all of the subclasses.

This will likely mean you will need to keep a directories contents in two separate collections. You can still expose a function that allows iterating over all of the items, but someone using that call would not have access the Directory specific methods.



FileSystemItem defines _rootPath as a member variable, but it is not used.



I prefer to have member variables at the top of the class. This way, someone reading the class for the first time, will know what variables are available to methods before seeing a method trying to use one.

I prefer to always use curly brackets for if statements and loops. It makes things less error prone when you have to edit the code later.