Skip to content

Commit

Permalink
add TaskCompletionSource example
Browse files Browse the repository at this point in the history
  • Loading branch information
grantwinney committed Dec 6, 2022
1 parent 9856109 commit bb705ed
Show file tree
Hide file tree
Showing 23 changed files with 1,067 additions and 0 deletions.
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ So to all my fellow devs that find themselves supporting the old coldness, let's
## Threading

* Using Async, Await, and Task to keep the WinForms UI responsive ([blog post](https://grantwinney.com/using-async-await-and-task-to-keep-the-winforms-ui-more-responsive), [source code](https://github.com/grantwinney/SurvivingWinForms/tree/master/Threading/AsyncAwait))
* Turning a BackgroundWorker into a Task with TaskCompletionSource ([blog post](https://grantwinney.com/turning-a-backgroundworker-into-a-task-with-taskcompletionsource), [source code](https://github.com/grantwinney/SurvivingWinForms/tree/master/Threading/TaskCompletion))

## Web

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
using Newtonsoft.Json;
using System.Collections.Generic;

namespace LegacySpaceLibrary
{
public class ISSAstronauts
{
[JsonProperty("people")]
public List<Astronaut> People { get; private set; }

[JsonProperty("number")]
public int Number { get; private set; }

[JsonProperty("message")]
public string Message { get; private set; }
}

public class Astronaut
{
[JsonProperty("name")]
public string Name { get; private set; }

[JsonProperty("craft")]
public string Craft { get; private set; }
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
using Newtonsoft.Json;

namespace LegacySpaceLibrary
{
public class ISSLocation
{
[JsonProperty("message")]
public string Message { get; private set; }

[JsonProperty("iss_position")]
public ISSPosition Position { get; private set; }

[JsonProperty("timestamp")]
public int Timestamp { get; private set; }
}

public class ISSPosition
{
[JsonProperty("latitude")]
public string Latitude { get; private set; }

[JsonProperty("longitude")]
public string Longitude { get; private set; }
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
<PropertyGroup>
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
<ProjectGuid>{61D76390-15D1-4A0F-9FB7-FEDE264B39C0}</ProjectGuid>
<OutputType>Library</OutputType>
<AppDesignerFolder>Properties</AppDesignerFolder>
<RootNamespace>LegacySpaceLibrary</RootNamespace>
<AssemblyName>LegacySpaceLibrary</AssemblyName>
<TargetFrameworkVersion>v2.0</TargetFrameworkVersion>
<FileAlignment>512</FileAlignment>
<Deterministic>true</Deterministic>
<TargetFrameworkProfile />
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<DebugSymbols>true</DebugSymbols>
<DebugType>full</DebugType>
<Optimize>false</Optimize>
<OutputPath>bin\Debug\</OutputPath>
<DefineConstants>DEBUG;TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<DebugType>pdbonly</DebugType>
<Optimize>true</Optimize>
<OutputPath>bin\Release\</OutputPath>
<DefineConstants>TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<ItemGroup>
<Reference Include="Newtonsoft.Json, Version=13.0.0.0, Culture=neutral, PublicKeyToken=30ad4fe6b2a6aeed, processorArchitecture=MSIL">
<HintPath>..\packages\Newtonsoft.Json.13.0.2\lib\net20\Newtonsoft.Json.dll</HintPath>
</Reference>
<Reference Include="System" />
<Reference Include="System.Data" />
<Reference Include="System.Xml" />
</ItemGroup>
<ItemGroup>
<Compile Include="Entities\ISSAstronauts.cs" />
<Compile Include="Entities\ISSLocation.cs" />
<Compile Include="OldSpaceLibrary.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
</ItemGroup>
<ItemGroup>
<None Include="packages.config" />
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
</Project>
93 changes: 93 additions & 0 deletions Threading/TaskCompletion/LegacySpaceLibrary/OldSpaceLibrary.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,93 @@
using Newtonsoft.Json;
using System.Collections.Generic;
using System.ComponentModel;
using System.IO;
using System.Net;
using System.Threading;

namespace LegacySpaceLibrary
{
public class OldSpaceLibrary
{
public readonly BackgroundWorker Worker = new BackgroundWorker { WorkerReportsProgress = true, WorkerSupportsCancellation = true };

public ISSLocation ISSLocation { get; private set; }
public ISSAstronauts ISSAstronauts { get; private set; }

public OldSpaceLibrary()
{
Worker.DoWork += Worker_DoWork;
Worker.RunWorkerCompleted += Worker_RunWorkerCompleted;
}

public void GetData()
{
if (Worker.IsBusy)
return;

ISSLocation = null;
ISSAstronauts = null;

Worker.RunWorkerAsync();
}

private void Worker_DoWork(object sender, DoWorkEventArgs e)
{
Worker.ReportProgress(0, "Requesting data...");

Thread.Sleep(2000);
if (Worker.CancellationPending)
{
e.Cancel = true;
return;
}

var issLocation = JsonConvert.DeserializeObject<ISSLocation>(
GetDataAsString("http://api.open-notify.org/iss-now.json"));
Worker.ReportProgress(25, "1/2 requests done.");

Thread.Sleep(2000);
if (Worker.CancellationPending)
{
e.Cancel = true;
return;
}

var issAstronauts = JsonConvert.DeserializeObject<ISSAstronauts>(
GetDataAsString("http://api.open-notify.org/astros.json"));
issAstronauts.People.RemoveAll(x => x.Craft != "ISS");
Worker.ReportProgress(50, "2/2 requests done.");
Worker.ReportProgress(75, "Processing data...");

Thread.Sleep(2000);
if (Worker.CancellationPending)
{
e.Cancel = true;
return;
}

Worker.ReportProgress(100, "Processing complete!");

e.Result = new List<object> { issLocation, issAstronauts };
}

private string GetDataAsString(string endpoint)
{
var request = WebRequest.Create(endpoint);
using (var response = (HttpWebResponse)request.GetResponse())
using (var dataStream = response.GetResponseStream())
using (var reader = new StreamReader(dataStream))
return reader.ReadToEnd();
}

private void Worker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
if (!e.Cancelled && e.Error == null)
{
var data = (List<object>)e.Result;
ISSLocation = (ISSLocation)data[0];
ISSAstronauts = (ISSAstronauts)data[1];
}
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;

// General Information about an assembly is controlled through the following
// set of attributes. Change these attribute values to modify the information
// associated with an assembly.
[assembly: AssemblyTitle("LegacySpaceLibrary")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("LegacySpaceLibrary")]
[assembly: AssemblyCopyright("Copyright © 2022")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]

// Setting ComVisible to false makes the types in this assembly not visible
// to COM components. If you need to access a type in this assembly from
// COM, set the ComVisible attribute to true on that type.
[assembly: ComVisible(false)]

// The following GUID is for the ID of the typelib if this project is exposed to COM
[assembly: Guid("61d76390-15d1-4a0f-9fb7-fede264b39c0")]

// Version information for an assembly consists of the following four values:
//
// Major Version
// Minor Version
// Build Number
// Revision
//
// You can specify all the values or you can default the Build and Revision Numbers
// by using the '*' as shown below:
// [assembly: AssemblyVersion("1.0.*")]
[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]
4 changes: 4 additions & 0 deletions Threading/TaskCompletion/LegacySpaceLibrary/packages.config
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<packages>
<package id="Newtonsoft.Json" version="13.0.2" targetFramework="net20" />
</packages>
31 changes: 31 additions & 0 deletions Threading/TaskCompletion/TaskCompletion.sln
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@

Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio Version 17
VisualStudioVersion = 17.4.33110.190
MinimumVisualStudioVersion = 10.0.40219.1
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TaskCompletion", "TaskCompletion\TaskCompletion.csproj", "{8DEAEDBE-C6D1-4578-BF8C-36DDB695EB44}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "LegacySpaceLibrary", "LegacySpaceLibrary\LegacySpaceLibrary.csproj", "{61D76390-15D1-4A0F-9FB7-FEDE264B39C0}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Release|Any CPU = Release|Any CPU
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{8DEAEDBE-C6D1-4578-BF8C-36DDB695EB44}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{8DEAEDBE-C6D1-4578-BF8C-36DDB695EB44}.Debug|Any CPU.Build.0 = Debug|Any CPU
{8DEAEDBE-C6D1-4578-BF8C-36DDB695EB44}.Release|Any CPU.ActiveCfg = Release|Any CPU
{8DEAEDBE-C6D1-4578-BF8C-36DDB695EB44}.Release|Any CPU.Build.0 = Release|Any CPU
{61D76390-15D1-4A0F-9FB7-FEDE264B39C0}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{61D76390-15D1-4A0F-9FB7-FEDE264B39C0}.Debug|Any CPU.Build.0 = Debug|Any CPU
{61D76390-15D1-4A0F-9FB7-FEDE264B39C0}.Release|Any CPU.ActiveCfg = Release|Any CPU
{61D76390-15D1-4A0F-9FB7-FEDE264B39C0}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {A0D4E38A-AA91-4090-819F-1353C4420CA0}
EndGlobalSection
EndGlobal
6 changes: 6 additions & 0 deletions Threading/TaskCompletion/TaskCompletion/App.config
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.8"/>
</startup>
</configuration>
22 changes: 22 additions & 0 deletions Threading/TaskCompletion/TaskCompletion/Program.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
using System;
using System.Windows.Forms;

namespace TaskCompletion
{
static class Program
{
/// <summary>
/// The main entry point for the application.
/// </summary>
[STAThread]
static void Main()
{
Application.EnableVisualStyles();
Application.SetHighDpiMode(HighDpiMode.SystemAware);
Application.SetCompatibleTextRenderingDefault(false);

//Application.Run(new frmCallBackgroundWorker());
Application.Run(new frmCallBackgroundWorkerAsTask());
}
}
}
36 changes: 36 additions & 0 deletions Threading/TaskCompletion/TaskCompletion/Properties/AssemblyInfo.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;

// General Information about an assembly is controlled through the following
// set of attributes. Change these attribute values to modify the information
// associated with an assembly.
[assembly: AssemblyTitle("SurvivingWinForms")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("SurvivingWinForms")]
[assembly: AssemblyCopyright("Copyright © 2021")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]

// Setting ComVisible to false makes the types in this assembly not visible
// to COM components. If you need to access a type in this assembly from
// COM, set the ComVisible attribute to true on that type.
[assembly: ComVisible(false)]

// The following GUID is for the ID of the typelib if this project is exposed to COM
[assembly: Guid("8deaedbe-c6d1-4578-bf8c-36ddb695eb44")]

// Version information for an assembly consists of the following four values:
//
// Major Version
// Minor Version
// Build Number
// Revision
//
// You can specify all the values or you can default the Build and Revision Numbers
// by using the '*' as shown below:
// [assembly: AssemblyVersion("1.0.*")]
[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]
Loading

0 comments on commit bb705ed

Please sign in to comment.