Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[API Proposal]: Introduce RandomAccess.SetLength(SafeFileHandle handle) method #58376

Closed
Tracked by #64596
adamsitnik opened this issue Aug 30, 2021 · 4 comments · Fixed by #63992
Closed
Tracked by #64596

[API Proposal]: Introduce RandomAccess.SetLength(SafeFileHandle handle) method #58376

adamsitnik opened this issue Aug 30, 2021 · 4 comments · Fixed by #63992
Assignees
Labels
api-approved API was approved in API review, it can be implemented area-System.IO
Milestone

Comments

@adamsitnik
Copy link
Member

Background and motivation

Recently, we have introduced new RandomAccess type (#24847) which exposes some convenient methods for File IO. One of them is RandomAccess.GetLength(SafeFileHandle) that allows for reading file length.

When it comes to setting file length, users can:

  • use FileMode.Truncate to truncate given file when opening it.
  • specify preallocationSize to set initial size when opening the file.

The problem is that by using the new APIs, they can't set file length after the file has been opened.

FileStream exposes SetLength method, so should RandomAccess.

API Proposal

namespace System.IO
{
    public static class RandomAccess
    {
        public static void SetLength(SafeFileHandle handle, long length);
    }
}

API Usage

void WriteToFile(string path, string contents, Encoding encoding)
{
    long estimatedFileSize = encoding.GetMaxByteCount(contents.Length); // estimated file length
    using SafeFileHandle fileHandle = OpenHandle(path, FileMode.Create, FileAccess.Write, preallocationSize: estimatedFileSize);

    byte[] bytes = encoding.GetBytes(contents);
    RandomAccess.Write(fileHandle, bytes, fileOffset: 0);

    if (bytes.Length < estimatedFileSize) // shrink the size if initial estimation was wrong
    {
        RandomAccess.SetLength(fileHandle, bytes.Length);
    }
}

Risks

I can't see any.

@adamsitnik adamsitnik added this to the 7.0.0 milestone Aug 30, 2021
@adamsitnik adamsitnik self-assigned this Aug 30, 2021
@dotnet-issue-labeler dotnet-issue-labeler bot added the untriaged New issue has not been triaged by the area owner label Aug 30, 2021
@ghost
Copy link

ghost commented Aug 30, 2021

Tagging subscribers to this area: @dotnet/area-system-io
See info in area-owners.md if you want to be subscribed.

Issue Details

Background and motivation

Recently, we have introduced new RandomAccess type (#24847) which exposes some convenient methods for File IO. One of them is RandomAccess.GetLength(SafeFileHandle) that allows for reading file length.

When it comes to setting file length, users can:

  • use FileMode.Truncate to truncate given file when opening it.
  • specify preallocationSize to set initial size when opening the file.

The problem is that by using the new APIs, they can't set file length after the file has been opened.

FileStream exposes SetLength method, so should RandomAccess.

API Proposal

namespace System.IO
{
    public static class RandomAccess
    {
        public static void SetLength(SafeFileHandle handle, long length);
    }
}

API Usage

void WriteToFile(string path, string contents, Encoding encoding)
{
    long estimatedFileSize = encoding.GetMaxByteCount(contents.Length); // estimated file length
    using SafeFileHandle fileHandle = OpenHandle(path, FileMode.Create, FileAccess.Write, preallocationSize: estimatedFileSize);

    byte[] bytes = encoding.GetBytes(contents);
    RandomAccess.Write(fileHandle, bytes, fileOffset: 0);

    if (bytes.Length < estimatedFileSize) // shrink the size if initial estimation was wrong
    {
        RandomAccess.SetLength(fileHandle, bytes.Length);
    }
}

Risks

I can't see any.

Author: adamsitnik
Assignees: adamsitnik
Labels:

area-System.IO

Milestone: 7.0.0

@adamsitnik adamsitnik removed the untriaged New issue has not been triaged by the area owner label Aug 30, 2021
@Thealexbarney
Copy link

Oh, I didn't realize this API was missing from RandomAccess until it was too late. I'd just assumed it would be included in a lower-level file operations API set.

What's the best way to work around this in .NET 6 if one always needs to have the possibility of setting the file length available? Open a FileStream, get its SafeFileHandle, use that for reads/writes and call FileStream.SetLength() to set the file length?

@adamsitnik
Copy link
Member Author

Open a FileStream, get its SafeFileHandle, use that for reads/writes and call FileStream.SetLength() to set the file length?

Yes. The alternative it to specify the exact size as preallocationSize when opening file

@adamsitnik adamsitnik added api-suggestion Early API idea and discussion, it is NOT ready for implementation api-ready-for-review API is ready for review, it is NOT ready for implementation labels Jan 13, 2022
@bartonjs
Copy link
Member

bartonjs commented Jan 18, 2022

Video

Looks good as proposed

namespace System.IO
{
    public partial static class RandomAccess
    {
        public static void SetLength(SafeFileHandle handle, long length);
    }
}

@bartonjs bartonjs added api-approved API was approved in API review, it can be implemented and removed api-suggestion Early API idea and discussion, it is NOT ready for implementation api-ready-for-review API is ready for review, it is NOT ready for implementation labels Jan 18, 2022
@ghost ghost added the in-pr There is an active PR which will close this issue when it is merged label Jan 19, 2022
@ghost ghost removed the in-pr There is an active PR which will close this issue when it is merged label Jan 21, 2022
@ghost ghost locked as resolved and limited conversation to collaborators Feb 20, 2022
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
api-approved API was approved in API review, it can be implemented area-System.IO
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants