diff --git a/src/Ramstack.FileSystem.Abstractions/VirtualFile.cs b/src/Ramstack.FileSystem.Abstractions/VirtualFile.cs
index 76d74b9..78ff4c6 100644
--- a/src/Ramstack.FileSystem.Abstractions/VirtualFile.cs
+++ b/src/Ramstack.FileSystem.Abstractions/VirtualFile.cs
@@ -143,7 +143,7 @@ public ValueTask CopyToAsync(string destinationPath, bool overwrite, Cancellatio
///
public ValueTask CopyToAsync(VirtualFile destination, bool overwrite, CancellationToken cancellationToken = default)
{
- EnsureWritable();
+ destination.EnsureWritable();
destination.Refresh();
if (destination.FileSystem != FileSystem)
diff --git a/tests/Ramstack.FileSystem.Specification.Tests/Ramstack.FileSystem.Specification.Tests.csproj b/tests/Ramstack.FileSystem.Specification.Tests/Ramstack.FileSystem.Specification.Tests.csproj
index ebdb578..7b4bc1f 100644
--- a/tests/Ramstack.FileSystem.Specification.Tests/Ramstack.FileSystem.Specification.Tests.csproj
+++ b/tests/Ramstack.FileSystem.Specification.Tests/Ramstack.FileSystem.Specification.Tests.csproj
@@ -45,6 +45,7 @@
+
diff --git a/tests/Ramstack.FileSystem.Specification.Tests/VirtualFileSystemSpecificationTests.cs b/tests/Ramstack.FileSystem.Specification.Tests/VirtualFileSystemSpecificationTests.cs
index 182ec64..62f2051 100644
--- a/tests/Ramstack.FileSystem.Specification.Tests/VirtualFileSystemSpecificationTests.cs
+++ b/tests/Ramstack.FileSystem.Specification.Tests/VirtualFileSystemSpecificationTests.cs
@@ -1,6 +1,8 @@
using System.Security.Cryptography;
using System.Text;
+using Ramstack.FileSystem.Physical;
+
namespace Ramstack.FileSystem.Specification.Tests;
///
@@ -353,6 +355,38 @@ await Assert.ThatAsync(
Throws.Exception);
}
+ [Test]
+ public async Task File_Readonly_ReadonlyToWritable_Succeeds()
+ {
+ using var fs = GetFileSystem();
+ using var ds = new PhysicalFileSystem(
+ Path.Combine(
+ Path.GetTempPath(),
+ Path.GetRandomFileName()));
+
+ if (!fs.IsReadOnly)
+ return;
+
+ var src = fs.GetFile("/project/README.md");
+ var dst = ds.GetFile("/README.md");
+
+ await src.CopyToAsync(dst);
+
+ Assert.That(
+ await dst.ExistsAsync(),
+ Is.True);
+
+ Assert.That(
+ await ds.FileExistsAsync("/README.md"),
+ Is.True);
+
+ Assert.That(
+ await src.ReadAllTextAsync(),
+ Is.EqualTo(await src.ReadAllTextAsync()));
+
+ Directory.Delete(ds.Root, true);
+ }
+
[Test]
public async Task File_CopyTo_Path()
{