UnityWebRequest, Addressables returns exception when already isDone and AsyncOperation has error.

master
neuecc 2020-07-13 09:34:43 +09:00
parent 9ddcac4c6c
commit b97451a915
3 changed files with 82 additions and 14 deletions

View File

@ -22,13 +22,29 @@ namespace Cysharp.Threading.Tasks
public static UniTask WithCancellation(this AsyncOperationHandle handle, CancellationToken cancellationToken) public static UniTask WithCancellation(this AsyncOperationHandle handle, CancellationToken cancellationToken)
{ {
if (handle.IsDone) return UniTask.CompletedTask; if (handle.IsDone)
{
if (handle.Status == AsyncOperationStatus.Failed)
{
return UniTask.FromException(handle.OperationException);
}
return UniTask.CompletedTask;
}
return new UniTask(AsyncOperationHandleWithCancellationSource.Create(handle, cancellationToken, out var token), token); return new UniTask(AsyncOperationHandleWithCancellationSource.Create(handle, cancellationToken, out var token), token);
} }
public static UniTask ToUniTask(this AsyncOperationHandle handle, IProgress<float> progress = null, PlayerLoopTiming timing = PlayerLoopTiming.Update, CancellationToken cancellationToken = default(CancellationToken)) public static UniTask ToUniTask(this AsyncOperationHandle handle, IProgress<float> progress = null, PlayerLoopTiming timing = PlayerLoopTiming.Update, CancellationToken cancellationToken = default(CancellationToken))
{ {
if (handle.IsDone) return UniTask.CompletedTask; if (handle.IsDone)
{
if (handle.Status == AsyncOperationStatus.Failed)
{
return UniTask.FromException(handle.OperationException);
}
return UniTask.CompletedTask;
}
return new UniTask(AsyncOperationHandleConfiguredSource.Create(handle, timing, progress, cancellationToken, out var token), token); return new UniTask(AsyncOperationHandleConfiguredSource.Create(handle, timing, progress, cancellationToken, out var token), token);
} }
@ -319,13 +335,28 @@ namespace Cysharp.Threading.Tasks
public static UniTask<T> WithCancellation<T>(this AsyncOperationHandle<T> handle, CancellationToken cancellationToken) public static UniTask<T> WithCancellation<T>(this AsyncOperationHandle<T> handle, CancellationToken cancellationToken)
{ {
if (handle.IsDone) return UniTask.FromResult(handle.Result); if (handle.IsDone)
{
if (handle.Status == AsyncOperationStatus.Failed)
{
return UniTask.FromException<T>(handle.OperationException);
}
return UniTask.FromResult(handle.Result);
}
return new UniTask<T>(AsyncOperationHandleWithCancellationSource<T>.Create(handle, cancellationToken, out var token), token); return new UniTask<T>(AsyncOperationHandleWithCancellationSource<T>.Create(handle, cancellationToken, out var token), token);
} }
public static UniTask<T> ToUniTask<T>(this AsyncOperationHandle<T> handle, IProgress<float> progress = null, PlayerLoopTiming timing = PlayerLoopTiming.Update, CancellationToken cancellationToken = default(CancellationToken)) public static UniTask<T> ToUniTask<T>(this AsyncOperationHandle<T> handle, IProgress<float> progress = null, PlayerLoopTiming timing = PlayerLoopTiming.Update, CancellationToken cancellationToken = default(CancellationToken))
{ {
if (handle.IsDone) return UniTask.FromResult(handle.Result); if (handle.IsDone)
{
if (handle.Status == AsyncOperationStatus.Failed)
{
return UniTask.FromException<T>(handle.OperationException);
}
return UniTask.FromResult(handle.Result);
}
return new UniTask<T>(AsyncOperationHandleConfiguredSource<T>.Create(handle, timing, progress, cancellationToken, out var token), token); return new UniTask<T>(AsyncOperationHandleConfiguredSource<T>.Create(handle, timing, progress, cancellationToken, out var token), token);
} }

View File

@ -1189,14 +1189,28 @@ namespace Cysharp.Threading.Tasks
public static UniTask<UnityWebRequest> WithCancellation(this UnityWebRequestAsyncOperation asyncOperation, CancellationToken cancellationToken) public static UniTask<UnityWebRequest> WithCancellation(this UnityWebRequestAsyncOperation asyncOperation, CancellationToken cancellationToken)
{ {
Error.ThrowArgumentNullException(asyncOperation, nameof(asyncOperation)); Error.ThrowArgumentNullException(asyncOperation, nameof(asyncOperation));
if (asyncOperation.isDone) return UniTask.FromResult(asyncOperation.webRequest); if (asyncOperation.isDone)
{
if (asyncOperation.webRequest.IsError())
{
return UniTask.FromException<UnityWebRequest>(new UnityWebRequestException(asyncOperation.webRequest));
}
return UniTask.FromResult(asyncOperation.webRequest);
}
return new UniTask<UnityWebRequest>(UnityWebRequestAsyncOperationWithCancellationSource.Create(asyncOperation, cancellationToken, out var token), token); return new UniTask<UnityWebRequest>(UnityWebRequestAsyncOperationWithCancellationSource.Create(asyncOperation, cancellationToken, out var token), token);
} }
public static UniTask<UnityWebRequest> ToUniTask(this UnityWebRequestAsyncOperation asyncOperation, IProgress<float> progress = null, PlayerLoopTiming timing = PlayerLoopTiming.Update, CancellationToken cancellationToken = default(CancellationToken)) public static UniTask<UnityWebRequest> ToUniTask(this UnityWebRequestAsyncOperation asyncOperation, IProgress<float> progress = null, PlayerLoopTiming timing = PlayerLoopTiming.Update, CancellationToken cancellationToken = default(CancellationToken))
{ {
Error.ThrowArgumentNullException(asyncOperation, nameof(asyncOperation)); Error.ThrowArgumentNullException(asyncOperation, nameof(asyncOperation));
if (asyncOperation.isDone) return UniTask.FromResult(asyncOperation.webRequest); if (asyncOperation.isDone)
{
if (asyncOperation.webRequest.IsError())
{
return UniTask.FromException<UnityWebRequest>(new UnityWebRequestException(asyncOperation.webRequest));
}
return UniTask.FromResult(asyncOperation.webRequest);
}
return new UniTask<UnityWebRequest>(UnityWebRequestAsyncOperationConfiguredSource.Create(asyncOperation, timing, progress, cancellationToken, out var token), token); return new UniTask<UnityWebRequest>(UnityWebRequestAsyncOperationConfiguredSource.Create(asyncOperation, timing, progress, cancellationToken, out var token), token);
} }

View File

@ -16,6 +16,7 @@
Func<string, string> ToUniTaskReturnType = x => (x == "void") ? "UniTask" : $"UniTask<{x}>"; Func<string, string> ToUniTaskReturnType = x => (x == "void") ? "UniTask" : $"UniTask<{x}>";
Func<string, string> ToIUniTaskSourceReturnType = x => (x == "void") ? "IUniTaskSource" : $"IUniTaskSource<{x}>"; Func<string, string> ToIUniTaskSourceReturnType = x => (x == "void") ? "IUniTaskSource" : $"IUniTaskSource<{x}>";
Func<(string typeName, string returnType, string returnField), bool> IsUnityWebRequest = x => x.returnType == "UnityWebRequest";
Func<(string typeName, string returnType, string returnField), bool> IsVoid = x => x.returnType == "void"; Func<(string typeName, string returnType, string returnField), bool> IsVoid = x => x.returnType == "void";
#> #>
#pragma warning disable CS1591 // Missing XML comment for publicly visible type or member #pragma warning disable CS1591 // Missing XML comment for publicly visible type or member
@ -34,7 +35,7 @@ namespace Cysharp.Threading.Tasks
public static partial class UnityAsyncExtensions public static partial class UnityAsyncExtensions
{ {
<# foreach(var t in types) { #> <# foreach(var t in types) { #>
<# if(t.returnType == "UnityWebRequest") { #> <# if(IsUnityWebRequest(t)) { #>
#if ENABLE_UNITYWEBREQUEST #if ENABLE_UNITYWEBREQUEST
<# } #> <# } #>
#region <#= t.typeName #> #region <#= t.typeName #>
@ -48,14 +49,36 @@ namespace Cysharp.Threading.Tasks
public static <#= ToUniTaskReturnType(t.returnType) #> WithCancellation(this <#= t.typeName #> asyncOperation, CancellationToken cancellationToken) public static <#= ToUniTaskReturnType(t.returnType) #> WithCancellation(this <#= t.typeName #> asyncOperation, CancellationToken cancellationToken)
{ {
Error.ThrowArgumentNullException(asyncOperation, nameof(asyncOperation)); Error.ThrowArgumentNullException(asyncOperation, nameof(asyncOperation));
<# if(IsUnityWebRequest(t)) { #>
if (asyncOperation.isDone)
{
if (asyncOperation.webRequest.IsError())
{
return UniTask.FromException<UnityWebRequest>(new UnityWebRequestException(asyncOperation.webRequest));
}
return UniTask.FromResult(asyncOperation.webRequest);
}
<# } else { #>
if (asyncOperation.isDone) return <#= IsVoid(t) ? "UniTask.CompletedTask" : $"UniTask.FromResult(asyncOperation.{t.returnField})" #>; if (asyncOperation.isDone) return <#= IsVoid(t) ? "UniTask.CompletedTask" : $"UniTask.FromResult(asyncOperation.{t.returnField})" #>;
<# } #>
return new <#= ToUniTaskReturnType(t.returnType) #>(<#= t.typeName #>WithCancellationSource.Create(asyncOperation, cancellationToken, out var token), token); return new <#= ToUniTaskReturnType(t.returnType) #>(<#= t.typeName #>WithCancellationSource.Create(asyncOperation, cancellationToken, out var token), token);
} }
public static <#= ToUniTaskReturnType(t.returnType) #> ToUniTask(this <#= t.typeName #> asyncOperation, IProgress<float> progress = null, PlayerLoopTiming timing = PlayerLoopTiming.Update, CancellationToken cancellationToken = default(CancellationToken)) public static <#= ToUniTaskReturnType(t.returnType) #> ToUniTask(this <#= t.typeName #> asyncOperation, IProgress<float> progress = null, PlayerLoopTiming timing = PlayerLoopTiming.Update, CancellationToken cancellationToken = default(CancellationToken))
{ {
Error.ThrowArgumentNullException(asyncOperation, nameof(asyncOperation)); Error.ThrowArgumentNullException(asyncOperation, nameof(asyncOperation));
<# if(IsUnityWebRequest(t)) { #>
if (asyncOperation.isDone)
{
if (asyncOperation.webRequest.IsError())
{
return UniTask.FromException<UnityWebRequest>(new UnityWebRequestException(asyncOperation.webRequest));
}
return UniTask.FromResult(asyncOperation.webRequest);
}
<# } else { #>
if (asyncOperation.isDone) return <#= IsVoid(t) ? "UniTask.CompletedTask" : $"UniTask.FromResult(asyncOperation.{t.returnField})" #>; if (asyncOperation.isDone) return <#= IsVoid(t) ? "UniTask.CompletedTask" : $"UniTask.FromResult(asyncOperation.{t.returnField})" #>;
<# } #>
return new <#= ToUniTaskReturnType(t.returnType) #>(<#= t.typeName #>ConfiguredSource.Create(asyncOperation, timing, progress, cancellationToken, out var token), token); return new <#= ToUniTaskReturnType(t.returnType) #>(<#= t.typeName #>ConfiguredSource.Create(asyncOperation, timing, progress, cancellationToken, out var token), token);
} }
@ -81,7 +104,7 @@ namespace Cysharp.Threading.Tasks
<# if (!IsVoid(t)) { #> <# if (!IsVoid(t)) { #>
var result = <#= $"asyncOperation.{t.returnField}" #>; var result = <#= $"asyncOperation.{t.returnField}" #>;
asyncOperation = null; asyncOperation = null;
<# if(t.returnType == "UnityWebRequest") { #> <# if(IsUnityWebRequest(t)) { #>
if (result.IsError()) if (result.IsError())
{ {
throw new UnityWebRequestException(result); throw new UnityWebRequestException(result);
@ -97,7 +120,7 @@ namespace Cysharp.Threading.Tasks
<# if (!IsVoid(t)) { #> <# if (!IsVoid(t)) { #>
var result = <#= $"asyncOperation.{t.returnField}" #>; var result = <#= $"asyncOperation.{t.returnField}" #>;
asyncOperation = null; asyncOperation = null;
<# if(t.returnType == "UnityWebRequest") { #> <# if(IsUnityWebRequest(t)) { #>
if (result.IsError()) if (result.IsError())
{ {
throw new UnityWebRequestException(result); throw new UnityWebRequestException(result);
@ -182,7 +205,7 @@ namespace Cysharp.Threading.Tasks
else else
{ {
completed = true; completed = true;
<# if(t.returnType == "UnityWebRequest") { #> <# if(IsUnityWebRequest(t)) { #>
var result = asyncOperation.webRequest; var result = asyncOperation.webRequest;
if (result.IsError()) if (result.IsError())
{ {
@ -240,7 +263,7 @@ namespace Cysharp.Threading.Tasks
if (cancellationToken.IsCancellationRequested) if (cancellationToken.IsCancellationRequested)
{ {
completed = true; completed = true;
<# if(t.returnType == "UnityWebRequest") { #> <# if(IsUnityWebRequest(t)) { #>
asyncOperation.webRequest.Abort(); asyncOperation.webRequest.Abort();
<# } #> <# } #>
core.TrySetCanceled(cancellationToken); core.TrySetCanceled(cancellationToken);
@ -347,7 +370,7 @@ namespace Cysharp.Threading.Tasks
{ {
if (cancellationToken.IsCancellationRequested) if (cancellationToken.IsCancellationRequested)
{ {
<# if(t.returnType == "UnityWebRequest") { #> <# if(IsUnityWebRequest(t)) { #>
asyncOperation.webRequest.Abort(); asyncOperation.webRequest.Abort();
<# } #> <# } #>
core.TrySetCanceled(cancellationToken); core.TrySetCanceled(cancellationToken);
@ -361,7 +384,7 @@ namespace Cysharp.Threading.Tasks
if (asyncOperation.isDone) if (asyncOperation.isDone)
{ {
<# if(t.returnType == "UnityWebRequest") { #> <# if(IsUnityWebRequest(t)) { #>
if (asyncOperation.webRequest.IsError()) if (asyncOperation.webRequest.IsError())
{ {
core.TrySetException(new UnityWebRequestException(asyncOperation.webRequest)); core.TrySetException(new UnityWebRequestException(asyncOperation.webRequest));
@ -391,7 +414,7 @@ namespace Cysharp.Threading.Tasks
} }
#endregion #endregion
<# if(t.returnType == "UnityWebRequest") { #> <# if(IsUnityWebRequest(t)) { #>
#endif #endif
<# } #> <# } #>