diff --git a/Deepgram.Dev.sln b/Deepgram.Dev.sln index c8379a58..25c56444 100644 --- a/Deepgram.Dev.sln +++ b/Deepgram.Dev.sln @@ -43,8 +43,6 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "keepalive", "keepalive", "{ EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "exercise_timeout", "exercise_timeout", "{3AC17A9C-30BB-4298-8E5A-4FAE73189821}" EndProject -Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "ExerciseTimeout", "tests\expected_failures\exercise_timeout\ExerciseTimeout.csproj", "{E19BE681-F801-444F-A3BD-8F1207FB3982}" -EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "KeepAlive", "tests\edge_cases\keepalive\KeepAlive.csproj", "{D3F886B5-1C28-44AF-A416-2BBE660D5EC4}" EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "file", "file", "{FA17B9A9-F542-4F8A-AF4B-48404D009967}" @@ -127,6 +125,20 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Manage", "examples\manage\s EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Manage", "examples\manage\usage\Manage.csproj", "{260D68E2-540F-4BFF-AF52-B014E7615795}" EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "trigger_cancel", "trigger_cancel", "{80E7546A-4CED-4644-8900-983422CDE73C}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "bad_host", "bad_host", "{D100AACD-E5FB-45E5-980B-B19C091440B2}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "websocket", "websocket", "{1262085B-6088-4DAA-8683-A9B4AD08EE63}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "rest", "rest", "{7FA977F3-415E-4681-B316-5C273DF3A1C6}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "BadHost", "tests\expected_failures\rest\bad_host\BadHost.csproj", "{DF383769-5F1F-4692-854F-2E923F3D0F09}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TriggerCancel", "tests\expected_failures\rest\trigger_cancel\TriggerCancel.csproj", "{F736604C-A245-411E-BECE-028FBD98166E}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "ExerciseTimeout", "tests\expected_failures\websocket\exercise_timeout\ExerciseTimeout.csproj", "{8C5A02D8-E18B-4060-A567-A4AACC49B2F6}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -157,10 +169,6 @@ Global {74335799-3B43-432C-ACD9-FBF2AB32A64A}.Debug|Any CPU.Build.0 = Debug|Any CPU {74335799-3B43-432C-ACD9-FBF2AB32A64A}.Release|Any CPU.ActiveCfg = Release|Any CPU {74335799-3B43-432C-ACD9-FBF2AB32A64A}.Release|Any CPU.Build.0 = Release|Any CPU - {E19BE681-F801-444F-A3BD-8F1207FB3982}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {E19BE681-F801-444F-A3BD-8F1207FB3982}.Debug|Any CPU.Build.0 = Debug|Any CPU - {E19BE681-F801-444F-A3BD-8F1207FB3982}.Release|Any CPU.ActiveCfg = Release|Any CPU - {E19BE681-F801-444F-A3BD-8F1207FB3982}.Release|Any CPU.Build.0 = Release|Any CPU {D3F886B5-1C28-44AF-A416-2BBE660D5EC4}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {D3F886B5-1C28-44AF-A416-2BBE660D5EC4}.Debug|Any CPU.Build.0 = Debug|Any CPU {D3F886B5-1C28-44AF-A416-2BBE660D5EC4}.Release|Any CPU.ActiveCfg = Release|Any CPU @@ -241,6 +249,18 @@ Global {260D68E2-540F-4BFF-AF52-B014E7615795}.Debug|Any CPU.Build.0 = Debug|Any CPU {260D68E2-540F-4BFF-AF52-B014E7615795}.Release|Any CPU.ActiveCfg = Release|Any CPU {260D68E2-540F-4BFF-AF52-B014E7615795}.Release|Any CPU.Build.0 = Release|Any CPU + {DF383769-5F1F-4692-854F-2E923F3D0F09}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {DF383769-5F1F-4692-854F-2E923F3D0F09}.Debug|Any CPU.Build.0 = Debug|Any CPU + {DF383769-5F1F-4692-854F-2E923F3D0F09}.Release|Any CPU.ActiveCfg = Release|Any CPU + {DF383769-5F1F-4692-854F-2E923F3D0F09}.Release|Any CPU.Build.0 = Release|Any CPU + {F736604C-A245-411E-BECE-028FBD98166E}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {F736604C-A245-411E-BECE-028FBD98166E}.Debug|Any CPU.Build.0 = Debug|Any CPU + {F736604C-A245-411E-BECE-028FBD98166E}.Release|Any CPU.ActiveCfg = Release|Any CPU + {F736604C-A245-411E-BECE-028FBD98166E}.Release|Any CPU.Build.0 = Release|Any CPU + {8C5A02D8-E18B-4060-A567-A4AACC49B2F6}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {8C5A02D8-E18B-4060-A567-A4AACC49B2F6}.Debug|Any CPU.Build.0 = Debug|Any CPU + {8C5A02D8-E18B-4060-A567-A4AACC49B2F6}.Release|Any CPU.ActiveCfg = Release|Any CPU + {8C5A02D8-E18B-4060-A567-A4AACC49B2F6}.Release|Any CPU.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE @@ -260,8 +280,7 @@ Global {1280E66D-A375-422A-ACB4-48F17E9C190E} = {9D2B336D-17F9-41D5-A4E5-F3EDA7F496A5} {5B1C7C37-BAE9-4027-927C-38B2393B3F43} = {9D2B336D-17F9-41D5-A4E5-F3EDA7F496A5} {7F7328CF-D932-4D0F-B832-9CCE65E7B308} = {1280E66D-A375-422A-ACB4-48F17E9C190E} - {3AC17A9C-30BB-4298-8E5A-4FAE73189821} = {5B1C7C37-BAE9-4027-927C-38B2393B3F43} - {E19BE681-F801-444F-A3BD-8F1207FB3982} = {3AC17A9C-30BB-4298-8E5A-4FAE73189821} + {3AC17A9C-30BB-4298-8E5A-4FAE73189821} = {1262085B-6088-4DAA-8683-A9B4AD08EE63} {D3F886B5-1C28-44AF-A416-2BBE660D5EC4} = {7F7328CF-D932-4D0F-B832-9CCE65E7B308} {FA17B9A9-F542-4F8A-AF4B-48404D009967} = {77ACBABB-CF6B-4929-957C-480E29646DFD} {02F10F52-5DFF-4CEC-8AAF-AFA16DEE27F1} = {77ACBABB-CF6B-4929-957C-480E29646DFD} @@ -303,6 +322,13 @@ Global {0C82172F-6433-4089-919A-6CA7A54BAFA4} = {E7D50060-F040-4607-A0EF-34A4ABB4C770} {A65BCE7D-761C-4D09-8E89-CEA461D7C832} = {6B24CAD4-8486-405C-B7EB-14086177C634} {260D68E2-540F-4BFF-AF52-B014E7615795} = {CB0677E6-85EC-47B9-A392-FF5B56484F15} + {80E7546A-4CED-4644-8900-983422CDE73C} = {7FA977F3-415E-4681-B316-5C273DF3A1C6} + {D100AACD-E5FB-45E5-980B-B19C091440B2} = {7FA977F3-415E-4681-B316-5C273DF3A1C6} + {1262085B-6088-4DAA-8683-A9B4AD08EE63} = {5B1C7C37-BAE9-4027-927C-38B2393B3F43} + {7FA977F3-415E-4681-B316-5C273DF3A1C6} = {5B1C7C37-BAE9-4027-927C-38B2393B3F43} + {DF383769-5F1F-4692-854F-2E923F3D0F09} = {D100AACD-E5FB-45E5-980B-B19C091440B2} + {F736604C-A245-411E-BECE-028FBD98166E} = {80E7546A-4CED-4644-8900-983422CDE73C} + {8C5A02D8-E18B-4060-A567-A4AACC49B2F6} = {3AC17A9C-30BB-4298-8E5A-4FAE73189821} EndGlobalSection GlobalSection(ExtensibilityGlobals) = postSolution SolutionGuid = {8D4ABC6D-7126-4EE2-9303-43A954616B2A} diff --git a/Deepgram/Abstractions/AbstractRestClient.cs b/Deepgram/Abstractions/AbstractRestClient.cs index b806fe34..8c0f6a2b 100644 --- a/Deepgram/Abstractions/AbstractRestClient.cs +++ b/Deepgram/Abstractions/AbstractRestClient.cs @@ -47,7 +47,7 @@ internal AbstractRestClient(string? apiKey = null, DeepgramHttpClientOptions? op public virtual async Task GetAsync(string uriSegment, CancellationTokenSource? cancellationToken = null, Dictionary? addons = null, Dictionary? headers = null) { - Log.Verbose("GetAsync", "ENTER"); + Log.Verbose("AbstractRestClient.GetAsync", "ENTER"); Log.Debug("GetAsync", $"uriSegment: {uriSegment}"); Log.Debug("GetAsync", $"addons: {addons}"); @@ -82,13 +82,21 @@ public virtual async Task GetAsync(string uriSegment, CancellationTokenSou var result = await HttpRequestUtil.DeserializeAsync(response); Log.Debug("GetAsync", "Succeeded"); - Log.Verbose("GetAsync", "LEAVE"); + Log.Verbose("AbstractRestClient.GetAsync", "LEAVE"); return result; } + catch (OperationCanceledException ex) + { + Log.Information("GetAsync", "Task was cancelled."); + Log.Verbose("GetAsync", $"Connect cancelled. Info: {ex}"); + Log.Verbose("AbstractRestClient.GetAsync", "LEAVE"); + throw; + } catch (Exception ex) { - Log.Error("GetAsync", $"Exception: {ex}"); - Log.Verbose("GetAsync", "LEAVE"); + Log.Error("GetAsync", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("GetAsync", $"Excepton: {ex}"); + Log.Verbose("AbstractRestClient.GetAsync", "LEAVE"); throw; } } @@ -96,7 +104,7 @@ public virtual async Task GetAsync(string uriSegment, CancellationTokenSou public virtual async Task GetAsync(string uriSegment, S? parameter, CancellationTokenSource? cancellationToken = null, Dictionary? addons = null, Dictionary? headers = null) { - Log.Verbose("GetAsync", "ENTER"); + Log.Verbose("AbstractRestClient.GetAsync", "ENTER"); Log.Debug("GetAsync", $"uriSegment: {uriSegment}"); Log.Debug("GetAsync", $"parameter: {parameter}"); Log.Debug("GetAsync", $"addons: {addons}"); @@ -131,14 +139,22 @@ public virtual async Task GetAsync(string uriSegment, S? parameter, Can var result = await HttpRequestUtil.DeserializeAsync(response); Log.Debug("GetAsync", "Succeeded"); - Log.Verbose("GetAsync", "LEAVE"); + Log.Verbose("AbstractRestClient.GetAsync", "LEAVE"); return result; } + catch (OperationCanceledException ex) + { + Log.Information("GetAsync", "Task was cancelled."); + Log.Verbose("GetAsync", $"Connect cancelled. Info: {ex}"); + Log.Verbose("AbstractRestClient.GetAsync", "LEAVE"); + throw; + } catch (Exception ex) { - Log.Error("GetAsync", $"Exception: {ex}"); - Log.Verbose("GetAsync", "LEAVE"); + Log.Error("GetAsync", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("GetAsync", $"Excepton: {ex}"); + Log.Verbose("AbstractRestClient.GetAsync", "LEAVE"); throw; } } @@ -155,7 +171,7 @@ public virtual async Task PostRetrieveLocalFileAsync? headers = null ) { - Log.Verbose("PostRetrieveLocalFileAsync", "ENTER"); + Log.Verbose("AbstractRestClient.PostRetrieveLocalFileAsync", "ENTER"); Log.Debug("PostRetrieveLocalFileAsync", $"uriSegment: {uriSegment}"); Log.Debug("PostRetrieveLocalFileAsync", $"parameter: {parameter}"); Log.Debug("PostRetrieveLocalFileAsync", $"keys: {keys}"); @@ -237,7 +253,7 @@ public virtual async Task PostRetrieveLocalFileAsync", "Succeeded"); - Log.Verbose("PostRetrieveLocalFileAsync", "LEAVE"); + Log.Verbose("AbstractRestClient.PostRetrieveLocalFileAsync", "LEAVE"); return new LocalFileWithMetadata() { @@ -246,10 +262,18 @@ public virtual async Task PostRetrieveLocalFileAsync", "Task was cancelled."); + Log.Verbose("PostRetrieveLocalFileAsync", $"Connect cancelled. Info: {ex}"); + Log.Verbose("AbstractRestClient.PostRetrieveLocalFileAsync", "LEAVE"); + throw; + } catch (Exception ex) { - Log.Error("PostRetrieveLocalFileAsync", $"Exception: {ex}"); - Log.Verbose("PostRetrieveLocalFileAsync", "LEAVE"); + Log.Error("PostRetrieveLocalFileAsync", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("PostRetrieveLocalFileAsync", $"Excepton: {ex}"); + Log.Verbose("AbstractRestClient.PostRetrieveLocalFileAsync", "LEAVE"); throw; } } @@ -264,7 +288,7 @@ public virtual async Task PostRetrieveLocalFileAsync PostAsync(string uriSegment, S? parameter, CancellationTokenSource? cancellationToken = null, Dictionary? addons = null, Dictionary? headers = null) { - Log.Verbose("PostAsync", "ENTER"); + Log.Verbose("AbstractRestClient.PostAsync", "ENTER"); Log.Debug("PostAsync", $"uriSegment: {uriSegment}"); Log.Debug("PostAsync", $"parameter: {parameter}"); Log.Debug("PostAsync", $"addons: {addons}"); @@ -302,14 +326,22 @@ public virtual async Task PostAsync(string uriSegment, S? parameter, Ca var result = await HttpRequestUtil.DeserializeAsync(response); Log.Debug("PostAsync", $"Succeeded. Result: {result}"); - Log.Verbose("PostAsync", "LEAVE"); + Log.Verbose("AbstractRestClient.PostAsync", "LEAVE"); return result; } + catch (OperationCanceledException ex) + { + Log.Information("PostAsync", "Task was cancelled."); + Log.Verbose("PostAsync", $"Connect cancelled. Info: {ex}"); + Log.Verbose("AbstractRestClient.PostAsync", "LEAVE"); + throw; + } catch (Exception ex) { - Log.Error("PostAsync", $"Exception: {ex}"); - Log.Verbose("PostAsync", "LEAVE"); + Log.Error("PostAsync", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("PostAsync", $"Excepton: {ex}"); + Log.Verbose("AbstractRestClient.PostAsync", "LEAVE"); throw; } } @@ -317,7 +349,7 @@ public virtual async Task PostAsync(string uriSegment, S? parameter, Ca public virtual async Task PostAsync(string uriSegment, S? parameter, R? content, CancellationTokenSource? cancellationToken = null, Dictionary? addons = null, Dictionary? headers = null) { - Log.Verbose("PostAsync", "ENTER"); + Log.Verbose("AbstractRestClient.PostAsync", "ENTER"); Log.Debug("PostAsync", $"uriSegment: {uriSegment}"); Log.Debug("PostAsync", $"parameter: {parameter}"); Log.Debug("PostAsync", $"addons: {addons}"); @@ -365,14 +397,22 @@ public virtual async Task PostAsync(string uriSegment, S? parameter, var result = await HttpRequestUtil.DeserializeAsync(response); Log.Debug("PostAsync", $"Succeeded. Result: {result}"); - Log.Verbose("PostAsync", "LEAVE"); + Log.Verbose("AbstractRestClient.PostAsync", "LEAVE"); return result; } + catch (OperationCanceledException ex) + { + Log.Information("PostAsync", "Task was cancelled."); + Log.Verbose("PostAsync", $"Connect cancelled. Info: {ex}"); + Log.Verbose("AbstractRestClient.PostAsync", "LEAVE"); + throw; + } catch (Exception ex) { - Log.Error("PostAsync", $"Exception: {ex}"); - Log.Verbose("PostAsync", "LEAVE"); + Log.Error("PostAsync", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("PostAsync", $"Excepton: {ex}"); + Log.Verbose("AbstractRestClient.PostAsync", "LEAVE"); throw; } } @@ -386,7 +426,7 @@ public virtual async Task PostAsync(string uriSegment, S? parameter, public virtual async Task PatchAsync(string uriSegment, S? parameter, CancellationTokenSource? cancellationToken = null, Dictionary? addons = null, Dictionary? headers = null) { - Log.Verbose("PatchAsync", "ENTER"); + Log.Verbose("AbstractRestClient.PatchAsync", "ENTER"); Log.Debug("PatchAsync", $"uriSegment: {uriSegment}"); Log.Debug("PatchAsync", $"parameter: {parameter}"); Log.Debug("PatchAsync", $"addons: {addons}"); @@ -431,18 +471,25 @@ public virtual async Task PatchAsync(string uriSegment, S? parameter, C var result = await HttpRequestUtil.DeserializeAsync(response); Log.Debug("PatchAsync", $"Succeeded. Result: {result}"); - Log.Verbose("PatchAsync", "LEAVE"); + Log.Verbose("AbstractRestClient.PatchAsync", "LEAVE"); return result; } + catch (OperationCanceledException ex) + { + Log.Information("PatchAsync", "Task was cancelled."); + Log.Verbose("PatchAsync", $"Connect cancelled. Info: {ex}"); + Log.Verbose("AbstractRestClient.PatchAsync", "LEAVE"); + throw; + } catch (Exception ex) { - Log.Error("PatchAsync", $"Exception: {ex}"); - Log.Verbose("PatchAsync", "LEAVE"); + Log.Error("PatchAsync", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("PatchAsync", $"Excepton: {ex}"); + Log.Verbose("AbstractRestClient.PatchAsync", "LEAVE"); throw; } - } /// @@ -454,7 +501,7 @@ public virtual async Task PatchAsync(string uriSegment, S? parameter, C public virtual async Task PutAsync(string uriSegment, S? parameter, CancellationTokenSource? cancellationToken = null, Dictionary? addons = null, Dictionary? headers = null) { - Log.Verbose("PutAsync", "ENTER"); + Log.Verbose("AbstractRestClient.PutAsync", "ENTER"); Log.Debug("PutAsync", $"uriSegment: {uriSegment}"); Log.Debug("PutAsync", $"parameter: {parameter}"); Log.Debug("PutAsync", $"addons: {addons}"); @@ -496,14 +543,22 @@ public virtual async Task PutAsync(string uriSegment, S? parameter, Can var result = await HttpRequestUtil.DeserializeAsync(response); Log.Debug("PutAsync", $"Succeeded. Result: {result}"); - Log.Verbose("PutAsync", "LEAVE"); + Log.Verbose("AbstractRestClient.PutAsync", "LEAVE"); return result; } + catch (OperationCanceledException ex) + { + Log.Information("PutAsync", "Task was cancelled."); + Log.Verbose("PutAsync", $"Connect cancelled. Info: {ex}"); + Log.Verbose("AbstractRestClient.PutAsync", "LEAVE"); + throw; + } catch (Exception ex) { - Log.Error("PutAsync", $"Exception: {ex}"); - Log.Verbose("PutAsync", "LEAVE"); + Log.Error("PutAsync", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("PutAsync", $"Excepton: {ex}"); + Log.Verbose("AbstractRestClient.PutAsync", "LEAVE"); throw; } } @@ -515,7 +570,7 @@ public virtual async Task PutAsync(string uriSegment, S? parameter, Can public virtual async Task DeleteAsync(string uriSegment, CancellationTokenSource? cancellationToken = null, Dictionary? addons = null, Dictionary? headers = null) { - Log.Verbose("DeleteAsync", "ENTER"); + Log.Verbose("AbstractRestClient.DeleteAsync", "ENTER"); Log.Debug("DeleteAsync", $"uriSegment: {uriSegment}"); Log.Debug("DeleteAsync", $"addons: {addons}"); @@ -549,14 +604,22 @@ public virtual async Task DeleteAsync(string uriSegment, CancellationToken var result = await HttpRequestUtil.DeserializeAsync(response); Log.Debug("DeleteAsync", $"Succeeded. Result: {result}"); - Log.Verbose("DeleteAsync", "LEAVE"); + Log.Verbose("AbstractRestClient.DeleteAsync", "LEAVE"); return result; } + catch (OperationCanceledException ex) + { + Log.Information("DeleteAsync", "Task was cancelled."); + Log.Verbose("DeleteAsync", $"Connect cancelled. Info: {ex}"); + Log.Verbose("AbstractRestClient.DeleteAsync", "LEAVE"); + throw; + } catch (Exception ex) { - Log.Error("DeleteAsync", $"Exception: {ex}"); - Log.Verbose("DeleteAsync", "LEAVE"); + Log.Error("DeleteAsync", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("DeleteAsync", $"Excepton: {ex}"); + Log.Verbose("AbstractRestClient.DeleteAsync", "LEAVE"); throw; } } @@ -570,7 +633,7 @@ public virtual async Task DeleteAsync(string uriSegment, CancellationToken public virtual async Task DeleteAsync(string uriSegment, S? parameter, CancellationTokenSource? cancellationToken = null, Dictionary? addons = null, Dictionary? headers = null) { - Log.Verbose("DeleteAsync", "ENTER"); + Log.Verbose("AbstractRestClient.DeleteAsync", "ENTER"); Log.Debug("DeleteAsync", $"uriSegment: {uriSegment}"); Log.Debug("DeleteAsync", $"parameter: {parameter}"); Log.Debug("DeleteAsync", $"addons: {addons}"); @@ -605,14 +668,22 @@ public virtual async Task DeleteAsync(string uriSegment, S? parameter, var result = await HttpRequestUtil.DeserializeAsync(response); Log.Debug("DeleteAsync", $"Succeeded. Result: {result}"); - Log.Verbose("DeleteAsync", "LEAVE"); + Log.Verbose("AbstractRestClient.DeleteAsync", "LEAVE"); return result; } + catch (OperationCanceledException ex) + { + Log.Information("DeleteAsync", "Task was cancelled."); + Log.Verbose("DeleteAsync", $"Connect cancelled. Info: {ex}"); + Log.Verbose("AbstractRestClient.DeleteAsync", "LEAVE"); + throw; + } catch (Exception ex) { - Log.Error("DeleteAsync", $"Exception: {ex}"); - Log.Verbose("DeleteAsync", "LEAVE"); + Log.Error("DeleteAsync", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("DeleteAsync", $"Excepton: {ex}"); + Log.Verbose("AbstractRestClient.DeleteAsync", "LEAVE"); throw; } } diff --git a/Deepgram/Clients/Live/v1/Client.cs b/Deepgram/Clients/Live/v1/Client.cs index 7d763f5f..2c590644 100644 --- a/Deepgram/Clients/Live/v1/Client.cs +++ b/Deepgram/Clients/Live/v1/Client.cs @@ -59,7 +59,7 @@ public Client(string? apiKey = null, DeepgramWsClientOptions? options = null) /// /// Options to use when transcribing audio /// The task object representing the asynchronous operation. - public async Task Connect(LiveSchema options, CancellationTokenSource? cancellationToken = null, Dictionary? addons = null, + public async Task Connect(LiveSchema options, CancellationTokenSource? cancelToken = null, Dictionary? addons = null, Dictionary? headers = null) { Log.Verbose("LiveClient.Connect", "ENTER"); @@ -72,9 +72,16 @@ public async Task Connect(LiveSchema options, CancellationTokenSource? cancellat // client has already connected var exStr = "Client has already been initialized"; Log.Error("Connect", exStr); + Log.Verbose("LiveClient.Connect", "LEAVE"); throw new InvalidOperationException(exStr); } + if (cancelToken == null) + { + Log.Information("Connect", "Using default connect cancellation token"); + cancelToken = new CancellationTokenSource(Constants.DefaultConnectTimeout); + } + // create client _clientWebSocket = new ClientWebSocket(); @@ -104,16 +111,8 @@ public async Task Connect(LiveSchema options, CancellationTokenSource? cancellat } } - // cancelation token - if (cancellationToken != null) - { - Log.Information("Connect", "Using provided cancellation token"); - _cancellationTokenSource = cancellationToken; - } else - { - Log.Information("Connect", "Using default cancellation token"); - _cancellationTokenSource = new CancellationTokenSource(); - } + // internal cancelation token for internal threads + _cancellationTokenSource = new CancellationTokenSource(); try { @@ -121,7 +120,7 @@ public async Task Connect(LiveSchema options, CancellationTokenSource? cancellat Log.Debug("Connect", $"uri: {_uri}"); Log.Debug("Connect", "Connecting to Deepgram API..."); - await _clientWebSocket.ConnectAsync(_uri, _cancellationTokenSource.Token).ConfigureAwait(false); + await _clientWebSocket.ConnectAsync(_uri, cancelToken.Token).ConfigureAwait(false); Log.Debug("Connect", "Starting Sender Thread..."); StartSenderBackgroundThread(); @@ -145,10 +144,20 @@ public async Task Connect(LiveSchema options, CancellationTokenSource? cancellat } Log.Debug("Connect", "Connect Succeeded"); + Log.Verbose("LiveClient.Connect", "LEAVE"); + } + catch (TaskCanceledException ex) + { + Log.Debug("Connect", "Connect cancelled."); + Log.Verbose("Connect", $"Connect cancelled. Info: {ex}"); + Log.Verbose("LiveClient.Connect", "LEAVE"); } catch (Exception ex) { - Log.Error("Connect", $"Excepton: {ex}"); + Log.Error("Connect", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("Connect", $"Excepton: {ex}"); + Log.Verbose("LiveClient.Connect", "LEAVE"); + throw; } void StartSenderBackgroundThread() => _ = Task.Factory.StartNew( @@ -162,8 +171,6 @@ void StartReceiverBackgroundThread() => _ = Task.Factory.StartNew( void StartKeepAliveBackgroundThread() => _ = Task.Factory.StartNew( _ => ProcessKeepAlive(), TaskCreationOptions.LongRunning); - - Log.Verbose("LiveClient.Connect", "LEAVE"); } #region Subscribe Event @@ -327,13 +334,14 @@ internal void EnqueueSendMessage(WebSocketMessage message) } catch (Exception ex) { - Log.Error("EnqueueSendMessage", $"Excepton: {ex}"); + Log.Error("EnqueueSendMessage", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("EnqueueSendMessage", $"Excepton: {ex}"); } } internal async Task ProcessSendQueue() { - Log.Verbose("ProcessSendQueue", "ENTER"); + Log.Verbose("LiveClient.ProcessSendQueue", "ENTER"); if (_clientWebSocket == null) { @@ -348,6 +356,12 @@ internal async Task ProcessSendQueue() { while (await _sendChannel.Reader.WaitToReadAsync(_cancellationTokenSource.Token)) { + if (_cancellationTokenSource.Token.IsCancellationRequested) + { + Log.Information("ProcessSendQueue", "KeepAliveThread cancelled"); + break; + } + Log.Verbose("ProcessSendQueue", "Reading message of queue..."); while (_sendChannel.Reader.TryRead(out var message)) { @@ -361,28 +375,26 @@ internal async Task ProcessSendQueue() } } - Log.Verbose("ProcessSendQueue", "Succeeded"); - Log.Verbose("ProcessSendQueue", "LEAVE"); - return; + Log.Verbose("ProcessSendQueue", "Exit"); + Log.Verbose("LiveClient.ProcessSendQueue", "LEAVE"); } catch (OperationCanceledException ex) { - Log.Debug("ProcessSendQueue", $"SendThread cancelled."); + Log.Debug("ProcessSendQueue", "SendThread cancelled."); Log.Verbose("ProcessSendQueue", $"SendThread cancelled. Info: {ex}"); + Log.Verbose("LiveClient.ProcessSendQueue", "LEAVE"); } catch (Exception ex) { - Log.Error("ProcessSendQueue", $"Excepton: {ex}"); - Log.Verbose("ProcessSendQueue", "LEAVE"); - throw; + Log.Error("ProcessSendQueue", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("ProcessSendQueue", $"Excepton: {ex}"); + Log.Verbose("LiveClient.ProcessSendQueue", "LEAVE"); } - - Log.Verbose("ProcessSendQueue", "LEAVE"); } internal async void ProcessKeepAlive() { - Log.Verbose("ProcessKeepAlive", "ENTER"); + Log.Verbose("LiveClient.ProcessKeepAlive", "ENTER"); try { @@ -406,28 +418,26 @@ internal async void ProcessKeepAlive() } } - Log.Verbose("ProcessKeepAlive", "Exiting"); - Log.Verbose("ProcessKeepAlive", "LEAVE"); - return; + Log.Verbose("ProcessKeepAlive", "Exit"); + Log.Verbose("LiveClient.ProcessKeepAlive", "LEAVE"); } catch (TaskCanceledException ex) { - Log.Debug("ProcessKeepAlive", $"KeepAliveThread cancelled."); + Log.Debug("ProcessKeepAlive", "KeepAliveThread cancelled."); Log.Verbose("ProcessKeepAlive", $"KeepAliveThread cancelled. Info: {ex}"); + Log.Verbose("LiveClient.ProcessKeepAlive", "LEAVE"); } catch (Exception ex) { - Log.Error("ProcessKeepAlive", $"Excepton: {ex}"); - Log.Verbose("ProcessKeepAlive", "LEAVE"); - throw; + Log.Error("ProcessKeepAlive", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("ProcessKeepAlive", $"Excepton: {ex}"); + Log.Verbose("LiveClient.ProcessKeepAlive", "LEAVE"); } - - Log.Verbose("ProcessKeepAlive", "LEAVE"); } internal async Task ProcessReceiveQueue() { - Log.Verbose("ProcessReceiveQueue", "ENTER"); + Log.Verbose("LiveClient.ProcessReceiveQueue", "ENTER"); while (_clientWebSocket?.State == WebSocketState.Open) { @@ -436,7 +446,9 @@ internal async Task ProcessReceiveQueue() if (_cancellationTokenSource.Token.IsCancellationRequested) { Log.Information("ProcessReceiveQueue", "ReceiveThread cancelled"); - break; + await Stop(); + Log.Verbose("ProcessReceiveQueue", "LEAVE"); + return; } var buffer = new ArraySegment(new byte[Constants.BufferSize]); @@ -456,50 +468,46 @@ internal async Task ProcessReceiveQueue() ); } while (!result.EndOfMessage); - if (result.MessageType == WebSocketMessageType.Close) + if (result.MessageType != WebSocketMessageType.Close) { - Log.Information("ProcessReceiveQueue", "Received Close message"); - break; + Log.Verbose("ProcessReceiveQueue", $"Received message: {result} / {ms}"); + ProcessDataReceived(result, ms); } - - Log.Verbose("ProcessReceiveQueue", $"Received message: {result} / {ms}"); - ProcessDataReceived(result, ms); } if (result.MessageType == WebSocketMessageType.Close) { - Log.Information("ProcessReceiveQueue", "Received WebSocket Close"); + Log.Information("ProcessReceiveQueue", "Received WebSocket Close. Trigger cancel..."); await Stop(); - break; + Log.Verbose("ProcessReceiveQueue", "LEAVE"); + return; } } catch (TaskCanceledException ex) { - Log.Debug("ProcessReceiveQueue", $"ReceiveThread cancelled."); + Log.Debug("ProcessReceiveQueue", "ReceiveThread cancelled."); Log.Verbose("ProcessReceiveQueue", $"ReceiveThread cancelled. Info: {ex}"); + Log.Verbose("LiveClient.ProcessReceiveQueue", "LEAVE"); } catch (Exception ex) { - Log.Error("ProcessReceiveQueue", $"Excepton: {ex}"); - Log.Verbose("ProcessReceiveQueue", "LEAVE"); - throw; + Log.Error("ProcessReceiveQueue", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("ProcessReceiveQueue", $"Excepton: {ex}"); + Log.Verbose("LiveClient.ProcessReceiveQueue", "LEAVE"); } } - - Log.Verbose("ProcessReceiveQueue", "Succeeded"); - Log.Verbose("ProcessReceiveQueue", "LEAVE"); } internal void ProcessDataReceived(WebSocketReceiveResult result, MemoryStream ms) { - Log.Verbose("ProcessDataReceived", "ENTER"); + Log.Verbose("LiveClient.ProcessDataReceived", "ENTER"); ms.Seek(0, SeekOrigin.Begin); if (result.MessageType != WebSocketMessageType.Text) { Log.Warning("ProcessDataReceived", "Received a text message. This is not supported."); - Log.Verbose("ProcessDataReceived", "LEAVE"); + Log.Verbose("LiveClient.ProcessDataReceived", "LEAVE"); return; } @@ -507,7 +515,7 @@ internal void ProcessDataReceived(WebSocketReceiveResult result, MemoryStream ms if (response == null) { Log.Warning("ProcessDataReceived", "Response is null"); - Log.Verbose("ProcessDataReceived", "LEAVE"); + Log.Verbose("LiveClient.ProcessDataReceived", "LEAVE"); return; } @@ -664,110 +672,110 @@ internal void ProcessDataReceived(WebSocketReceiveResult result, MemoryStream ms } Log.Debug("ProcessDataReceived", "Succeeded"); - Log.Verbose("ProcessDataReceived", "LEAVE"); - return; + Log.Verbose("LiveClient.ProcessDataReceived", "LEAVE"); } catch (JsonException ex) { - Log.Error("ProcessDataReceived", $"JsonException: {ex}"); + Log.Error("ProcessDataReceived", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("ProcessDataReceived", $"Excepton: {ex}"); + Log.Verbose("LiveClient.ProcessDataReceived", "LEAVE"); } catch (Exception ex) { - Log.Error("ProcessDataReceived", $"Excepton: {ex}"); + Log.Error("ProcessDataReceived", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("ProcessDataReceived", $"Excepton: {ex}"); + Log.Verbose("LiveClient.ProcessDataReceived", "LEAVE"); } - - Log.Verbose("ProcessDataReceived", "LEAVE"); } /// /// Closes the Web Socket connection to the Deepgram API /// /// The task object representing the asynchronous operation. - public async Task Stop(CancellationTokenSource? cancellationToken = null) + public async Task Stop(CancellationTokenSource? cancelToken = null) { - Log.Verbose("Stop", "ENTER"); - - var cancelToken = _cancellationTokenSource.Token; - if (cancellationToken != null) - { - Log.Verbose("Stop", "Using provided cancellation token"); - cancelToken = cancellationToken.Token; - } + Log.Verbose("LiveClient.Stop", "ENTER"); // client is already disposed if (_clientWebSocket == null) { - Log.Warning("Stop", "Client has already been disposed"); - Log.Verbose("Stop", "LEAVE"); + Log.Information("Stop", "Client has already been disposed"); + Log.Verbose("LiveClient.Stop", "LEAVE"); return; } - // send the close message and flush transcription message - try { + if (cancelToken == null) + { + Log.Information("Stop", "Using default disconnect cancellation token"); + cancelToken = new CancellationTokenSource(Constants.DefaultConnectTimeout); + } + + try + { + // cancel the internal token to stop all threads + if (_cancellationTokenSource != null) + { + Log.Debug("Stop", "Cancelling native token..."); + _cancellationTokenSource.Cancel(); + } + + // if websocket is open, send a close message if (_clientWebSocket!.State == WebSocketState.Open) { Log.Debug("Stop", "Sending Close message..."); - // send a close to Deepgram lock (_mutexSend) { - _clientWebSocket.SendAsync(new ArraySegment([]), WebSocketMessageType.Binary, true, cancelToken) + _clientWebSocket.SendAsync(new ArraySegment([0]), WebSocketMessageType.Binary, true, cancelToken.Token) .ConfigureAwait(false); } + } - // send a CloseResponse event - if (_closeReceived != null) - { - Log.Debug("Stop", "Sending CloseResponse event..."); - var data = new CloseResponse(); - data.Type = LiveType.Close; - _closeReceived.Invoke(null, data); - } + // send a CloseResponse event + if (_closeReceived != null) + { + Log.Debug("Stop", "Sending CloseResponse event..."); + var data = new CloseResponse(); + data.Type = LiveType.Close; + InvokeParallel(_closeReceived, data); } // attempt to stop the connection - if (_clientWebSocket!.State != WebSocketState.Closed) + if (_clientWebSocket!.State != WebSocketState.Closed && _clientWebSocket!.State != WebSocketState.Aborted) { Log.Debug("Stop", "Closing WebSocket connection..."); - await _clientWebSocket.CloseOutputAsync( - WebSocketCloseStatus.NormalClosure, - string.Empty, - cancelToken) + await _clientWebSocket.CloseOutputAsync(WebSocketCloseStatus.NormalClosure, string.Empty, cancelToken.Token) .ConfigureAwait(false); } - // Always request cancellation to the local token source, if some function has been called without a token - if (cancellationToken != null) - { - Log.Debug("Stop", "Cancelling provided token..."); - cancellationToken.Cancel(); - } - - Log.Debug("Stop", "Disposing WebSocket connection..."); + // clean up internal token if (_cancellationTokenSource != null) { - Log.Debug("Stop", "Cancelling native token..."); - _cancellationTokenSource.Cancel(); + Log.Debug("Stop", "Disposing internal token..."); _cancellationTokenSource.Dispose(); _cancellationTokenSource = null; } + // release the socket + Log.Debug("Stop", "Disposing WebSocket socket..."); + _clientWebSocket = null; + Log.Debug("Stop", "Succeeded"); - Log.Verbose("Stop", "LEAVE"); - return; + Log.Verbose("LiveClient.Stop", "LEAVE"); } catch (TaskCanceledException ex) { - Log.Debug("Stop", $"Stop cancelled."); + Log.Debug("Stop", "Stop cancelled."); Log.Verbose("Stop", $"Stop cancelled. Info: {ex}"); + Log.Verbose("LiveClient.Stop", "LEAVE"); } catch (Exception ex) { - Log.Error("Stop", $"Excepton: {ex}"); + Log.Error("Stop", $"{ex.GetType()} thrown {ex.Message}"); + Log.Verbose("Stop", $"Excepton: {ex}"); + Log.Verbose("LiveClient.Stop", "LEAVE"); + throw; } - - _clientWebSocket = null; - Log.Verbose("Stop", "LEAVE"); } #region Helpers diff --git a/Deepgram/Clients/Live/v1/Constants.cs b/Deepgram/Clients/Live/v1/Constants.cs index 8de49ed7..957332c7 100644 --- a/Deepgram/Clients/Live/v1/Constants.cs +++ b/Deepgram/Clients/Live/v1/Constants.cs @@ -11,5 +11,8 @@ public static class Constants { // WS buffer size public const int BufferSize = 1024 * 16; + + // Default timeout for connect/disconnect + public const int DefaultConnectTimeout = 5000; } diff --git a/Deepgram/Logger/Constants.cs b/Deepgram/Logger/Constants.cs index 48fc9f3f..b3b13c80 100644 --- a/Deepgram/Logger/Constants.cs +++ b/Deepgram/Logger/Constants.cs @@ -44,4 +44,9 @@ public enum LogLevel /// occurs. /// Fatal = Serilog.Events.LogEventLevel.Fatal, + + /// + /// Disable logging... Do so at your own peril. + /// + Disable = Serilog.Events.LogEventLevel.Fatal + 1 } diff --git a/Deepgram/Logger/Log.cs b/Deepgram/Logger/Log.cs index deaaff52..80cf9839 100644 --- a/Deepgram/Logger/Log.cs +++ b/Deepgram/Logger/Log.cs @@ -3,6 +3,7 @@ // SPDX-License-Identifier: MIT using Serilog; +using Serilog.Events; namespace Deepgram.Logger; @@ -21,17 +22,25 @@ static Log() /// public static Serilog.ILogger Initialize(LogLevel level = LogLevel.Information, string? filename = "log.txt") { + if (level == LogLevel.Disable) + { + instance = new LoggerConfiguration() + .MinimumLevel.Is(((LogEventLevel)1 + (int)LogEventLevel.Fatal)) + .WriteTo.Console(outputTemplate: "{Timestamp:yyyy-MM-dd HH:mm:ss.fff} [{Level}] {Message}{NewLine}{Exception}") + .CreateLogger(); + return instance; + } if (filename != null) { instance = new LoggerConfiguration() - .MinimumLevel.Is((Serilog.Events.LogEventLevel) level) + .MinimumLevel.Is((LogEventLevel) level) .WriteTo.Console(outputTemplate: "{Timestamp:yyyy-MM-dd HH:mm:ss.fff} [{Level}] {Message}{NewLine}{Exception}") .WriteTo.File(filename, outputTemplate: "{Timestamp:yyyy-MM-dd HH:mm:ss.fff} [{Level}] {Message}{NewLine}{Exception}") .CreateLogger(); return instance; } instance = new LoggerConfiguration() - .MinimumLevel.Is((Serilog.Events.LogEventLevel)level) + .MinimumLevel.Is((LogEventLevel)level) .WriteTo.Console(outputTemplate: "{Timestamp:yyyy-MM-dd HH:mm:ss.fff} [{Level}] {Message}{NewLine}{Exception}") .CreateLogger(); return instance; diff --git a/examples/streaming/microphone/Program.cs b/examples/streaming/microphone/Program.cs index e4cca38d..e0632dc2 100644 --- a/examples/streaming/microphone/Program.cs +++ b/examples/streaming/microphone/Program.cs @@ -18,9 +18,9 @@ static async Task Main(string[] args) { // Initialize Library with default logging // Normal logging is "Info" level - //Deepgram.Library.Initialize(); + Deepgram.Library.Initialize(); // OR very chatty logging - Deepgram.Library.Initialize(LogLevel.Debug); // LogLevel.Default, LogLevel.Debug, LogLevel.Verbose + //Deepgram.Library.Initialize(LogLevel.Debug); // LogLevel.Default, LogLevel.Debug, LogLevel.Verbose Deepgram.Microphone.Library.Initialize(); Console.WriteLine("\n\nPress any key to stop and exit...\n\n\n"); @@ -34,7 +34,7 @@ static async Task Main(string[] args) // Subscribe to the EventResponseReceived event liveClient.Subscribe(new EventHandler((sender, e) => { - Console.WriteLine($"----> {e.Type} received"); + Console.WriteLine($"\n\n----> {e.Type} received"); })); liveClient.Subscribe(new EventHandler((sender, e) => { @@ -48,7 +48,7 @@ static async Task Main(string[] args) } // Console.WriteLine("Transcription received: " + JsonSerializer.Serialize(e.Transcription)); - Console.WriteLine($"\n\n\n----> Speaker: {e.Channel.Alternatives[0].Transcript}\n\n\n"); + Console.WriteLine($"----> Speaker: {e.Channel.Alternatives[0].Transcript}"); })); liveClient.Subscribe(new EventHandler((sender, e) => { @@ -71,9 +71,6 @@ static async Task Main(string[] args) Console.WriteLine($"----> { e.Type} received. Error: {e.Message}"); })); - // my own cancellation token - //var cancellationToken = new CancellationTokenSource(); - // Start the connection var liveSchema = new LiveSchema() { @@ -86,7 +83,6 @@ static async Task Main(string[] args) UtteranceEnd = "1000", VadEvents = true, }; - //await liveClient.Connect(liveSchema, cancellationToken); await liveClient.Connect(liveSchema); // Microphone streaming @@ -96,14 +92,9 @@ static async Task Main(string[] args) // Wait for the user to press a key Console.ReadKey(); - Console.WriteLine("Stopping the microphone streaming..."); + // Stop the microphone microphone.Stop(); - //// START: test an external cancellation - //cancellationToken.Cancel(); - //Thread.Sleep(10000); // wait 10 seconds to cancel externally - //// END: test an external cancellation - // Stop the connection await liveClient.Stop(); diff --git a/tests/expected_failures/rest/bad_host/BadHost.csproj b/tests/expected_failures/rest/bad_host/BadHost.csproj new file mode 100644 index 00000000..39bfa63e --- /dev/null +++ b/tests/expected_failures/rest/bad_host/BadHost.csproj @@ -0,0 +1,18 @@ + + + + Exe + net6.0 + enable + enable + + + + + + + + + + + diff --git a/tests/expected_failures/rest/bad_host/Program.cs b/tests/expected_failures/rest/bad_host/Program.cs new file mode 100644 index 00000000..04f0114b --- /dev/null +++ b/tests/expected_failures/rest/bad_host/Program.cs @@ -0,0 +1,49 @@ +// Copyright 2024 Deepgram .NET SDK contributors. All Rights Reserved. +// Use of this source code is governed by a MIT license that can be found in the LICENSE file. +// SPDX-License-Identifier: MIT + +using System.Text.Json; + +using Deepgram.Models.PreRecorded.v1; +using Deepgram.Logger; +using Deepgram.Models.Authenticate.v1; + +namespace SampleApp +{ + class Program + { + static async Task Main(string[] args) + { + // Normal logging is "Info" level + Library.Initialize(); + // OR very chatty logging + //Library.Initialize(LogLevel.Debug); // LogLevel.Default, LogLevel.Debug, LogLevel.Verbose + + // Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key + var clientOptions = new DeepgramHttpClientOptions(null, "http://127.0.0.1"); + var deepgramClient = new PreRecordedClient("", clientOptions); + + try + { + var response = await deepgramClient.TranscribeUrl( + new UrlSource("https://static.deepgram.com/examples/Bueller-Life-moves-pretty-fast.wav"), + new PrerecordedSchema() + { + Model = "nova-2", + }); + + Console.WriteLine(JsonSerializer.Serialize(response)); + } + catch (Exception ex) + { + Console.WriteLine($"\n\nException thrown: {ex.Message}.\n\n"); + } + + Console.WriteLine("Press any key to exit."); + Console.ReadKey(); + + // Terminate Libraries + Deepgram.Library.Terminate(); + } + } +} diff --git a/tests/expected_failures/rest/trigger_cancel/Program.cs b/tests/expected_failures/rest/trigger_cancel/Program.cs new file mode 100644 index 00000000..59ce96b5 --- /dev/null +++ b/tests/expected_failures/rest/trigger_cancel/Program.cs @@ -0,0 +1,51 @@ +// Copyright 2024 Deepgram .NET SDK contributors. All Rights Reserved. +// Use of this source code is governed by a MIT license that can be found in the LICENSE file. +// SPDX-License-Identifier: MIT + +using System.Text.Json; + +using Deepgram.Models.PreRecorded.v1; +using Deepgram.Logger; + +namespace SampleApp +{ + class Program + { + static async Task Main(string[] args) + { + // Normal logging is "Info" level + Library.Initialize(); + // OR very chatty logging + //Library.Initialize(LogLevel.Debug); // LogLevel.Default, LogLevel.Debug, LogLevel.Verbose + + // Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key + var deepgramClient = new PreRecordedClient(); + + // intentionally cancel the request after 250ms + CancellationTokenSource cancelToken = new CancellationTokenSource(250); + + try + { + var response = await deepgramClient.TranscribeUrl( + new UrlSource("https://static.deepgram.com/examples/Bueller-Life-moves-pretty-fast.wav"), + new PrerecordedSchema() + { + Model = "nova-2", + }, + cancelToken); + + Console.WriteLine(JsonSerializer.Serialize(response)); + } + catch (OperationCanceledException) + { + Console.WriteLine("\n\nRequest was intentionally cancelled.\n\n"); + } + + Console.WriteLine("Press any key to exit."); + Console.ReadKey(); + + // Terminate Libraries + Deepgram.Library.Terminate(); + } + } +} diff --git a/tests/expected_failures/rest/trigger_cancel/TriggerCancel.csproj b/tests/expected_failures/rest/trigger_cancel/TriggerCancel.csproj new file mode 100644 index 00000000..39bfa63e --- /dev/null +++ b/tests/expected_failures/rest/trigger_cancel/TriggerCancel.csproj @@ -0,0 +1,18 @@ + + + + Exe + net6.0 + enable + enable + + + + + + + + + + + diff --git a/tests/expected_failures/exercise_timeout/ExerciseTimeout.csproj b/tests/expected_failures/websocket/exercise_timeout/ExerciseTimeout.csproj similarity index 82% rename from tests/expected_failures/exercise_timeout/ExerciseTimeout.csproj rename to tests/expected_failures/websocket/exercise_timeout/ExerciseTimeout.csproj index c1f1063c..39bfa63e 100644 --- a/tests/expected_failures/exercise_timeout/ExerciseTimeout.csproj +++ b/tests/expected_failures/websocket/exercise_timeout/ExerciseTimeout.csproj @@ -8,7 +8,7 @@ - + diff --git a/tests/expected_failures/exercise_timeout/Program.cs b/tests/expected_failures/websocket/exercise_timeout/Program.cs similarity index 94% rename from tests/expected_failures/exercise_timeout/Program.cs rename to tests/expected_failures/websocket/exercise_timeout/Program.cs index 7fedeb53..0a8a5728 100644 --- a/tests/expected_failures/exercise_timeout/Program.cs +++ b/tests/expected_failures/websocket/exercise_timeout/Program.cs @@ -12,9 +12,9 @@ class Program static async Task Main(string[] args) { // Normal logging is "Info" level - Library.Initialize(); + //Library.Initialize(); // OR very chatty logging - //Library.Initialize(LogLevel.Debug); // LogLevel.Default, LogLevel.Debug, LogLevel.Verbose + Library.Initialize(LogLevel.Debug); // LogLevel.Default, LogLevel.Debug, LogLevel.Verbose // Set "DEEPGRAM_API_KEY" environment variable to your Deepgram API Key var liveClient = new LiveClient();