using System; using System.IO; namespace pkNX.Containers.VFS; public readonly record struct VirtualFile(IFileSystem FileSystem, FileSystemPath Path) : IFileSystemEntity { public string Name => Path.EntityName; public VirtualDirectory ParentDirectory => VirtualDirectory.Create(FileSystem, Path.ParentPath); public (string, string) GetFileNameAndExtension() { int lastPeriod = Name.LastIndexOf('.'); return (Name[..lastPeriod], Name[(lastPeriod + 1)..]); } public string GetFileNameWithoutExtension() { int lastPeriod = Name.LastIndexOf('.'); return Name[..lastPeriod]; } public string GetExtension() { int lastPeriod = Name.LastIndexOf('.'); return Name[(lastPeriod + 1)..]; } public Stream Open(FileMode mode = FileMode.Open, FileAccess access = FileAccess.Read) { return FileSystem.OpenFile(Path, mode, access); } public Stream OpenRead() { return FileSystem.OpenFile(Path, FileMode.Open, FileAccess.Read); } public Stream OpenWrite() { return FileSystem.OpenWrite(Path); } public void CopyTo(VirtualDirectory destination) { FileSystem.Copy(Path, destination.FileSystem, destination.Path.AppendFile(Name)); } public void MoveTo(VirtualDirectory destination) { FileSystem.Move(Path, destination.FileSystem, destination.Path.AppendFile(Name)); } public void Delete(DeleteMode mode = DeleteMode.TopMostLayer) { FileSystem.Delete(Path, mode); } public ReadOnlySpan ReadAllBytes() { using var stream = Open(); using var memoryStream = new MemoryStream(); stream.CopyTo(memoryStream); return memoryStream.ToArray(); } public void ReadAllBytes(Span bytes) { using var stream = Open(); int bytesRead = stream.Read(bytes); if (bytesRead != bytes.Length) throw new IOException("Could not read all bytes."); } public string ReadAllText() { using var stream = Open(); using var reader = new StreamReader(stream); return reader.ReadToEnd(); } public void WriteAllBytes(ReadOnlySpan bytes) { using var stream = OpenWrite(); stream.Write(bytes); } public void WriteAllBytes(IBinarySerializable source) { using var stream = OpenWrite(); using var bw = new BinaryWriter(stream); source.Write(bw); } public void WriteAllText(string text) { using var stream = OpenWrite(); using var writer = new StreamWriter(stream); writer.Write(text); } internal static VirtualFile Create(IFileSystem fileSystem, FileSystemPath path) { if (!path.IsFile) throw new ArgumentException("The specified path is not a file.", nameof(path)); return new VirtualFile(fileSystem, path); } }