Skip to content
This repository has been archived by the owner on Jan 23, 2023. It is now read-only.

Add async document/element loading for XLinq. #110

Closed
wants to merge 14 commits into from
Closed

Add async document/element loading for XLinq. #110

wants to merge 14 commits into from

Conversation

scalablecory
Copy link

Adds XElement.LoadAsync and XDocument.LoadAsync. Code from the sync versions has been largely lifted out so they can share an implementation as much as possible.

@roel666
Copy link

roel666 commented Nov 17, 2014

Love it

@davkean
Copy link
Member

davkean commented Nov 18, 2014

First of all, I want to say thank-you for your contribution. This looks like a lot of great work and is the first contribution that we've had with API additions!

At the moment, we're right in the middle of bringing our API review process out in the open - and we're not immediately ready to take on this change. Over the next couple of weeks we'll work with you and use this PR as the guinea pig of the process.

In the meantime, we'll provide some feedback on the pull request itself.

@scalablecory
Copy link
Author

Sounds great, lets figure out this process. I'll do my best to address feedback.

@krwq
Copy link
Member

krwq commented Nov 18, 2014

I really like the idea of these new async APIs. I'll do my best to push it :) Good job!

…ith sync methods. This is needed due to them creating XmlReaderSettings using undocumented functionality based on the given LoadOptions.
@scalablecory
Copy link
Author

Verification is admittedly difficult without a test harness for the project.

I (minimally) checked myself by using the monster JMDict file, loading/saving both in 4.5.2 and with the new sync/async variants to verify the output was identical.

@davkean davkean added the api-needs-work API needs work before it is approved, it is NOT ready for implementation label Dec 3, 2014
@scalablecory
Copy link
Author

Has anyone had a chance to look at this yet?

@davkean
Copy link
Member

davkean commented Dec 6, 2014

Apologies, we haven't forgotten about this. There's two things that we're working on that are preventing us from taking this right at this moment:

  1. API review process. @terrajobst has written a proposal and will be publishing over the next week or so. We'll be taking you through you that soon.

  2. Branching. We're trying to figure out our branching structure at the moment. Currently we have only a single branch that represents what we're shipping for the next update of .NET Core. Clearly this isn't scalable for the product, and we're going to creating branches for future work so PR's that have API changes and destablizing changes get a little more bake time. @joshfree is looking into that.

@davkean
Copy link
Member

davkean commented Dec 19, 2014

Thanks for your continued patience, @terrajobst has just posted our API Review process proposal, feel free to comment over here: https://github.com/dotnet/corefx/issues/294.

/// significant whitespace will be preserved.
/// </returns>
[SuppressMessage("Microsoft.Design", "CA1054:UriParametersShouldNotBeStrings", Justification = "Back-compat with System.Xml.")]
public static async Task<XElement> Load(string uri, LoadOptions options, CancellationToken token)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why isn't this named LoadAsync?

@justinvp
Copy link
Contributor

The proposed LoadAsync methods in this PR take a CancellationToken as the last parameter. Should an overload be included that doesn't take CancellationToken?

For example:

public static Task<XDocument> LoadAsync(string uri, LoadOptions options)
{
    return LoadAsync(uri, options, CancellationToken.None);
}

public static async Task<XDocument> LoadAsync(string uri, LoadOptions options, CancellationToken token)
{
    ...
}

@justinvp
Copy link
Contributor

Also, most existing methods in the Framework that take a CancellationToken parameter name the parameter cancellationToken, not token. I personally don't have a strong opinion about this either way, but it might be best to be consistent with how it's predominantly named elsewhere.

@scalablecory
Copy link
Author

re: "token" vs "cancellationToken", you're right, and I'd rather maintain consistency with existing conventions. I'll change that.

re: overloads that don't support cancellation, I didn't include them simply because I never use them (why implement an async API if you won't support cancellation?) and didn't think about it. I can add if wanted.

@justinvp
Copy link
Contributor

I didn't include them simply because I never use them (why implement an async API if you won't support cancellation?) and didn't think about it. I can add if wanted.

I'll let the official API reviewers weigh in, but this is mentioned in the Task-based Asynchronous Pattern (TAP) design guidelines:

In TAP, cancellation is optional for both asynchronous method implementers and asynchronous method consumers. If an operation allows cancellation, it exposes an overload of the asynchronous method that accepts a cancellation token (CancellationToken instance). By convention, the parameter is named cancellationToken.

ContentReader cr = new ContentReader(this);
while (!token.IsCancellationRequested && cr.ReadContentFrom(this, r, o) && await r.ReadAsync().ConfigureAwait(false)) ;

token.ThrowIfCancellationRequested();
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In general, cancellation should not be checked for / cause an exception after the relevant work has already completed. This loop should be restructured such that ThrowIfCancellationRequested occurs where you currently poll IsCancellationRequested.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agreed, will change.

@terrajobst terrajobst added the api-ready-for-review API is ready for formal API review - https://github.com/dotnet/apireviews label Jan 14, 2015
@terrajobst
Copy link
Member

We've reviewed these APIs.

We're OK with adding these APIs but in order to be complete, Save needs corresponding methods as well.

@dotnet-bot
Copy link

Can one of the admins approve this PR test or whitelist this user? ('@dotnet-bot add to whitelist' to whitelist, '@dotnet-bot okay to test' to accept for PR, '@dotnet-bot test this please' to retest. Case sensitive).

1 similar comment
@dotnet-bot
Copy link

Can one of the admins approve this PR test or whitelist this user? ('@dotnet-bot add to whitelist' to whitelist, '@dotnet-bot okay to test' to accept for PR, '@dotnet-bot test this please' to retest. Case sensitive).

@scalablecory
Copy link
Author

Thank you @terrajobst.

In addition to Save(), there is also XNode.ReadFrom() and XNode.WriteTo() which should get an async implementation. I will add these to the PR.

I excluded Save() initially due to there not really being a clean way to implement... will involve essentially duplicating all relevant implementation.

@dnfclas
Copy link

dnfclas commented Jan 28, 2015

@scalablecory, Thanks for signing the contribution license agreement so quickly! Actual humans will now validate the agreement and then evaluate the PR.

Thanks, DNFBOT;

public static async Task<XNode> ReadFromAsync(XmlReader reader, CancellationToken cancellationToken)
{
if (reader == null) throw new ArgumentNullException("reader");
if (reader.ReadState != ReadState.Interactive) throw new InvalidOperationException(SR.InvalidOperation_ExpectedInteractive);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same comment about separating out usage errors into non-async methods.

@stephentoub
Copy link
Member

Maybe I just missed them or discussion of them, but are there tests to accompany the new APIs?

@nguerrera
Copy link
Contributor

@scalablecory We've changed our branching strategy in a way that impacts this PR.

When you're ready to continue work on this, you'll need to either recreate the PR against the 'future' branch or wait until after we have snapped the first release branch before we can merge it in to master.

See https://github.com/dotnet/corefx/wiki/branching-guide

@scalablecory
Copy link
Author

Hrm, I wonder if I could rebase it to keep the same PR.

@khellang
Copy link
Member

Unfortunately you can't change the target branch of an existing PR. You have to close this and open a new one targeted at the new branch. 😭

Add your 👍 here: isaacs/github#18 😉

@ghost
Copy link

ghost commented May 24, 2015

@scalablecory , it is so simple! :just-kidding: :)
You can open a new PR against future branch. You may want to work in your corresponding future branch:

cd \my\projects\path\corefx
git remote add corefx https://github.com/dotnet/corefx
git fetch corefx
git checkout future
git merge --no-ff master
# resolve conflicts
# add more commits, for example, addressing review comments here
git push

Then future...scalablecory:future and open a new PR, where you reference the link to this PR in description to retain the comment history / all this interesting conversation. :)

@stephentoub
Copy link
Member

@scalablecory, just checking in on this. Do you need any assistance in order to move forward?

@scalablecory
Copy link
Author

@stephentoub Someone reorganized the master repo without using "git mv" and it wrecked my merge. I'm finding some time to redo the changes against future.

@KindDragon
Copy link
Contributor

without using "git mv"

JFYI, Git doesn't store move/rename information. git mv identical to copy file to another location and remove it from old.
You can try this advice http://stackoverflow.com/a/4722641/61505 , maybe git will detect renames with this changes (check if you have line too many files skipping inexact rename detection in git output)

@ghost
Copy link

ghost commented Jun 10, 2015

@stephentoub, since OP is having trouble with rebasing; would it make sense if this gets superseded by a separate PR, for instance, with an additional commit of yours fixing the merge conflicts?

@stephentoub
Copy link
Member

It's up to Cory whether he'd like that or not.

@ghost
Copy link

ghost commented Jul 7, 2015

@scalablecory, are you still pursuing this? Otherwise someone else can rebase these commits on your behalf and send a new PR.

@scalablecory
Copy link
Author

@stephentoub If you've got the time to fix this patch, please do! I'm unfortunately too busy to follow through.

@stephentoub
Copy link
Member

Ok, I'll see what I can do. Thanks.

@stephentoub
Copy link
Member

Replaced by #2436.

@karelz karelz modified the milestone: 1.0.0-rtm Dec 3, 2016
MaximLipnin pushed a commit to MaximLipnin/corefx that referenced this pull request Aug 9, 2018
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
api-needs-work API needs work before it is approved, it is NOT ready for implementation api-ready-for-review API is ready for formal API review - https://github.com/dotnet/apireviews area-System.Xml
Projects
None yet