Jim
Jim

Reputation: 11379

Mock File methods in .NET (like File.Copy("1.txt", "2.txt"))

We have some methods that call File.Copy, File.Delete, File.Exists, etc. How can we test these methods without actually hitting the file system?

I consider myself a unit testing n00b, so any advice is appreciated.

Upvotes: 15

Views: 7552

Answers (6)

Steve Guidi
Steve Guidi

Reputation: 20200

I maintain the Jolt.NET project on CodePlex, which contains a library to generate such interfaces and their implementations for you. Please refer to the Jolt.Testing library for more information.

Upvotes: 0

Jamie Penney
Jamie Penney

Reputation: 9522

I tend to create an interface in most of my projects called IFileController that has all file operations on it. This can have the basic ones, plus any methods that the .NET framework doesn't provide that deal with files.

Using a dependency injection framework, you can get an instance of IFileController without knowing exactly what type it is, and use it without needing to mess around with mocking framework types. This makes everything much more testable, and as a bonus you can change the file storage mechanism without changing your code at all.

On the down side, any new developers need to be told about this interface, otherwise they will just use the .NET methods directly.

Upvotes: 0

yfeldblum
yfeldblum

Reputation: 65435

public interface IFile {
    void Copy(string source, string dest);
    void Delete(string fn);
    bool Exists(string fn);
}

public class FileImpl : IFile {
    public virtual void Copy(string source, string dest) { File.Copy(source, dest); }
    public virtual void Delete(string fn) { File.Delete(fn); }
    public virtual bool Exists(string fn) { return File.Exists(fn); }
}

[Test]
public void TestMySystemCalls() {
    var filesystem = new Moq.Mock<IFile>();
    var obj = new ClassUnderTest(filesystem);
    filesystem.Expect(fs => fs.Exists("MyFile.txt")).Return(true);
    obj.CheckIfFileExists(); // doesn't hit the underlying filesystem!!!
}

Upvotes: 24

bovium
bovium

Reputation: 2937

You can use a mock framework for this and it will create a fake copy of the File object and you can inject the file in the system under test.

I will recommend Rhino Mock.

Upvotes: 0

cfeduke
cfeduke

Reputation: 23226

I would use Moq for this. You would have to create an interface and a class that proxies to the real thing so you could have Moq create an instance of your proxy (a mocked instance) but its the best way to test these sorts of things.

Upvotes: 2

Jon Skeet
Jon Skeet

Reputation: 1499800

If you absolutely have to do this, Typemock Isolator is your friend.

I can't say I've used it myself, and I would try to design my way around it instead, but it'll do the job as far as I'm aware.

Upvotes: 3

Related Questions