Skip to content

Commit

Permalink
Incremental source generator for actors (#1334)
Browse files Browse the repository at this point in the history
* Samples - Add k8s deployment yaml to DemoActor sample (#1308)

* up

Signed-off-by: Manuel Menegazzo <[email protected]>

* Fixed build

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added scripts for image build

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added readme Build and push Docker image

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added demo-actor.yaml

Signed-off-by: Manuel Menegazzo <[email protected]>

* Fixed typo

Signed-off-by: Manuel Menegazzo <[email protected]>

* Updated guide, fixed invocation throw curl

Signed-off-by: Manuel Menegazzo <[email protected]>

* Removed dockerfile, updated readme, removed ps1 and sh scripts

Signed-off-by: Manuel Menegazzo <[email protected]>

* Updated base image

Signed-off-by: Manuel Menegazzo <[email protected]>
Signed-off-by: Manuel Menegazzo <[email protected]>

* Update demo-actor.yaml

Signed-off-by: Manuel Menegazzo <[email protected]>
Signed-off-by: Manuel Menegazzo <[email protected]>

* Added overload for DaprClient DI registration (#1289)

* Added overload for DaprClient DI registration allowing the consumer to easily use values from injected services (e.g. IConfiguration).

Signed-off-by: Whit Waldo <[email protected]>

* Added supporting unit test

Signed-off-by: Whit Waldo <[email protected]>

---------

Signed-off-by: Whit Waldo <[email protected]>
Co-authored-by: Phillip Hoff <[email protected]>
Signed-off-by: Manuel Menegazzo <[email protected]>

* Merge `release-1.13` back into `master` (#1285)

* Update protos and related use for Dapr 1.13. (#1236)

* Update protos and related use.

Signed-off-by: Phillip Hoff <[email protected]>

* Update Dapr runtime version.

Signed-off-by: Phillip Hoff <[email protected]>

* Init properties.

Signed-off-by: Phillip Hoff <[email protected]>

---------

Signed-off-by: Phillip Hoff <[email protected]>

* Update artifact action versions. (#1240)

Signed-off-by: Phillip Hoff <[email protected]>

* Make recursive true as default (#1243)

Signed-off-by: Shivam Kumar <[email protected]>

* Fix for secret key transformation in multi-value scenarios (#1274)

* Add repro test.

Signed-off-by: Phillip Hoff <[email protected]>

* Fix for secret key transformation in multi-value scenarios.

Signed-off-by: Phillip Hoff <[email protected]>

---------

Signed-off-by: Phillip Hoff <[email protected]>

* Update Dapr version numbers used during testing.

Signed-off-by: Phillip Hoff <[email protected]>

---------

Signed-off-by: Phillip Hoff <[email protected]>
Signed-off-by: Shivam Kumar <[email protected]>
Co-authored-by: Shivam Kumar <[email protected]>
Signed-off-by: Manuel Menegazzo <[email protected]>

---------

Signed-off-by: Manuel Menegazzo <[email protected]>
Signed-off-by: Manuel Menegazzo <[email protected]>
Signed-off-by: Whit Waldo <[email protected]>
Signed-off-by: Phillip Hoff <[email protected]>
Signed-off-by: Shivam Kumar <[email protected]>
Co-authored-by: Whit Waldo <[email protected]>
Co-authored-by: Phillip Hoff <[email protected]>
Co-authored-by: Shivam Kumar <[email protected]>
Signed-off-by: Manuel Menegazzo <[email protected]>

* Aligned nuget version

Signed-off-by: Manuel Menegazzo <[email protected]>

* UP

Signed-off-by: Manuel Menegazzo <[email protected]>

* UP

Signed-off-by: Manuel Menegazzo <[email protected]>

* Debug profile added

Signed-off-by: Manuel Menegazzo <[email protected]>

* Updated implementation

Signed-off-by: Manuel Menegazzo <[email protected]>

* Emitted DAPR001 Diagnostic warning

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added DAPR002 diagnostic

Signed-off-by: Manuel Menegazzo <[email protected]>

* Cleaun

Signed-off-by: Manuel Menegazzo <[email protected]>

* UP

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added summaries

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added base interface to ActorClient

Signed-off-by: Manuel Menegazzo <[email protected]>

* Updated

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added ctor

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added nullable directive

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added null check for actorproxy ctor parameter

Signed-off-by: Manuel Menegazzo <[email protected]>

* Moved DiagnoticException in a dedicate cs file

Signed-off-by: Manuel Menegazzo <[email protected]>

* Moved generator costants to dedicated class

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added ActorReference creation from the ActorBase class informations (#1277)

* Handled creation of ActorReference from Actor base class

Signed-off-by: Manuel Menegazzo <[email protected]>

* Updated null check

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added unit test for GetActorReference from null actore and actor proxy

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added test for ActorReference created inside Actor implementation

Signed-off-by: Manuel Menegazzo <[email protected]>

* Updated description

Signed-off-by: Manuel Menegazzo <[email protected]>

* Fixed test method naming

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added unit test for exception generated in case the type is not convertible to an ActorReference

Signed-off-by: Manuel Menegazzo <[email protected]>

---------

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added overload to support SDK supplying query string on invoked URL (#1310)

* Refactored extensions and their tests into separate directories

Signed-off-by: Whit Waldo <[email protected]>

* Added overload to method invocation to allow query string parameters to be passed in via the SDK instead of being uncermoniously added to the end of the produced HttpRequestMessage URI

Signed-off-by: Whit Waldo <[email protected]>

* Added unit tests to support implementation

Signed-off-by: Whit Waldo <[email protected]>

* Marking HttpExtensions as internal to prevent external usage and updating to work against Uri instead of HttpRequestMessage.

Signed-off-by: Whit Waldo <[email protected]>

* Updated unit tests to match new extension purpose

Signed-off-by: Whit Waldo <[email protected]>

* Resolved an ambiguous method invocation wherein it was taking the query string and passing it as the payload for a request. Removed the offending method and reworked the remaining configurations so there's no API impact.

Signed-off-by: Whit Waldo <[email protected]>

---------

Signed-off-by: Whit Waldo <[email protected]>
Signed-off-by: Manuel Menegazzo <[email protected]>

* Fixed actorProxy argument null check

Signed-off-by: Manuel Menegazzo <[email protected]>

* Moved ActorClientDesciptor into separta cs file

Signed-off-by: Manuel Menegazzo <[email protected]>

* Moved textual templates to dedicated class

Signed-off-by: Manuel Menegazzo <[email protected]>

* Updated comments, property names

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added argument null check to SyntaxFactoryHelpers

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added comments

Signed-off-by: Manuel Menegazzo <[email protected]>

* Removed obsolete testing packages https://github.com/dotnet/roslyn-sdk/blob/main/src/Microsoft.CodeAnalysis.Testing/README.md#obsolete-packages

Signed-off-by: Manuel Menegazzo <[email protected]>

* Adapted existing unit test to new source generated code

Signed-off-by: Manuel Menegazzo <[email protected]>

* Up

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added tests for SyntaxFactoryHelpers

Signed-off-by: Manuel Menegazzo <[email protected]>

* Updated generation of ArgumentNullException

Signed-off-by: Manuel Menegazzo <[email protected]>

* Updated nullability

Signed-off-by: Manuel Menegazzo <[email protected]>

* Fixed internal methods tests

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added test to IEnumerableExtensions

Signed-off-by: Manuel Menegazzo <[email protected]>

* Unittested GetSyntaxKinds from Accessibility

Signed-off-by: Manuel Menegazzo <[email protected]>

* UP

Signed-off-by: Manuel Menegazzo <[email protected]>

* Updated assignment implementation of ctor body

Signed-off-by: Manuel Menegazzo <[email protected]>

* Improved unit test

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added implementation of method generation

Signed-off-by: Manuel Menegazzo <[email protected]>

* Fixed ArgumentNullException invocation

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added test for NameOfExpression

Signed-off-by: Manuel Menegazzo <[email protected]>

* Fixed ActorProxy method invocation

Signed-off-by: Manuel Menegazzo <[email protected]>

* Simplified proxy argument definition

Signed-off-by: Manuel Menegazzo <[email protected]>

* Explicit generic arguments of the proxy call during generation

Signed-off-by: Manuel Menegazzo <[email protected]>

* Handled cancellation token with default value

Signed-off-by: Manuel Menegazzo <[email protected]>

* Fixed typo

Signed-off-by: Manuel Menegazzo <[email protected]>

* Configured eol used in NormalizeWhitespace function

Signed-off-by: Manuel Menegazzo <[email protected]>

* Normalized expected source

Signed-off-by: Manuel Menegazzo <[email protected]>

* Moved to constat the ActorProxyTypeName

Signed-off-by: Manuel Menegazzo <[email protected]>

* Fix typo

Signed-off-by: Manuel Menegazzo <[email protected]>

* Created ActorProxyInvokeMethodAsync SyntaxFactoryHelper

Signed-off-by: Manuel Menegazzo <[email protected]>

* Removed custom concat implementation

Signed-off-by: Manuel Menegazzo <[email protected]>

* fix (#1329)

Signed-off-by: Hannah Hunter <[email protected]>
Signed-off-by: Manuel Menegazzo <[email protected]>

* link to non-dapr endpoint howto (#1335)

Signed-off-by: Hannah Hunter <[email protected]>
Signed-off-by: Manuel Menegazzo <[email protected]>

* Merge 1.14 release branch back into `master`. (#1337)

Signed-off-by: Manuel Menegazzo <[email protected]>

* Fixed merge errors
Signed-off-by: Manuel Menegazzo <[email protected]>

Signed-off-by: Manuel Menegazzo <[email protected]>

* Updated some summaries

Signed-off-by: Manuel Menegazzo <[email protected]>

* Added some missing summaries

Signed-off-by: Manuel Menegazzo <[email protected]>

* Fixed typo

Signed-off-by: Manuel Menegazzo <[email protected]>

* Improved some summary text

Signed-off-by: Manuel Menegazzo <[email protected]>

* Improved summaries

Signed-off-by: Manuel Menegazzo <[email protected]>

* Handled review requests

Signed-off-by: Manuel Menegazzo <[email protected]>

* Changed SyntaxFactoryHelpers accessor to internal

Signed-off-by: Manuel Menegazzo <[email protected]>

---------

Signed-off-by: Manuel Menegazzo <[email protected]>
Signed-off-by: Manuel Menegazzo <[email protected]>
Signed-off-by: Whit Waldo <[email protected]>
Signed-off-by: Phillip Hoff <[email protected]>
Signed-off-by: Shivam Kumar <[email protected]>
Signed-off-by: Hannah Hunter <[email protected]>
Co-authored-by: Whit Waldo <[email protected]>
Co-authored-by: Phillip Hoff <[email protected]>
Co-authored-by: Shivam Kumar <[email protected]>
Co-authored-by: Hannah Hunter <[email protected]>
  • Loading branch information
5 people authored Oct 28, 2024
1 parent c61b15d commit 03038fa
Show file tree
Hide file tree
Showing 21 changed files with 1,090 additions and 436 deletions.
2 changes: 1 addition & 1 deletion Directory.Packages.props
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@
<PackageVersion Include="Microsoft.CodeAnalysis.Analyzers" Version="3.3.4" />
<PackageVersion Include="Microsoft.CodeAnalysis.Common" Version="4.8.0" />
<PackageVersion Include="Microsoft.CodeAnalysis.CSharp" Version="4.8.0" />
<PackageVersion Include="Microsoft.CodeAnalysis.CSharp.SourceGenerators.Testing.XUnit" Version="1.1.2" />
<PackageVersion Include="Microsoft.CodeAnalysis.CSharp.SourceGenerators.Testing" Version="1.1.2" />
<PackageVersion Include="Microsoft.CodeAnalysis.CSharp.Workspaces" Version="4.8.0" />
<PackageVersion Include="Microsoft.DurableTask.Client.Grpc" Version="1.3.0" />
<PackageVersion Include="Microsoft.DurableTask.Worker.Grpc" Version="1.3.0" />
Expand Down
41 changes: 24 additions & 17 deletions examples/GeneratedActor/ActorClient/ActorClient.csproj
Original file line number Diff line number Diff line change
@@ -1,22 +1,29 @@
<Project Sdk="Microsoft.NET.Sdk">
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net6</TargetFramework>
<LangVersion>10.0</LangVersion>
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
</PropertyGroup>
<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net6</TargetFramework>
<LangVersion>10.0</LangVersion>
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>

<ItemGroup>
<ProjectReference Include="..\ActorCommon\ActorCommon.csproj" />
<ProjectReference Include="..\..\..\src\Dapr.Actors\Dapr.Actors.csproj" />
</ItemGroup>
<!-- Persist the source generator (and other) files to disk -->
<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
<!-- 👇 The "base" path for the source generators -->
<!--<GeneratedFolder>Generated</GeneratedFolder>-->
<!-- 👇 Write the output for each target framework to a different sub-folder -->
<!--<CompilerGeneratedFilesOutputPath>$(GeneratedFolder)\$(TargetFramework)</CompilerGeneratedFilesOutputPath>-->
</PropertyGroup>

<ItemGroup>
<ProjectReference Include="..\..\..\src\Dapr.Actors.Generators\Dapr.Actors.Generators.csproj"
OutputItemType="Analyzer"
ReferenceOutputAssembly="false" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\ActorCommon\ActorCommon.csproj" />
<ProjectReference Include="..\..\..\src\Dapr.Actors\Dapr.Actors.csproj" />
</ItemGroup>

<ItemGroup>
<ProjectReference Include="..\..\..\src\Dapr.Actors.Generators\Dapr.Actors.Generators.csproj"
OutputItemType="Analyzer"
ReferenceOutputAssembly="false" />
</ItemGroup>

</Project>
2 changes: 1 addition & 1 deletion examples/GeneratedActor/ActorClient/IClientActor.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
// ------------------------------------------------------------------------
// ------------------------------------------------------------------------
// Copyright 2023 The Dapr Authors
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
Expand Down
454 changes: 221 additions & 233 deletions src/Dapr.Actors.Generators/ActorClientGenerator.cs

Large diffs are not rendered by default.

8 changes: 8 additions & 0 deletions src/Dapr.Actors.Generators/AnalyzerReleases.Shipped.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
## Release 1.14

### New Rules

Rule ID | Category | Severity | Notes
--------|----------|----------|--------------------
DAPR0001| Usage | Error | Cancellation tokens must be the last argument
DAPR0002| Usage | Error | Only methods with a single argument or a single argument followed by a cancellation token are supported
3 changes: 3 additions & 0 deletions src/Dapr.Actors.Generators/AnalyzerReleases.Unshipped.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
; Unshipped analyzer release
; https://github.com/dotnet/roslyn-analyzers/blob/main/src/Microsoft.CodeAnalysis.Analyzers/ReleaseTrackingAnalyzers.Help.md

38 changes: 38 additions & 0 deletions src/Dapr.Actors.Generators/Constants.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
namespace Dapr.Actors.Generators
{
/// <summary>
/// Constants used by the code generator.
/// </summary>
internal static class Constants
{
/// <summary>
/// The namespace used by the generated code.
/// </summary>
public const string GeneratorsNamespace = "Dapr.Actors.Generators";

/// <summary>
/// The name of the attribute used to mark actor interfaces.
/// </summary>
public const string ActorMethodAttributeTypeName = "ActorMethodAttribute";

/// <summary>
/// The full type name of the attribute used to mark actor interfaces.
/// </summary>
public const string ActorMethodAttributeFullTypeName = GeneratorsNamespace + "." + ActorMethodAttributeTypeName;

/// <summary>
/// The name of the attribute used to mark actor interfaces.
/// </summary>
public const string GenerateActorClientAttributeTypeName = "GenerateActorClientAttribute";

/// <summary>
/// The full type name of the attribute used to mark actor interfaces.
/// </summary>
public const string GenerateActorClientAttributeFullTypeName = GeneratorsNamespace + "." + GenerateActorClientAttributeTypeName;

/// <summary>
/// Actor proxy type name.
/// </summary>
public const string ActorProxyTypeName = "Dapr.Actors.Client.ActorProxy";
}
}
64 changes: 37 additions & 27 deletions src/Dapr.Actors.Generators/Dapr.Actors.Generators.csproj
Original file line number Diff line number Diff line change
@@ -1,45 +1,55 @@
<Project Sdk="Microsoft.NET.Sdk">
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
</PropertyGroup>
<PropertyGroup>
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
<IsRoslynComponent>true</IsRoslynComponent>
</PropertyGroup>

<PropertyGroup>
<EnforceExtendedAnalyzerRules>true</EnforceExtendedAnalyzerRules>
</PropertyGroup>
<PropertyGroup>
<EnforceExtendedAnalyzerRules>true</EnforceExtendedAnalyzerRules>
</PropertyGroup>

<ItemGroup>
<PackageReference Include="Microsoft.CodeAnalysis.CSharp" PrivateAssets="all" />
<PackageReference Include="Microsoft.CodeAnalysis.Analyzers" PrivateAssets="all" />
</ItemGroup>

<!--
<!--
Source generators are built and packaged as analyzers and not "normal" NuGet libraries.
-->

<PropertyGroup>
<!-- Generators must target netstandard2.0. -->
<TargetFramework>netstandard2.0</TargetFramework>
<TargetFrameworks></TargetFrameworks>
<PropertyGroup>
<!-- Generators must target netstandard2.0. -->
<TargetFramework>netstandard2.0</TargetFramework>
<TargetFrameworks></TargetFrameworks>

<!-- Do not include the generator as a lib dependency -->
<IncludeBuildOutput>false</IncludeBuildOutput>
<!-- Do not include the generator as a lib dependency -->
<IncludeBuildOutput>false</IncludeBuildOutput>

<!-- Suppress false-positive error NU5128 when packing analyzers with no lib/ref files. -->
<SuppressDependenciesWhenPacking>true</SuppressDependenciesWhenPacking>
<!-- Suppress false-positive error NU5128 when packing analyzers with no lib/ref files. -->
<SuppressDependenciesWhenPacking>true</SuppressDependenciesWhenPacking>

<!-- Suppress generation of symbol package (.snupkg). -->
<IncludeSymbols>false</IncludeSymbols>
<!-- Suppress generation of symbol package (.snupkg). -->
<IncludeSymbols>false</IncludeSymbols>

<!-- Additional NuGet package properties. -->
<Description>This package contains source generators for interacting with Actor services using Dapr.</Description>
<PackageTags>$(PackageTags);Actors</PackageTags>
</PropertyGroup>
<!-- Additional NuGet package properties. -->
<Description>This package contains source generators for interacting with Actor services using Dapr.</Description>
<PackageTags>$(PackageTags);Actors</PackageTags>
</PropertyGroup>

<ItemGroup>
<!-- Package the generator in the analyzer directory of the NuGet package -->
<None Include="$(OutputPath)\$(AssemblyName).dll" Pack="true" PackagePath="analyzers/dotnet/cs" Visible="false" />
</ItemGroup>
<ItemGroup>
<!-- Package the generator in the analyzer directory of the NuGet package -->
<None Include="$(OutputPath)\$(AssemblyName).dll" Pack="true" PackagePath="analyzers/dotnet/cs" Visible="false" />
</ItemGroup>

<ItemGroup>
<AdditionalFiles Include="AnalyzerReleases.Shipped.md" />
<AdditionalFiles Include="AnalyzerReleases.Unshipped.md" />
</ItemGroup>

<ItemGroup>
<InternalsVisibleTo Include="$(AssemblyName).Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100b1f597635c44597fcecb493e2b1327033b29b1a98ac956a1a538664b68f87d45fbaada0438a15a6265e62864947cc067d8da3a7d93c5eb2fcbb850e396c8684dba74ea477d82a1bbb18932c0efb30b64ff1677f85ae833818707ac8b49ad8062ca01d2c89d8ab1843ae73e8ba9649cd28666b539444dcdee3639f95e2a099bb2"/>
</ItemGroup>

</Project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
using Microsoft.CodeAnalysis;

namespace Dapr.Actors.Generators.Diagnostics
{
internal static class CancellationTokensMustBeTheLastArgument
{
public const string DiagnosticId = "DAPR0001";
public const string Title = "Invalid method signature";
public const string MessageFormat = "Cancellation tokens must be the last argument";
public const string Category = "Usage";

private static readonly DiagnosticDescriptor Rule = new DiagnosticDescriptor(
DiagnosticId,
Title,
MessageFormat,
Category,
DiagnosticSeverity.Error,
isEnabledByDefault: true);

internal static Diagnostic CreateDiagnostic(ISymbol symbol) => Diagnostic.Create(
Rule,
symbol.Locations.First(),
symbol.ToDisplayString(SymbolDisplayFormat.FullyQualifiedFormat));
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
using Microsoft.CodeAnalysis;

namespace Dapr.Actors.Generators.Diagnostics
{
internal static class MethodMustOnlyHaveASingleArgumentOptionallyFollowedByACancellationToken
{
public const string DiagnosticId = "DAPR0002";
public const string Title = "Invalid method signature";
public const string MessageFormat = "Only methods with a single argument or a single argument followed by a cancellation token are supported";
public const string Category = "Usage";

private static readonly DiagnosticDescriptor Rule = new DiagnosticDescriptor(
DiagnosticId,
Title,
MessageFormat,
Category,
DiagnosticSeverity.Error,
isEnabledByDefault: true);

internal static Diagnostic CreateDiagnostic(ISymbol symbol) => Diagnostic.Create(
Rule,
symbol.Locations.First(),
symbol.ToDisplayString(SymbolDisplayFormat.FullyQualifiedFormat));
}
}
25 changes: 25 additions & 0 deletions src/Dapr.Actors.Generators/DiagnosticsException.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
using Microsoft.CodeAnalysis;

namespace Dapr.Actors.Generators
{
/// <summary>
/// Exception thrown when diagnostics are encountered during code generation.
/// </summary>
internal sealed class DiagnosticsException : Exception
{
/// <summary>
/// Initializes a new instance of the <see cref="DiagnosticsException"/> class.
/// </summary>
/// <param name="diagnostics">List of diagnostics generated.</param>
public DiagnosticsException(IEnumerable<Diagnostic> diagnostics)
: base(string.Join("\n", diagnostics.Select(d => d.ToString())))
{
this.Diagnostics = diagnostics.ToArray();
}

/// <summary>
/// Diagnostics encountered during code generation.
/// </summary>
public ICollection<Diagnostic> Diagnostics { get; }
}
}
34 changes: 34 additions & 0 deletions src/Dapr.Actors.Generators/Extensions/IEnumerableExtensions.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
namespace Dapr.Actors.Generators.Extensions
{
internal static class IEnumerableExtensions
{
/// <summary>
/// Returns the index of the first item in the sequence that satisfies the predicate. If no item satisfies the predicate, -1 is returned.
/// </summary>
/// <typeparam name="T">The type of objects in the <see cref="IEnumerable{T}"/>.</typeparam>
/// <param name="source"><see cref="IEnumerable{T}"/> in which to search.</param>
/// <param name="predicate">Function performed to check whether an item satisfies the condition.</param>
/// <returns>Return the zero-based index of the first occurrence of an element that satisfies the condition, if found; otherwise, -1.</returns>
internal static int IndexOf<T>(this IEnumerable<T> source, Func<T, bool> predicate)
{
if (predicate is null)
{
throw new ArgumentNullException(nameof(predicate));
}

int index = 0;

foreach (var item in source)
{
if (predicate(item))
{
return index;
}

index++;
}

return -1;
}
}
}
Loading

0 comments on commit 03038fa

Please sign in to comment.