Category: .NET

RSCG – WhatIAmDoing

RSCG – WhatIAmDoing
 
 

name WhatIAmDoing
nuget https://www.nuget.org/packages/RSCG_WhatIAmDoing/
https://www.nuget.org/packages/RSCG_WhatIAmDoing_Common/
link https://github.com/ignatandrei/RSCG_WhatIAmDoing
author Ignat Andrei

Intercept any method in any project

 

This is how you can use WhatIAmDoing .

The code that you start with is


<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>net8.0</TargetFramework>
    <ImplicitUsings>enable</ImplicitUsings>
    <Nullable>enable</Nullable>
  </PropertyGroup>

	<ItemGroup>
		<!-- <PackageReference Include="Microsoft.Extensions.Caching.Memory" Version="8.0.0" /> -->
		<PackageReference Include="RSCG_WhatIAmDoing" Version="8.2024.10201.735" />
		<PackageReference Include="RSCG_WhatIAmDoing_Common" Version="8.2024.10201.735" />
	</ItemGroup>

	<PropertyGroup>

		<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
		<CompilerGeneratedFilesOutputPath>$(BaseIntermediateOutputPath)\GX</CompilerGeneratedFilesOutputPath>
		<InterceptorsPreviewNamespaces>$(InterceptorsPreviewNamespaces);RSCG_InterceptorTemplate</InterceptorsPreviewNamespaces>
	</PropertyGroup>

</Project>


The code that you will use is


using RSCG_WhatIAmDoing_Common;

Console.WriteLine("Hello, World!");
var data = CachingData.Methods().ToArray();

foreach (var item in data)
{
    Console.WriteLine($"Method {item.typeAndMethodData.MethodName} from class {item.typeAndMethodData.TypeOfClass} Time: {item.StartedAtDate} state {item.State} ");
    Console.WriteLine($"  =>Arguments: {item.ArgumentsAsString()}");
    if ((item.State & AccumulatedStateMethod.HasResult) == AccumulatedStateMethod.HasResult)
    {
        Console.WriteLine($"  =>Result: {item.Result}");
    }

}



using RSCG_WhatIAmDoing;
using RSCG_WhatIAmDoing_Common;

namespace WIADDemo;
//[ExposeClass(typeof(Encoding), nameof(Encoding.EncodingName))]
[InterceptStatic("System.Console.*")] // regex
internal class InterceptorMethodStatic : InterceptorMethodStaticBase, IInterceptorMethodStatic
{

}

 

The code that is generated is

#pragma warning disable CS1591 
#pragma warning disable CS9113
namespace System.Runtime.CompilerServices{
[AttributeUsage(AttributeTargets.Method,AllowMultiple =true)]
file class InterceptsLocationAttribute(string filePath, int line, int character) : Attribute
{
}
}//end namespace

namespace RSCG_InterceptorTemplate{
static partial class SimpleIntercept
{


//replace code:Console.WriteLine("Hello, World!");
//replace code:123456789!123456789!123456789!12345
[System.Runtime.CompilerServices.InterceptsLocation(@"D:\gth\RSCG_Examples\v2\rscg_examples\WIAD\src\WIADDemo\WIADDemo\Program.cs", 3, 9)]
    
//[System.Diagnostics.DebuggerStepThrough()]
public static  void Intercept__WriteLine_0 (  string? value )  
{

System.Collections.Generic.Dictionary<string,string?> valValues = new (){


};//end valValues

System.Collections.Generic.Dictionary<string,string?> stringValues = new() {


                { "value", value  ?.ToString() } ,
            };//end stringValues

        System.Collections.Generic.Dictionary<string,string?>
            expValues = new() {

            };//end exposeValues


        var x=WIADDemo.InterceptorMethodStatic .InterceptStaticMethodBefore(
$$$""""
    {"IsVoid":true,"Tag":"","MethodName":"WriteLine","TypeOfClass":"System.Console"}
""""
            ,valValues , stringValues , expValues
)
; 


                try{

                 System.Console.WriteLine(value);

                WIADDemo.InterceptorMethodStatic .InterceptMethodAfterWithoutResult(x);
                
                }

            
        
            catch(System.Exception ex){
                WIADDemo.InterceptorMethodStatic .InterceptMethodException(x,ex);
                throw;
            }
            finally{
                WIADDemo.InterceptorMethodStatic .InterceptMethodFinally(x);
            }
        
}
                

}//end class

}//namespace RSCG_InterceptorTemplate


#pragma warning disable CS1591 
#pragma warning disable CS9113
namespace System.Runtime.CompilerServices{
[AttributeUsage(AttributeTargets.Method,AllowMultiple =true)]
file class InterceptsLocationAttribute(string filePath, int line, int character) : Attribute
{
}
}//end namespace

namespace RSCG_InterceptorTemplate{
static partial class SimpleIntercept
{


//replace code:    Console.WriteLine($"Method {item.typeAndMethodData.MethodName} from class {item.typeAndMethodData.TypeOfClass} Time: {item.StartedAtDate} state {item.State} ");
//replace code:123456789!123456789!123456789!123456789!123456789!123456789!123456789!123456789!123456789!123456789!123456789!123456789!123456789!123456789!123456789!123456789!1234
[System.Runtime.CompilerServices.InterceptsLocation(@"D:\gth\RSCG_Examples\v2\rscg_examples\WIAD\src\WIADDemo\WIADDemo\Program.cs", 8, 13)]
    
//[System.Diagnostics.DebuggerStepThrough()]
public static  void Intercept__WriteLine_1 (  string? value )  
{

System.Collections.Generic.Dictionary<string,string?> valValues = new (){


};//end valValues

System.Collections.Generic.Dictionary<string,string?> stringValues = new() {


                { "value", value  ?.ToString() } ,
            };//end stringValues

        System.Collections.Generic.Dictionary<string,string?>
            expValues = new() {

            };//end exposeValues


        var x=WIADDemo.InterceptorMethodStatic .InterceptStaticMethodBefore(
$$$""""
    {"IsVoid":true,"Tag":"","MethodName":"WriteLine","TypeOfClass":"System.Console"}
""""
            ,valValues , stringValues , expValues
)
; 


                try{

                 System.Console.WriteLine(value);

                WIADDemo.InterceptorMethodStatic .InterceptMethodAfterWithoutResult(x);
                
                }

            
        
            catch(System.Exception ex){
                WIADDemo.InterceptorMethodStatic .InterceptMethodException(x,ex);
                throw;
            }
            finally{
                WIADDemo.InterceptorMethodStatic .InterceptMethodFinally(x);
            }
        
}
                

}//end class

}//namespace RSCG_InterceptorTemplate


#pragma warning disable CS1591 
#pragma warning disable CS9113
namespace System.Runtime.CompilerServices{
[AttributeUsage(AttributeTargets.Method,AllowMultiple =true)]
file class InterceptsLocationAttribute(string filePath, int line, int character) : Attribute
{
}
}//end namespace

namespace RSCG_InterceptorTemplate{
static partial class SimpleIntercept
{


//replace code:    Console.WriteLine($"  =>Arguments: {item.ArgumentsAsString()}");
//replace code:123456789!123456789!123456789!123456789!123456789!123456789!12345678
[System.Runtime.CompilerServices.InterceptsLocation(@"D:\gth\RSCG_Examples\v2\rscg_examples\WIAD\src\WIADDemo\WIADDemo\Program.cs", 9, 13)]
    
//[System.Diagnostics.DebuggerStepThrough()]
public static  void Intercept__WriteLine_2 (  string? value )  
{

System.Collections.Generic.Dictionary<string,string?> valValues = new (){


};//end valValues

System.Collections.Generic.Dictionary<string,string?> stringValues = new() {


                { "value", value  ?.ToString() } ,
            };//end stringValues

        System.Collections.Generic.Dictionary<string,string?>
            expValues = new() {

            };//end exposeValues


        var x=WIADDemo.InterceptorMethodStatic .InterceptStaticMethodBefore(
$$$""""
    {"IsVoid":true,"Tag":"","MethodName":"WriteLine","TypeOfClass":"System.Console"}
""""
            ,valValues , stringValues , expValues
)
; 


                try{

                 System.Console.WriteLine(value);

                WIADDemo.InterceptorMethodStatic .InterceptMethodAfterWithoutResult(x);
                
                }

            
        
            catch(System.Exception ex){
                WIADDemo.InterceptorMethodStatic .InterceptMethodException(x,ex);
                throw;
            }
            finally{
                WIADDemo.InterceptorMethodStatic .InterceptMethodFinally(x);
            }
        
}
                

}//end class

}//namespace RSCG_InterceptorTemplate


#pragma warning disable CS1591 
#pragma warning disable CS9113
namespace System.Runtime.CompilerServices{
[AttributeUsage(AttributeTargets.Method,AllowMultiple =true)]
file class InterceptsLocationAttribute(string filePath, int line, int character) : Attribute
{
}
}//end namespace

namespace RSCG_InterceptorTemplate{
static partial class SimpleIntercept
{


//replace code:        Console.WriteLine($"  =>Result: {item.Result}");
//replace code:123456789!123456789!123456789!123456789!123456789!123456
[System.Runtime.CompilerServices.InterceptsLocation(@"D:\gth\RSCG_Examples\v2\rscg_examples\WIAD\src\WIADDemo\WIADDemo\Program.cs", 12, 17)]
    
//[System.Diagnostics.DebuggerStepThrough()]
public static  void Intercept__WriteLine_3 (  string? value )  
{

System.Collections.Generic.Dictionary<string,string?> valValues = new (){


};//end valValues

System.Collections.Generic.Dictionary<string,string?> stringValues = new() {


                { "value", value  ?.ToString() } ,
            };//end stringValues

        System.Collections.Generic.Dictionary<string,string?>
            expValues = new() {

            };//end exposeValues


        var x=WIADDemo.InterceptorMethodStatic .InterceptStaticMethodBefore(
$$$""""
    {"IsVoid":true,"Tag":"","MethodName":"WriteLine","TypeOfClass":"System.Console"}
""""
            ,valValues , stringValues , expValues
)
; 


                try{

                 System.Console.WriteLine(value);

                WIADDemo.InterceptorMethodStatic .InterceptMethodAfterWithoutResult(x);
                
                }

            
        
            catch(System.Exception ex){
                WIADDemo.InterceptorMethodStatic .InterceptMethodException(x,ex);
                throw;
            }
            finally{
                WIADDemo.InterceptorMethodStatic .InterceptMethodFinally(x);
            }
        
}
                

}//end class

}//namespace RSCG_InterceptorTemplate


Code and pdf at

https://ignatandrei.github.io/RSCG_Examples/v2/docs/WhatIAmDoing

RSCG – NotNotAppSettings

RSCG – NotNotAppSettings
 
 

name NotNotAppSettings
nuget https://www.nuget.org/packages/NotNot.AppSettings/
link https://github.com/jasonswearingen/NotNot.AppSettings/
author jasonswearingen

Application Settings to strongly typed classes. Generate also from AppSettings development

 

This is how you can use NotNotAppSettings .

The code that you start with is


<Project Sdk="Microsoft.NET.Sdk.Web">

  <PropertyGroup>
    <TargetFramework>net8.0</TargetFramework>
    <Nullable>enable</Nullable>
    <ImplicitUsings>enable</ImplicitUsings>
    <InvariantGlobalization>true</InvariantGlobalization>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="Microsoft.AspNetCore.OpenApi" Version="8.0.1" />
    <PackageReference Include="NotNot.AppSettings" Version="1.0.0" OutputItemType="Analyzer" ReferenceOutputAssembly="true" />
    <PackageReference Include="Swashbuckle.AspNetCore" Version="6.4.0" />
  </ItemGroup>

  <ItemGroup>
    <AdditionalFiles Update="appsettings.json">
      <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
    </AdditionalFiles>
  </ItemGroup>
	<PropertyGroup>
		<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
		<CompilerGeneratedFilesOutputPath>$(BaseIntermediateOutputPath)\GX</CompilerGeneratedFilesOutputPath>
	</PropertyGroup>
</Project>


The code that you will use is


var builder = WebApplication.CreateBuilder(args);

// Add services to the container.
// Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();
builder.Services.AddSingleton<TestAppSettings.AppSettingsGen.IAppSettingsBinder, TestAppSettings.AppSettingsGen.AppSettingsBinder>();

var app = builder.Build();

// Configure the HTTP request pipeline.
if (app.Environment.IsDevelopment())
{
    app.UseSwagger();
    app.UseSwaggerUI();
}

app.UseHttpsRedirection();

var summaries = new[]
{
    "Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
};

var appSettings = app.Services.GetRequiredService<TestAppSettings.AppSettingsGen.IAppSettingsBinder>().AppSettings;
Console.WriteLine(appSettings.AppName);

app.MapGet("/weatherforecast", () =>
{
    var forecast = Enumerable.Range(1, 5).Select(index =>
        new WeatherForecast
        (
            DateOnly.FromDateTime(DateTime.Now.AddDays(index)),
            Random.Shared.Next(-20, 55),
            summaries[Random.Shared.Next(summaries.Length)]
        ))
        .ToArray();
    return forecast;
})
.WithName("GetWeatherForecast")
.WithOpenApi();

app.Run();

internal record WeatherForecast(DateOnly Date, int TemperatureC, string? Summary)
{
    public int TemperatureF => 32 + (int)(TemperatureC / 0.5556);
}


 

The code that is generated is


/** 
 * This file is generated by the NotNot.AppSettings nuget package.
 * Do not edit this file directly, instead edit the appsettings.json files and rebuild the project.
**/
using System;
using System.Runtime.CompilerServices;
namespace TestAppSettings.AppSettingsGen;

[CompilerGenerated]
public partial class AppSettings {
   public TestAppSettings.AppSettingsGen._AppSettings.Logging? Logging{get; set;}
   public string? AllowedHosts{get; set;}
   public string? AppName{get; set;}

}


/** 
 * This file is generated by the NotNot.AppSettings nuget package.
 * Do not edit this file directly, instead edit the appsettings.json files and rebuild the project.
**/
using System;
using System.Runtime.CompilerServices;
namespace TestAppSettings.AppSettingsGen._AppSettings;

[CompilerGenerated]
public partial class Logging {
   public TestAppSettings.AppSettingsGen._AppSettings._Logging.LogLevel? LogLevel{get; set;}

}


/** 
 * This file is generated by the NotNot.AppSettings nuget package.
 * Do not edit this file directly, instead edit the appsettings.json files and rebuild the project.
**/
using System;
using System.Runtime.CompilerServices;
namespace TestAppSettings.AppSettingsGen._AppSettings._Logging;

[CompilerGenerated]
public partial class LogLevel {
   public string? Default{get; set;}
   public string? Microsoft_AspNetCore{get; set;}

}


/** 
 * This file is generated by the NotNot.AppSettings nuget package.
 * Do not edit this file directly, instead edit the appsettings.json files and rebuild the project.
**/

using Microsoft.Extensions.Configuration;
namespace TestAppSettings.AppSettingsGen;


/// <summary>
/// Strongly typed AppSettings.json, recreated every build. 
/// <para>You can use this directly, extend it (it's a partial class), 
/// or get a populated instance of it via the <see cref="AppSettingsBinder"/> DI service</para>
/// </summary>
public partial class AppSettings
{
}

/// <summary>
/// a DI service that contains a strongly-typed copy of your appsettings.json
/// <para><strong>DI Usage:</strong></para>
/// <para><c>builder.Services.AddSingleton&lt;IAppSettingsBinder, AppSettingsBinder&gt;();</c></para>
/// <para><c>var app = builder.Build();</c></para>
///  <para><c>var appSettings = app.Services.GetRequiredService&lt;IAppSettingsBinder&gt;().AppSettings;</c></para>
/// <para><strong>Non-DI Usage:</strong></para>
/// <para><c>var appSettings = AppSettingsBinder.LoadDirect();</c></para>
/// </summary>
public partial class AppSettingsBinder : IAppSettingsBinder
{
   public AppSettings AppSettings { get; protected set; }

   public AppSettingsBinder(IConfiguration _config)
   {
      AppSettings = new AppSettings();

      //automatically reads and binds to config file
      _config.Bind(AppSettings);
   }

   /// <summary>
   /// Manually construct an AppSettings from your appsettings.json files.
   /// <para>NOTE: This method is provided for non-DI users.  If you use DI, don't use this method.  Instead just register this class as a service.</para>
   /// </summary>
   /// <param name="appSettingsLocation">folder where to search for appsettings.json.  defaults to current app folder.</param>
   /// <param name="appSettingsFileNames">lets you override the files to load up.  defaults to 'appsettings.json' and 'appsettings.{DOTNET_ENVIRONMENT}.json'</param>
   /// <param name="throwIfFilesMissing">default is to silently ignore if any of the .json files are missing.</param>
   /// <returns>your strongly typed appsettings with values from your .json loaded in</returns>
   public static AppSettings LoadDirect(string? appSettingsLocation = null,IEnumerable<string>? appSettingsFileNames=null,bool throwIfFilesMissing=false )
   {      
      //pick what .json files to load
      if (appSettingsFileNames is null)
      {
         //figure out what env
         var env = Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT");
         env ??= Environment.GetEnvironmentVariable("DOTNET_ENVIRONMENT");
         env ??= Environment.GetEnvironmentVariable("ENVIRONMENT");
         //env ??= "Development"; //default to "Development
         if (env is null)
         {
            appSettingsFileNames = new[] { "appsettings.json" };
         }
         else
         {
            appSettingsFileNames = new[] { "appsettings.json", $"appsettings.{env}.json" };
         }
      }

      //build a config from the specified files
      var builder = new ConfigurationBuilder();
      if (appSettingsLocation != null)
      {
         builder.SetBasePath(appSettingsLocation);
      }
      var optional = !throwIfFilesMissing;
      foreach (var fileName in appSettingsFileNames)
      {         
         builder.AddJsonFile(fileName, optional: optional, reloadOnChange: false); // Add appsettings.json
      }
      IConfigurationRoot configuration = builder.Build();

      //now finally get the appsettings we care about
      var binder = new AppSettingsBinder(configuration);
      return binder.AppSettings;
   }
}

/// <summary>
/// a DI service that contains a strongly-typed copy of your appsettings.json
/// <para><strong>DI Usage:</strong></para>
/// <para><c>builder.Services.AddSingleton&lt;IAppSettingsBinder, AppSettingsBinder&gt;();</c></para>
/// <para><c>var app = builder.Build();</c></para>
///  <para><c>var appSettings = app.Services.GetRequiredService&lt;IAppSettingsBinder&gt;().AppSettings;</c></para>
/// <para><strong>Non-DI Usage:</strong></para>
/// <para><c>var appSettings = AppSettingsBinder.LoadDirect();</c></para>
/// </summary>
public interface IAppSettingsBinder
{
   public AppSettings AppSettings { get; }
}

Code and pdf at

https://ignatandrei.github.io/RSCG_Examples/v2/docs/NotNotAppSettings

RSCG – Weave

RSCG – Weave
 
 

name Weave
nuget https://www.nuget.org/packages/Weave/
link https://github.com/otac0n/Weave
author John Gietzen

Scriban like generator

 

This is how you can use Weave .

The code that you start with is


<Project Sdk="Microsoft.NET.Sdk">

	<PropertyGroup>
		<OutputType>Exe</OutputType>
		<TargetFramework>net8.0</TargetFramework>
		<ImplicitUsings>enable</ImplicitUsings>
		<Nullable>enable</Nullable>
	</PropertyGroup>

	<ItemGroup>
	  <None Remove="MyDataT.weave" />
	</ItemGroup>
	<ItemGroup>
		<PackageReference Include="Weave" Version="2.1.0">
			<PrivateAssets>all</PrivateAssets>
			<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
		</PackageReference>
	</ItemGroup>
	<ItemGroup>
	  <WeaveTemplate Include="MyDataT.weave">
	    
	  </WeaveTemplate>
	</ItemGroup>
	<PropertyGroup>
		<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
		<CompilerGeneratedFilesOutputPath>$(BaseIntermediateOutputPath)\GX</CompilerGeneratedFilesOutputPath>
	</PropertyGroup>

</Project>


The code that you will use is


using WeaveDemo;

Person p = new()
{
FirstName = "Andrei", LastName = "Ignat" 
};


MyProject.Templates.RenderFizzBuzz(p, Console.Out);

StringWriter sw = new();
MyProject.Templates.RenderFizzBuzz(p, sw);
Console.WriteLine("---------------------------");
Console.WriteLine(sw.ToString());




namespace WeaveDemo;
internal class Person
{
    public string? FirstName { get; set; }
    public string? LastName { get; set; }
    public string FullName() => $"{FirstName} {LastName}";
}


 

The code that is generated is

// -----------------------------------------------------------------------
// <auto-generated>
//   This code was generated by Weave 2.1.0.0
//
//   Changes to this file may cause incorrect behavior and will be lost if
//   the code is regenerated.
// </auto-generated>
// -----------------------------------------------------------------------

namespace
    #line 1 "..\..\..\MyDataT.weave"
           MyProject
    #line default
{
    using System;
    using System.IO;

    partial class
    Templates
    {
        [System.CodeDom.Compiler.GeneratedCode("Weave", "2.1.0.0")]
        public
        static void
        #line 2 "..\..\..\MyDataT.weave"
            RenderFizzBuzz
        #line default
            (
            #line 3 "..\..\..\MyDataT.weave"
       WeaveDemo.Person
            #line default
            model, TextWriter writer, string indentation = null)
        {
            var __originalIndentation = indentation = indentation ?? string.Empty;
            writer.Write(indentation);
            writer.Write("I will write p.FullName();");
            writer.WriteLine();
            writer.WriteLine();
            writer.Write(indentation);
            writer.Write(
                #line 7 "..\..\..\MyDataT.weave"
    model.FullName() 
                #line default
                );
            writer.WriteLine();
        }
    }
}

Code and pdf at

https://ignatandrei.github.io/RSCG_Examples/v2/docs/Weave

RSCG – HangfireRecurringJob

RSCG – HangfireRecurringJob
 
 

name HangfireRecurringJob
nuget https://www.nuget.org/packages/IeuanWalker.Hangfire.RecurringJob/
link https://github.com/IeuanWalker/Hangfire.RecurringJob
author Ieuan Walker

Generating recurring jobs for Hangfire from class attribute

 

This is how you can use HangfireRecurringJob .

The code that you start with is


<Project Sdk="Microsoft.NET.Sdk.Web">

  <PropertyGroup>
    <TargetFramework>net8.0</TargetFramework>
    <Nullable>enable</Nullable>
    <ImplicitUsings>enable</ImplicitUsings>
    <InvariantGlobalization>true</InvariantGlobalization>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="Hangfire.AspNetCore" Version="1.8.9" />
    <PackageReference Include="Hangfire.Core" Version="1.8.9" />
    <PackageReference Include="Hangfire.InMemory" Version="0.7.0" />
    <!--<PackageReference Include="Hangfire.MemoryStorage" Version="1.8.0" />-->
    <PackageReference Include="Hangfire.SqlServer" Version="1.8.9" />
    <PackageReference Include="IeuanWalker.Hangfire.RecurringJob" Version="1.0.1" />
    <PackageReference Include="Microsoft.AspNetCore.OpenApi" Version="8.0.1" />
    <PackageReference Include="Swashbuckle.AspNetCore" Version="6.5.0" />
  </ItemGroup>
	<PropertyGroup>
		<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
		<CompilerGeneratedFilesOutputPath>$(BaseIntermediateOutputPath)\GX</CompilerGeneratedFilesOutputPath>
	</PropertyGroup>
</Project>


The code that you will use is


using IeuanWalker.Hangfire.RecurringJob.Attributes;

namespace HangFireRec;
[RecurringJob("*/1 * * * *")]
public class MyNewJob
{
    public async Task Execute()
    {
       await Task.Delay(1000);
        Console.WriteLine("Hello from recurring job hangfire");
    }
}



using Hangfire;
//using Hangfire.MemoryStorage;
using HangFireRec;
var builder = WebApplication.CreateBuilder(args);

// Add services to the container.
// Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();
builder.Services.AddHangfire(it =>
{
    it.UseInMemoryStorage();
    
});
builder.Services.AddHangfireServer(opt =>
{
    //config.UseMemoryStorage();
});
//GlobalConfiguration.Configuration.UseInMemoryStorage();
var app = builder.Build();

// Configure the HTTP request pipeline.
if (app.Environment.IsDevelopment())
{
    app.UseSwagger();
    app.UseSwaggerUI();
}

app.UseHangfireDashboard();
//app.UseHangfireServer();

var summaries = new[]
{
    "Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
};

app.MapGet("/weatherforecast", () =>
{
    var forecast = Enumerable.Range(1, 5).Select(index =>
        new WeatherForecast
        (
            DateOnly.FromDateTime(DateTime.Now.AddDays(index)),
            Random.Shared.Next(-20, 55),
            summaries[Random.Shared.Next(summaries.Length)]
        ))
        .ToArray();
    return forecast;
})
.WithName("GetWeatherForecast")
.WithOpenApi();
BackgroundJob.Enqueue(() =>Console.WriteLine("Hello from hangfire"));
RecurringJob.AddOrUpdate(() => Console.WriteLine("Hello from hangfire"), Cron.Minutely());
app.AddRecurringJobsFromHangFireRec();
app.Run();

internal record WeatherForecast(DateOnly Date, int TemperatureC, string? Summary)
{
    public int TemperatureF => 32 + (int)(TemperatureC / 0.5556);
}


 

The code that is generated is

namespace HangFireRec;

// <auto-generated/>

using Hangfire;
using Microsoft.AspNetCore.Builder;

public static class RecurringJobRegistrationExtensions
{
	public static IApplicationBuilder AddRecurringJobsFromHangFireRec(this IApplicationBuilder app)
	{
		RecurringJob.AddOrUpdate<HangFireRec.MyNewJob>("MyNewJob", "default", x => x.Execute(), "*/1 * * * *", new RecurringJobOptions
		{
			TimeZone = TimeZoneInfo.FindSystemTimeZoneById("UTC")
		});

		return app;
	}
}

Code and pdf at

https://ignatandrei.github.io/RSCG_Examples/v2/docs/HangfireRecurringJob

RSCG – Blazorators

RSCG – Blazorators
 
 

name Blazorators
nuget https://www.nuget.org/packages/Blazor.SourceGenerators/
link https://github.com/IEvangelist/blazorators/
author David Pine

Generate javascript interop code for Blazor WASM projects.

 

This is how you can use Blazorators .

The code that you start with is


<Project Sdk="Microsoft.NET.Sdk.BlazorWebAssembly">

  <PropertyGroup>
    <TargetFramework>net8.0</TargetFramework>
    <Nullable>enable</Nullable>
    <ImplicitUsings>enable</ImplicitUsings>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="Microsoft.AspNetCore.Components.WebAssembly" Version="8.0.1" />
    <PackageReference Include="Microsoft.AspNetCore.Components.WebAssembly.DevServer" Version="8.0.1" PrivateAssets="all" />
  </ItemGroup>

	<ItemGroup>
		<PackageReference Include="Blazor.Serialization" Version="8.0.0" />
		<PackageReference Include="Blazor.SourceGenerators"
						  Version="8.0.0"
						  OutputItemType="Analyzer"
						  SetTargetFramework="TargetFramework=netstandard2.0"
						  ReferenceOutputAssembly="false">
		</PackageReference>
	</ItemGroup>
	<PropertyGroup>
		<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
		<CompilerGeneratedFilesOutputPath>$(BaseIntermediateOutputPath)\GX</CompilerGeneratedFilesOutputPath>
	</PropertyGroup>
</Project>




The code that you will use is


using BlazorApp2;
using Microsoft.AspNetCore.Components.Web;
using Microsoft.AspNetCore.Components.WebAssembly.Hosting;

var builder = WebAssemblyHostBuilder.CreateDefault(args);
builder.RootComponents.Add<App>("#app");
builder.RootComponents.Add<HeadOutlet>("head::after");

builder.Services.AddScoped(sp => new HttpClient { BaseAddress = new Uri(builder.HostEnvironment.BaseAddress) });
builder.Services.AddLocalStorageServices();

await builder.Build().RunAsync();



namespace BlazorApp2;

[JSAutoGenericInterop(
    TypeName = "Storage",
    Implementation = "window.localStorage",
    Url = "https://developer.mozilla.org/docs/Web/API/Window/localStorage",
    GenericMethodDescriptors = new[]
    {
        "getItem",
        "setItem:value"
    })]

public partial interface ILocalStorageService
{
}





@page "/"
@inject ILocalStorageService MyLocalStorage;

<PageTitle>Home</PageTitle>

<h1>Hello, world!</h1>

Please refresh the page to see the value persisted in local storage.
@{
    var name = MyLocalStorage.GetItem<string>("name");
    if (name != null)
    {
        <p>Hi, @name</p>
    }
    else
    {
        <p>Hi, stranger</p>
    }
    MyLocalStorage.SetItem("name", "Andrei Ignat");
}


 

The code that is generated is

/// <summary>
/// The Blazor hosting model source, either WebAssembly or Server.
/// </summary>
public enum BlazorHostingModel
{
    /// <summary>
    /// This is the default. Use this to source generate targeting the synchronous <c>IJSInProcessRuntime</c> type.
    /// </summary>
    WebAssembly,

    /// <summary>
    /// Use this to source generate targeting the synchronous <c>IJSRuntime</c> type.
    /// </summary>
    Server
};

// Copyright (c) David Pine. All rights reserved.
// Licensed under the MIT License:
// https://bit.ly/blazorators-license
// Auto-generated by blazorators.
using Blazor.Serialization.Extensions;
using System.Text.Json;

#nullable enable
namespace BlazorApp2;
/// <summary>
/// Source generated interface definition of the <c>Storage</c> type.
/// </summary>
public partial interface ILocalStorageService
{
    /// <summary>
    /// Source generated implementation of <c>window.localStorage.clear</c>.
    /// <a href="https://developer.mozilla.org/docs/Web/API/Storage/clear"></a>
    /// </summary>
    void Clear();
    /// <summary>
    /// Source generated implementation of <c>window.localStorage.getItem</c>.
    /// <a href="https://developer.mozilla.org/docs/Web/API/Storage/getItem"></a>
    /// </summary>
    TValue? GetItem<TValue>(string key, JsonSerializerOptions? options = null);
    /// <summary>
    /// Source generated implementation of <c>window.localStorage.key</c>.
    /// <a href="https://developer.mozilla.org/docs/Web/API/Storage/key"></a>
    /// </summary>
    string? Key(double index);
    /// <summary>
    /// Source generated implementation of <c>window.localStorage.removeItem</c>.
    /// <a href="https://developer.mozilla.org/docs/Web/API/Storage/removeItem"></a>
    /// </summary>
    void RemoveItem(string key);
    /// <summary>
    /// Source generated implementation of <c>window.localStorage.setItem</c>.
    /// <a href="https://developer.mozilla.org/docs/Web/API/Storage/setItem"></a>
    /// </summary>
    void SetItem<TValue>(string key, TValue value, JsonSerializerOptions? options = null);
    /// <summary>
    /// Source generated implementation of <c>window.localStorage.length</c>.
    /// <a href="https://developer.mozilla.org/docs/Web/API/Storage/length"></a>
    /// </summary>
    double Length { get; }
}
#nullable enable
/// <summary>
/// Use this attribute on <code>public static partial</code> extension method classes.
/// For example:
/// <example>
/// <code>
/// [JSAutoGenericInterop(
///    TypeName = "Storage",
///    Implementation = "window.localStorage",
///    HostingModel = BlazorHostingModel.WebAssembly,
///    Url = "https://developer.mozilla.org/docs/Web/API/Window/localStorage",
///    GenericMethodDescriptors = new[]
///    {
///        "getItem",
///        "setItem:value"
///    })]
/// public static partial LocalStorageExtensions
/// {
/// }
/// </code>
/// </example>
/// This will source generate all the extension methods for the IJSInProcessRuntime type for the localStorage APIs.
/// </summary>
public class JSAutoGenericInteropAttribute : JSAutoInteropAttribute
{
    /// <summary>
    /// The descriptors that define which APIs are to use default JSON serialization and support generics.
    /// For example:
    /// <code>
    /// new[]
    /// {
    ///     "getItem",      // Serializes the return type of getItem as TValue
    ///     "setItem:value" // Serializes the value parameter of the setItem TValue
    /// }
    /// </code>
    /// </summary>
    public string[] GenericMethodDescriptors { get; set; } = null!;

    /// <summary>
    /// The overrides that define which APIs to override (only applicable for pure JavaScript).
    /// For example:
    /// <code>
    /// new[]
    /// {
    ///     "getVoices",  // A pure JS method with by this name will have a custom impl.
    /// }
    /// </code>
    /// </summary>
    public string[] PureJavaScriptOverrides { get; set; } = null!;
}

#nullable enable
/// <summary>
/// Use this attribute on <code>public static partial</code> extension method classes.
/// For example:
/// <code>
/// [JSAutoInterop(
///    TypeName = "Storage",
///    Implementation = "window.localStorage",
///    HostingModel = BlazorHostingModel.WebAssembly,
///    Url = "https://developer.mozilla.org/docs/Web/API/Window/localStorage")]
/// public static partial LocalStorageExtensions
/// {
/// }
/// </code>
/// This will source generate all the extension methods for the IJSInProcessRuntime type for the localStorage APIs.
/// </summary>
[AttributeUsage(
    AttributeTargets.Interface,
    Inherited = false,
    AllowMultiple = false)]
public class JSAutoInteropAttribute : Attribute
{
    /// <summary>
    /// The type name that corresponds to the lib.dom.d.ts interface. For example, <c>"Geolocation"</c>.
    /// For more information, search 'interface {Name}'
    /// <a href='https://raw.githubusercontent.com/microsoft/TypeScript/main/lib/lib.dom.d.ts'>here for types</a>.
    /// </summary>
    public string TypeName { get; set; } = null!;

    /// <summary>
    /// The path from the <c>window</c> object to the corresponding <see cref="TypeName"/> implementation.
    /// For example, if the <see cref="TypeName"/> was <c>"Geolocation"</c>, this would be
    /// <c>"window.navigator.geolocation"</c> (or <c>"navigator.geolocation"</c>).
    /// </summary>
    public string Implementation { get; set; } = null!;

    /// <summary>
    /// Whether to generate only pure JavaScript functions that do not require callbacks.
    /// For example, <c>"Geolocation.clearWatch"</c> is consider pure, but <c>"Geolocation.watchPosition"</c> is not.
    /// Defaults to <c>true</c>.
    /// </summary>
    public bool OnlyGeneratePureJS { get; set; } = true;

    /// <summary>
    /// The Blazor hosting model to generate source for. WebAssembly creates <c>IJSInProcessRuntime</c> extensions,
    /// while Server creates <c>IJSRuntime</c> extensions. Defaults to <see cref="BlazorHostingModel.WebAssembly" />.
    /// </summary>
    public BlazorHostingModel HostingModel { get; set; } = BlazorHostingModel.WebAssembly;

    /// <summary>
    /// The optional URL to the corresponding API.
    /// </summary>
    public string? Url { get; set; }

    /// <summary>
    /// An optional array of TypeScript type declarations sources. Valid values are URLs or file paths.
    /// </summary>
    public string[]? TypeDeclarationSources { get; set; }
}

// Copyright (c) David Pine. All rights reserved.
// Licensed under the MIT License:
// https://bit.ly/blazorators-license
// Auto-generated by blazorators.
using Blazor.Serialization.Extensions;
using System.Text.Json;

#nullable enable
namespace BlazorApp2;
/// <inheritdoc/>
internal sealed class LocalStorageService : ILocalStorageService
{
    internal readonly IJSInProcessRuntime _javaScript = null !;
    public LocalStorageService(IJSInProcessRuntime javaScript) => _javaScript = javaScript;
    /// <inheritdoc cref = "ILocalStorageService.Clear"/>
    void ILocalStorageService.Clear() => _javaScript.InvokeVoid("window.localStorage.clear");
    /// <inheritdoc cref = "ILocalStorageService.GetItem"/>
    TValue? ILocalStorageService.GetItem<TValue>(string key, JsonSerializerOptions? options)
        where TValue : default => _javaScript.Invoke<string?>("window.localStorage.getItem", key).FromJson<TValue>(options);
    /// <inheritdoc cref = "ILocalStorageService.Key"/>
    string? ILocalStorageService.Key(double index) => _javaScript.Invoke<string?>("window.localStorage.key", index);
    /// <inheritdoc cref = "ILocalStorageService.RemoveItem"/>
    void ILocalStorageService.RemoveItem(string key) => _javaScript.InvokeVoid("window.localStorage.removeItem", key);
    /// <inheritdoc cref = "ILocalStorageService.SetItem"/>
    void ILocalStorageService.SetItem<TValue>(string key, TValue value, JsonSerializerOptions? options) => _javaScript.InvokeVoid("window.localStorage.setItem", key, value.ToJson(options));
    /// <inheritdoc cref = "ILocalStorageService.Length"/>
    double ILocalStorageService.Length => _javaScript.Invoke<double>("eval", "window.localStorage.length");
}
// Copyright (c) David Pine. All rights reserved.
// Licensed under the MIT License:
// https://github.com/IEvangelist/blazorators/blob/main/LICENSE
// Auto-generated by blazorators.

using Microsoft.JSInterop;

namespace Microsoft.Extensions.DependencyInjection;

/// <summary></summary>
public static class LocalStorageServiceCollectionExtensions
{
    /// <summary>
    /// Adds the <see cref="ILocalStorageService" /> service to the service collection.
    /// </summary>
    public static IServiceCollection AddLocalStorageServices(
        this IServiceCollection services) =>
        services.AddSingleton<IJSInProcessRuntime>(serviceProvider =>
            (IJSInProcessRuntime)serviceProvider.GetRequiredService<IJSRuntime>())
            .AddSingleton<ILocalStorageService, LocalStorageService>();
}

using System.ComponentModel;

namespace System.Runtime.CompilerServices
{
    [EditorBrowsable(EditorBrowsableState.Never)]
    internal class IsExternalInit { }
}
#pragma checksum "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\App.razor" "{8829d00f-11b8-4213-878b-770e8597ac16}" "ca69fbc161c0130d6d7831728befc975abb17b04491a271bc49266261055543b"
// <auto-generated/>
#pragma warning disable 1591
namespace BlazorApp2
{
    #line hidden
    using global::System;
    using global::System.Collections.Generic;
    using global::System.Linq;
    using global::System.Threading.Tasks;
    using global::Microsoft.AspNetCore.Components;
#nullable restore
#line 1 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 2 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http.Json;

#line default
#line hidden
#nullable disable
#nullable restore
#line 3 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Forms;

#line default
#line hidden
#nullable disable
#nullable restore
#line 4 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Routing;

#line default
#line hidden
#nullable disable
#nullable restore
#line 5 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web;

#line default
#line hidden
#nullable disable
#nullable restore
#line 6 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web.Virtualization;

#line default
#line hidden
#nullable disable
#nullable restore
#line 7 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.WebAssembly.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 8 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.JSInterop;

#line default
#line hidden
#nullable disable
#nullable restore
#line 9 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2;

#line default
#line hidden
#nullable disable
#nullable restore
#line 10 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2.Layout;

#line default
#line hidden
#nullable disable
    public partial class App : global::Microsoft.AspNetCore.Components.ComponentBase
    {
        #pragma warning disable 1998
        protected override void BuildRenderTree(global::Microsoft.AspNetCore.Components.Rendering.RenderTreeBuilder __builder)
        {
            __builder.OpenComponent<global::Microsoft.AspNetCore.Components.Routing.Router>(0);
            __builder.AddComponentParameter(1, "AppAssembly", global::Microsoft.AspNetCore.Components.CompilerServices.RuntimeHelpers.TypeCheck<global::System.Reflection.Assembly>(
#nullable restore
#line 1 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\App.razor"
                      typeof(App).Assembly

#line default
#line hidden
#nullable disable
            ));
            __builder.AddAttribute(2, "Found", (global::Microsoft.AspNetCore.Components.RenderFragment<Microsoft.AspNetCore.Components.RouteData>)((routeData) => (__builder2) => {
                __builder2.OpenComponent<global::Microsoft.AspNetCore.Components.RouteView>(3);
                __builder2.AddComponentParameter(4, "RouteData", global::Microsoft.AspNetCore.Components.CompilerServices.RuntimeHelpers.TypeCheck<global::Microsoft.AspNetCore.Components.RouteData>(
#nullable restore
#line 3 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\App.razor"
                               routeData

#line default
#line hidden
#nullable disable
                ));
                __builder2.AddComponentParameter(5, "DefaultLayout", global::Microsoft.AspNetCore.Components.CompilerServices.RuntimeHelpers.TypeCheck<global::System.Type>(
#nullable restore
#line 3 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\App.razor"
                                                          typeof(MainLayout)

#line default
#line hidden
#nullable disable
                ));
                __builder2.CloseComponent();
                __builder2.AddMarkupContent(6, "\r\n        ");
                __builder2.OpenComponent<global::Microsoft.AspNetCore.Components.Routing.FocusOnNavigate>(7);
                __builder2.AddComponentParameter(8, "RouteData", global::Microsoft.AspNetCore.Components.CompilerServices.RuntimeHelpers.TypeCheck<global::Microsoft.AspNetCore.Components.RouteData>(
#nullable restore
#line 4 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\App.razor"
                                     routeData

#line default
#line hidden
#nullable disable
                ));
                __builder2.AddComponentParameter(9, "Selector", "h1");
                __builder2.CloseComponent();
            }
            ));
            __builder.AddAttribute(10, "NotFound", (global::Microsoft.AspNetCore.Components.RenderFragment)((__builder2) => {
                __builder2.OpenComponent<global::Microsoft.AspNetCore.Components.Web.PageTitle>(11);
                __builder2.AddAttribute(12, "ChildContent", (global::Microsoft.AspNetCore.Components.RenderFragment)((__builder3) => {
                    __builder3.AddContent(13, "Not found");
                }
                ));
                __builder2.CloseComponent();
                __builder2.AddMarkupContent(14, "\r\n        ");
                __builder2.OpenComponent<global::Microsoft.AspNetCore.Components.LayoutView>(15);
                __builder2.AddComponentParameter(16, "Layout", global::Microsoft.AspNetCore.Components.CompilerServices.RuntimeHelpers.TypeCheck<global::System.Type>(
#nullable restore
#line 8 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\App.razor"
                             typeof(MainLayout)

#line default
#line hidden
#nullable disable
                ));
                __builder2.AddAttribute(17, "ChildContent", (global::Microsoft.AspNetCore.Components.RenderFragment)((__builder3) => {
                    __builder3.AddMarkupContent(18, "<p role=\"alert\">Sorry, there\'s nothing at this address.</p>");
                }
                ));
                __builder2.CloseComponent();
            }
            ));
            __builder.CloseComponent();
        }
        #pragma warning restore 1998
    }
}
#pragma warning restore 1591

#pragma checksum "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Layout\MainLayout.razor" "{8829d00f-11b8-4213-878b-770e8597ac16}" "93d4b940f2ce228e270b07368e54f6d439ffc44bc31096274325558e65d2157f"
// <auto-generated/>
#pragma warning disable 1591
namespace BlazorApp2.Layout
{
    #line hidden
    using global::System;
    using global::System.Collections.Generic;
    using global::System.Linq;
    using global::System.Threading.Tasks;
    using global::Microsoft.AspNetCore.Components;
#nullable restore
#line 1 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 2 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http.Json;

#line default
#line hidden
#nullable disable
#nullable restore
#line 3 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Forms;

#line default
#line hidden
#nullable disable
#nullable restore
#line 4 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Routing;

#line default
#line hidden
#nullable disable
#nullable restore
#line 5 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web;

#line default
#line hidden
#nullable disable
#nullable restore
#line 6 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web.Virtualization;

#line default
#line hidden
#nullable disable
#nullable restore
#line 7 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.WebAssembly.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 8 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.JSInterop;

#line default
#line hidden
#nullable disable
#nullable restore
#line 9 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2;

#line default
#line hidden
#nullable disable
#nullable restore
#line 10 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2.Layout;

#line default
#line hidden
#nullable disable
    public partial class MainLayout : LayoutComponentBase
    {
        #pragma warning disable 1998
        protected override void BuildRenderTree(global::Microsoft.AspNetCore.Components.Rendering.RenderTreeBuilder __builder)
        {
            __builder.OpenElement(0, "div");
            __builder.AddAttribute(1, "class", "page");
            __builder.AddAttribute(2, "b-iwvdxzpj6w");
            __builder.OpenElement(3, "div");
            __builder.AddAttribute(4, "class", "sidebar");
            __builder.AddAttribute(5, "b-iwvdxzpj6w");
            __builder.OpenComponent<global::BlazorApp2.Layout.NavMenu>(6);
            __builder.CloseComponent();
            __builder.CloseElement();
            __builder.AddMarkupContent(7, "\r\n\r\n    ");
            __builder.OpenElement(8, "main");
            __builder.AddAttribute(9, "b-iwvdxzpj6w");
            __builder.AddMarkupContent(10, "<div class=\"top-row px-4\" b-iwvdxzpj6w><a href=\"https://learn.microsoft.com/aspnet/core/\" target=\"_blank\" b-iwvdxzpj6w>About</a></div>\r\n\r\n        ");
            __builder.OpenElement(11, "article");
            __builder.AddAttribute(12, "class", "content px-4");
            __builder.AddAttribute(13, "b-iwvdxzpj6w");
#nullable restore
#line (13,14)-(13,18) 25 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Layout\MainLayout.razor"
__builder.AddContent(14, Body);

#line default
#line hidden
#nullable disable
            __builder.CloseElement();
            __builder.CloseElement();
            __builder.CloseElement();
        }
        #pragma warning restore 1998
    }
}
#pragma warning restore 1591

#pragma checksum "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Layout\NavMenu.razor" "{8829d00f-11b8-4213-878b-770e8597ac16}" "4ed23773930f65532bdb0b17b15ff5e805d3c4e59aad805d432503d0191cd0a9"
// <auto-generated/>
#pragma warning disable 1591
namespace BlazorApp2.Layout
{
    #line hidden
    using global::System;
    using global::System.Collections.Generic;
    using global::System.Linq;
    using global::System.Threading.Tasks;
    using global::Microsoft.AspNetCore.Components;
#nullable restore
#line 1 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 2 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http.Json;

#line default
#line hidden
#nullable disable
#nullable restore
#line 3 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Forms;

#line default
#line hidden
#nullable disable
#nullable restore
#line 4 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Routing;

#line default
#line hidden
#nullable disable
#nullable restore
#line 5 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web;

#line default
#line hidden
#nullable disable
#nullable restore
#line 6 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web.Virtualization;

#line default
#line hidden
#nullable disable
#nullable restore
#line 7 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.WebAssembly.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 8 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.JSInterop;

#line default
#line hidden
#nullable disable
#nullable restore
#line 9 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2;

#line default
#line hidden
#nullable disable
#nullable restore
#line 10 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2.Layout;

#line default
#line hidden
#nullable disable
    public partial class NavMenu : global::Microsoft.AspNetCore.Components.ComponentBase
    {
        #pragma warning disable 1998
        protected override void BuildRenderTree(global::Microsoft.AspNetCore.Components.Rendering.RenderTreeBuilder __builder)
        {
            __builder.OpenElement(0, "div");
            __builder.AddAttribute(1, "class", "top-row ps-3 navbar navbar-dark");
            __builder.AddAttribute(2, "b-18uzve78me");
            __builder.OpenElement(3, "div");
            __builder.AddAttribute(4, "class", "container-fluid");
            __builder.AddAttribute(5, "b-18uzve78me");
            __builder.AddMarkupContent(6, "<a class=\"navbar-brand\" href b-18uzve78me>BlazorApp2</a>\r\n        ");
            __builder.OpenElement(7, "button");
            __builder.AddAttribute(8, "title", "Navigation menu");
            __builder.AddAttribute(9, "class", "navbar-toggler");
            __builder.AddAttribute(10, "onclick", global::Microsoft.AspNetCore.Components.EventCallback.Factory.Create<global::Microsoft.AspNetCore.Components.Web.MouseEventArgs>(this, 
#nullable restore
#line 4 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Layout\NavMenu.razor"
                                                                         ToggleNavMenu

#line default
#line hidden
#nullable disable
            ));
            __builder.AddAttribute(11, "b-18uzve78me");
            __builder.AddMarkupContent(12, "<span class=\"navbar-toggler-icon\" b-18uzve78me></span>");
            __builder.CloseElement();
            __builder.CloseElement();
            __builder.CloseElement();
            __builder.AddMarkupContent(13, "\r\n\r\n");
            __builder.OpenElement(14, "div");
            __builder.AddAttribute(15, "class", (
#nullable restore
#line 10 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Layout\NavMenu.razor"
             NavMenuCssClass

#line default
#line hidden
#nullable disable
            ) + " nav-scrollable");
            __builder.AddAttribute(16, "onclick", global::Microsoft.AspNetCore.Components.EventCallback.Factory.Create<global::Microsoft.AspNetCore.Components.Web.MouseEventArgs>(this, 
#nullable restore
#line 10 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Layout\NavMenu.razor"
                                                       ToggleNavMenu

#line default
#line hidden
#nullable disable
            ));
            __builder.AddAttribute(17, "b-18uzve78me");
            __builder.OpenElement(18, "nav");
            __builder.AddAttribute(19, "class", "flex-column");
            __builder.AddAttribute(20, "b-18uzve78me");
            __builder.OpenElement(21, "div");
            __builder.AddAttribute(22, "class", "nav-item px-3");
            __builder.AddAttribute(23, "b-18uzve78me");
            __builder.OpenComponent<global::Microsoft.AspNetCore.Components.Routing.NavLink>(24);
            __builder.AddComponentParameter(25, "class", "nav-link");
            __builder.AddComponentParameter(26, "href", "");
            __builder.AddComponentParameter(27, "Match", global::Microsoft.AspNetCore.Components.CompilerServices.RuntimeHelpers.TypeCheck<global::Microsoft.AspNetCore.Components.Routing.NavLinkMatch>(
#nullable restore
#line 13 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Layout\NavMenu.razor"
                                                     NavLinkMatch.All

#line default
#line hidden
#nullable disable
            ));
            __builder.AddAttribute(28, "ChildContent", (global::Microsoft.AspNetCore.Components.RenderFragment)((__builder2) => {
                __builder2.AddMarkupContent(29, "<span class=\"bi bi-house-door-fill-nav-menu\" aria-hidden=\"true\" b-18uzve78me></span> Home\r\n            ");
            }
            ));
            __builder.CloseComponent();
            __builder.CloseElement();
            __builder.AddMarkupContent(30, "\r\n        ");
            __builder.OpenElement(31, "div");
            __builder.AddAttribute(32, "class", "nav-item px-3");
            __builder.AddAttribute(33, "b-18uzve78me");
            __builder.OpenComponent<global::Microsoft.AspNetCore.Components.Routing.NavLink>(34);
            __builder.AddComponentParameter(35, "class", "nav-link");
            __builder.AddComponentParameter(36, "href", "counter");
            __builder.AddAttribute(37, "ChildContent", (global::Microsoft.AspNetCore.Components.RenderFragment)((__builder2) => {
                __builder2.AddMarkupContent(38, "<span class=\"bi bi-plus-square-fill-nav-menu\" aria-hidden=\"true\" b-18uzve78me></span> Counter\r\n            ");
            }
            ));
            __builder.CloseComponent();
            __builder.CloseElement();
            __builder.AddMarkupContent(39, "\r\n        ");
            __builder.OpenElement(40, "div");
            __builder.AddAttribute(41, "class", "nav-item px-3");
            __builder.AddAttribute(42, "b-18uzve78me");
            __builder.OpenComponent<global::Microsoft.AspNetCore.Components.Routing.NavLink>(43);
            __builder.AddComponentParameter(44, "class", "nav-link");
            __builder.AddComponentParameter(45, "href", "weather");
            __builder.AddAttribute(46, "ChildContent", (global::Microsoft.AspNetCore.Components.RenderFragment)((__builder2) => {
                __builder2.AddMarkupContent(47, "<span class=\"bi bi-list-nested-nav-menu\" aria-hidden=\"true\" b-18uzve78me></span> Weather\r\n            ");
            }
            ));
            __builder.CloseComponent();
            __builder.CloseElement();
            __builder.CloseElement();
            __builder.CloseElement();
        }
        #pragma warning restore 1998
#nullable restore
#line 30 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Layout\NavMenu.razor"
       
    private bool collapseNavMenu = true;

    private string? NavMenuCssClass => collapseNavMenu ? "collapse" : null;

    private void ToggleNavMenu()
    {
        collapseNavMenu = !collapseNavMenu;
    }

#line default
#line hidden
#nullable disable
    }
}
#pragma warning restore 1591

#pragma checksum "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Counter.razor" "{8829d00f-11b8-4213-878b-770e8597ac16}" "886d5e15f1c63f4cc1caec7ff58936690cc18dd69931479d26471f7575854ec2"
// <auto-generated/>
#pragma warning disable 1591
namespace BlazorApp2.Pages
{
    #line hidden
    using global::System;
    using global::System.Collections.Generic;
    using global::System.Linq;
    using global::System.Threading.Tasks;
    using global::Microsoft.AspNetCore.Components;
#nullable restore
#line 1 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 2 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http.Json;

#line default
#line hidden
#nullable disable
#nullable restore
#line 3 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Forms;

#line default
#line hidden
#nullable disable
#nullable restore
#line 4 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Routing;

#line default
#line hidden
#nullable disable
#nullable restore
#line 5 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web;

#line default
#line hidden
#nullable disable
#nullable restore
#line 6 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web.Virtualization;

#line default
#line hidden
#nullable disable
#nullable restore
#line 7 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.WebAssembly.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 8 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.JSInterop;

#line default
#line hidden
#nullable disable
#nullable restore
#line 9 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2;

#line default
#line hidden
#nullable disable
#nullable restore
#line 10 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2.Layout;

#line default
#line hidden
#nullable disable
    [global::Microsoft.AspNetCore.Components.RouteAttribute("/counter")]
    public partial class Counter : global::Microsoft.AspNetCore.Components.ComponentBase
    {
        #pragma warning disable 1998
        protected override void BuildRenderTree(global::Microsoft.AspNetCore.Components.Rendering.RenderTreeBuilder __builder)
        {
            __builder.OpenComponent<global::Microsoft.AspNetCore.Components.Web.PageTitle>(0);
            __builder.AddAttribute(1, "ChildContent", (global::Microsoft.AspNetCore.Components.RenderFragment)((__builder2) => {
                __builder2.AddContent(2, "Counter");
            }
            ));
            __builder.CloseComponent();
            __builder.AddMarkupContent(3, "\r\n\r\n");
            __builder.AddMarkupContent(4, "<h1>Counter</h1>\r\n\r\n");
            __builder.OpenElement(5, "p");
            __builder.AddAttribute(6, "role", "status");
            __builder.AddContent(7, "Current count: ");
#nullable restore
#line (7,34)-(7,46) 24 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Counter.razor"
__builder.AddContent(8, currentCount);

#line default
#line hidden
#nullable disable
            __builder.CloseElement();
            __builder.AddMarkupContent(9, "\r\n\r\n");
            __builder.OpenElement(10, "button");
            __builder.AddAttribute(11, "class", "btn btn-primary");
            __builder.AddAttribute(12, "onclick", global::Microsoft.AspNetCore.Components.EventCallback.Factory.Create<global::Microsoft.AspNetCore.Components.Web.MouseEventArgs>(this, 
#nullable restore
#line 9 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Counter.razor"
                                          IncrementCount

#line default
#line hidden
#nullable disable
            ));
            __builder.AddContent(13, "Click me");
            __builder.CloseElement();
        }
        #pragma warning restore 1998
#nullable restore
#line 11 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Counter.razor"
       
    private int currentCount = 0;

    private void IncrementCount()
    {
        currentCount++;
    }

#line default
#line hidden
#nullable disable
    }
}
#pragma warning restore 1591

#pragma checksum "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Home.razor" "{8829d00f-11b8-4213-878b-770e8597ac16}" "3aa0919abc135f80e5cf81940d496935db1ecddffc2b0b077d38018b20b6d726"
// <auto-generated/>
#pragma warning disable 1591
namespace BlazorApp2.Pages
{
    #line hidden
    using global::System;
    using global::System.Collections.Generic;
    using global::System.Linq;
    using global::System.Threading.Tasks;
    using global::Microsoft.AspNetCore.Components;
#nullable restore
#line 1 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 2 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http.Json;

#line default
#line hidden
#nullable disable
#nullable restore
#line 3 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Forms;

#line default
#line hidden
#nullable disable
#nullable restore
#line 4 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Routing;

#line default
#line hidden
#nullable disable
#nullable restore
#line 5 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web;

#line default
#line hidden
#nullable disable
#nullable restore
#line 6 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web.Virtualization;

#line default
#line hidden
#nullable disable
#nullable restore
#line 7 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.WebAssembly.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 8 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.JSInterop;

#line default
#line hidden
#nullable disable
#nullable restore
#line 9 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2;

#line default
#line hidden
#nullable disable
#nullable restore
#line 10 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2.Layout;

#line default
#line hidden
#nullable disable
    [global::Microsoft.AspNetCore.Components.RouteAttribute("/")]
    public partial class Home : global::Microsoft.AspNetCore.Components.ComponentBase
    {
        #pragma warning disable 1998
        protected override void BuildRenderTree(global::Microsoft.AspNetCore.Components.Rendering.RenderTreeBuilder __builder)
        {
            __builder.OpenComponent<global::Microsoft.AspNetCore.Components.Web.PageTitle>(0);
            __builder.AddAttribute(1, "ChildContent", (global::Microsoft.AspNetCore.Components.RenderFragment)((__builder2) => {
                __builder2.AddContent(2, "Home");
            }
            ));
            __builder.CloseComponent();
            __builder.AddMarkupContent(3, "\r\n\r\n");
            __builder.AddMarkupContent(4, "<h1>Hello, world!</h1>\r\n\r\nPlease refresh the page to see the value persisted in local storage.\r\n");
#nullable restore
#line 9 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Home.razor"
  
    var name = MyLocalStorage.GetItem<string>("name");
    if (name != null)
    {

#line default
#line hidden
#nullable disable
            __builder.OpenElement(5, "p");
            __builder.AddContent(6, "Hi, ");
#nullable restore
#line (13,17)-(13,21) 24 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Home.razor"
__builder.AddContent(7, name);

#line default
#line hidden
#nullable disable
            __builder.CloseElement();
#nullable restore
#line 14 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Home.razor"
    }
    else
    {

#line default
#line hidden
#nullable disable
            __builder.AddMarkupContent(8, "<p>Hi, stranger</p>");
#nullable restore
#line 18 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Home.razor"
    }
    MyLocalStorage.SetItem("name", "Andrei Ignat");

#line default
#line hidden
#nullable disable
        }
        #pragma warning restore 1998
        [global::Microsoft.AspNetCore.Components.InjectAttribute] private ILocalStorageService MyLocalStorage { get; set; }
    }
}
#pragma warning restore 1591

#pragma checksum "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Weather.razor" "{8829d00f-11b8-4213-878b-770e8597ac16}" "91e0cba167af58d4c1dbd17785187574d7b8431106eb9fc9b48193bb1e109a61"
// <auto-generated/>
#pragma warning disable 1591
namespace BlazorApp2.Pages
{
    #line hidden
    using global::System;
    using global::System.Collections.Generic;
    using global::System.Linq;
    using global::System.Threading.Tasks;
    using global::Microsoft.AspNetCore.Components;
#nullable restore
#line 1 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 2 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http.Json;

#line default
#line hidden
#nullable disable
#nullable restore
#line 3 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Forms;

#line default
#line hidden
#nullable disable
#nullable restore
#line 4 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Routing;

#line default
#line hidden
#nullable disable
#nullable restore
#line 5 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web;

#line default
#line hidden
#nullable disable
#nullable restore
#line 6 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web.Virtualization;

#line default
#line hidden
#nullable disable
#nullable restore
#line 7 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.WebAssembly.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 8 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.JSInterop;

#line default
#line hidden
#nullable disable
#nullable restore
#line 9 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2;

#line default
#line hidden
#nullable disable
#nullable restore
#line 10 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2.Layout;

#line default
#line hidden
#nullable disable
    [global::Microsoft.AspNetCore.Components.RouteAttribute("/weather")]
    public partial class Weather : global::Microsoft.AspNetCore.Components.ComponentBase
    {
        #pragma warning disable 1998
        protected override void BuildRenderTree(global::Microsoft.AspNetCore.Components.Rendering.RenderTreeBuilder __builder)
        {
            __builder.OpenComponent<global::Microsoft.AspNetCore.Components.Web.PageTitle>(0);
            __builder.AddAttribute(1, "ChildContent", (global::Microsoft.AspNetCore.Components.RenderFragment)((__builder2) => {
                __builder2.AddContent(2, "Weather");
            }
            ));
            __builder.CloseComponent();
            __builder.AddMarkupContent(3, "\r\n\r\n");
            __builder.AddMarkupContent(4, "<h1>Weather</h1>\r\n\r\n");
            __builder.AddMarkupContent(5, "<p>This component demonstrates fetching data from the server.</p>");
#nullable restore
#line 10 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Weather.razor"
 if (forecasts == null)
{

#line default
#line hidden
#nullable disable
            __builder.AddMarkupContent(6, "<p><em>Loading...</em></p>");
#nullable restore
#line 13 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Weather.razor"
}
else
{

#line default
#line hidden
#nullable disable
            __builder.OpenElement(7, "table");
            __builder.AddAttribute(8, "class", "table");
            __builder.AddMarkupContent(9, "<thead><tr><th>Date</th>\r\n                <th>Temp. (C)</th>\r\n                <th>Temp. (F)</th>\r\n                <th>Summary</th></tr></thead>\r\n        ");
            __builder.OpenElement(10, "tbody");
#nullable restore
#line 26 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Weather.razor"
             foreach (var forecast in forecasts)
            {

#line default
#line hidden
#nullable disable
            __builder.OpenElement(11, "tr");
            __builder.OpenElement(12, "td");
#nullable restore
#line (29,26)-(29,59) 25 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Weather.razor"
__builder.AddContent(13, forecast.Date.ToShortDateString());

#line default
#line hidden
#nullable disable
            __builder.CloseElement();
            __builder.AddMarkupContent(14, "\r\n                    ");
            __builder.OpenElement(15, "td");
#nullable restore
#line (30,26)-(30,47) 25 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Weather.razor"
__builder.AddContent(16, forecast.TemperatureC);

#line default
#line hidden
#nullable disable
            __builder.CloseElement();
            __builder.AddMarkupContent(17, "\r\n                    ");
            __builder.OpenElement(18, "td");
#nullable restore
#line (31,26)-(31,47) 25 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Weather.razor"
__builder.AddContent(19, forecast.TemperatureF);

#line default
#line hidden
#nullable disable
            __builder.CloseElement();
            __builder.AddMarkupContent(20, "\r\n                    ");
            __builder.OpenElement(21, "td");
#nullable restore
#line (32,26)-(32,42) 25 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Weather.razor"
__builder.AddContent(22, forecast.Summary);

#line default
#line hidden
#nullable disable
            __builder.CloseElement();
            __builder.CloseElement();
#nullable restore
#line 34 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Weather.razor"
            }

#line default
#line hidden
#nullable disable
            __builder.CloseElement();
            __builder.CloseElement();
#nullable restore
#line 37 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Weather.razor"
}

#line default
#line hidden
#nullable disable
        }
        #pragma warning restore 1998
#nullable restore
#line 39 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\Pages\Weather.razor"
       
    private WeatherForecast[]? forecasts;

    protected override async Task OnInitializedAsync()
    {
        forecasts = await Http.GetFromJsonAsync<WeatherForecast[]>("sample-data/weather.json");
    }

    public class WeatherForecast
    {
        public DateOnly Date { get; set; }

        public int TemperatureC { get; set; }

        public string? Summary { get; set; }

        public int TemperatureF => 32 + (int)(TemperatureC / 0.5556);
    }

#line default
#line hidden
#nullable disable
        [global::Microsoft.AspNetCore.Components.InjectAttribute] private HttpClient Http { get; set; }
    }
}
#pragma warning restore 1591

#pragma checksum "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor" "{8829d00f-11b8-4213-878b-770e8597ac16}" "d065d06a7544abc87a0d6ac6e4b47ca33ed0bc373f5ec7b85b2aa4d888f77d3e"
// <auto-generated/>
#pragma warning disable 1591
namespace BlazorApp2
{
    #line hidden
    using global::System;
    using global::System.Collections.Generic;
    using global::System.Linq;
    using global::System.Threading.Tasks;
    using global::Microsoft.AspNetCore.Components;
#nullable restore
#line 1 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 2 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using System.Net.Http.Json;

#line default
#line hidden
#nullable disable
#nullable restore
#line 3 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Forms;

#line default
#line hidden
#nullable disable
#nullable restore
#line 4 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Routing;

#line default
#line hidden
#nullable disable
#nullable restore
#line 5 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web;

#line default
#line hidden
#nullable disable
#nullable restore
#line 6 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.Web.Virtualization;

#line default
#line hidden
#nullable disable
#nullable restore
#line 7 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.AspNetCore.Components.WebAssembly.Http;

#line default
#line hidden
#nullable disable
#nullable restore
#line 8 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using Microsoft.JSInterop;

#line default
#line hidden
#nullable disable
#nullable restore
#line 9 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2;

#line default
#line hidden
#nullable disable
#nullable restore
#line 10 "C:\Users\ignat\Downloads\BlazorAppFullRef1\BlazorApp2\_Imports.razor"
using BlazorApp2.Layout;

#line default
#line hidden
#nullable disable
    public partial class _Imports : global::Microsoft.AspNetCore.Components.ComponentBase
    {
        #pragma warning disable 1998
        protected override void BuildRenderTree(global::Microsoft.AspNetCore.Components.Rendering.RenderTreeBuilder __builder)
        {
        }
        #pragma warning restore 1998
    }
}
#pragma warning restore 1591

Code and pdf at

https://ignatandrei.github.io/RSCG_Examples/v2/docs/Blazorators

RSCG – Chorn.EmbeddedResourceAccessGenerator

RSCG – Chorn.EmbeddedResourceAccessGenerator
 
 

name Chorn.EmbeddedResourceAccessGenerator
nuget https://www.nuget.org/packages/Chorn.EmbeddedResourceAccessGenerator/
link https://github.com/ChristophHornung/EmbeddedResourceGenerator
author Christoph Hornung

Embedded Resources to C# Code

 

This is how you can use Chorn.EmbeddedResourceAccessGenerator .

The code that you start with is


<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>net8.0</TargetFramework>
    <ImplicitUsings>enable</ImplicitUsings>
    <Nullable>enable</Nullable>
  </PropertyGroup>

  <PropertyGroup>
		<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
		<CompilerGeneratedFilesOutputPath>$(BaseIntermediateOutputPath)\GX</CompilerGeneratedFilesOutputPath>
	</PropertyGroup>
	<ItemGroup>
	  <EmbeddedResource  Include="sql/*.sql" />
	</ItemGroup>
	<ItemGroup>
	  <PackageReference Include="Chorn.EmbeddedResourceAccessGenerator" Version="1.1.5" OutputItemType="Analyzer"  >
	    <PrivateAssets>all</PrivateAssets>
	    <IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
	  </PackageReference>
	</ItemGroup>
	
	
</Project>


The code that you will use is


using EmbedDemo;
using StreamReader sr = EmbeddedResource.sql_createDB_sql.GetReader();
var data=sr.ReadToEnd();
Console.WriteLine(data);



create database Andrei;
GO;
use Andrei;
GO;


 

The code that is generated is

#nullable enable
namespace EmbedDemo;
using System;
using System.Collections;
using System.IO;
using System.Reflection;

/// <summary>
/// Auto-generated class to access all embedded resources in an assembly.
/// </summary>
public static partial class EmbeddedResources
{
	/// <summary>
	/// Gets the embedded resource 'sql.createDB.sql' as a stream.
	/// </summary>
	/// <returns>The stream to access the embedded resource.</returns>
	public static Stream sql_createDB_sql_Stream
	{
		get {
			Assembly assembly = typeof(EmbeddedResources).Assembly;
			string resource = "EmbedDemo.sql.createDB.sql";
			return assembly.GetManifestResourceStream(resource)!;
		}
	}

	/// <summary>
	/// Gets the embedded resource 'sql.createDB.sql' as a stream-reader.
	/// </summary>
	/// <returns>The stream-reader to access the embedded resource.</returns>
	public static StreamReader sql_createDB_sql_Reader
	{
		get 
		{
			Assembly assembly = typeof(EmbeddedResources).Assembly;
			string resource = "EmbedDemo.sql.createDB.sql";
			return new StreamReader(assembly.GetManifestResourceStream(resource)!);
		}
	}

	/// <summary>
	/// Gets the embedded resource's stream.
	/// </summary>
	/// <param name="resource">The embedded resource to retrieve the stream for.</param>
	/// <returns>The stream to access the embedded resource.</returns>
	public static Stream GetStream(this EmbeddedResource resource)
	{
		Assembly assembly = typeof(EmbeddedResources).Assembly;
		return assembly.GetManifestResourceStream(GetResourceName(resource))!;
	}

	/// <summary>
	/// Gets the embedded resource's stream-reader.
	/// </summary>
	/// <param name="resource">The embedded resource to retrieve the stream-reader for.</param>
	/// <returns>The stream-reader to access the embedded resource.</returns>
	public static StreamReader GetReader(this EmbeddedResource resource)
	{
		Assembly assembly = typeof(EmbeddedResources).Assembly;
		return new StreamReader(assembly.GetManifestResourceStream(GetResourceName(resource))!);
	}

	/// <summary>
	/// Gets the embedded resource's name in the format required by <c>GetManifestResourceStream</c>.
	/// </summary>
	/// <param name="resource">The embedded resource to retrieve the name for.</param>
	/// <returns>The name to access the embedded resource.</returns>
	public static string GetResourceName(this EmbeddedResource resource)
	{
		return resource switch 
		{
			EmbeddedResource.sql_createDB_sql => "EmbedDemo.sql.createDB.sql",
			_ => throw new InvalidOperationException(),
		};
	}

	/// <summary>
	/// Gets the embedded resource's stream.
	/// </summary>
	/// <param name="resource">The embedded resource to retrieve the stream for.</param>
	/// <returns>The stream to access the embedded resource.</returns>
	public static Stream GetStream(this EmbeddedResourcesql resource)
	{
		Assembly assembly = typeof(EmbeddedResources).Assembly;
		return assembly.GetManifestResourceStream(GetResourceName(resource))!;
	}

	/// <summary>
	/// Gets the embedded resource's stream-reader.
	/// </summary>
	/// <param name="resource">The embedded resource to retrieve the stream-reader for.</param>
	/// <returns>The stream-reader to access the embedded resource.</returns>
	public static StreamReader GetReader(this EmbeddedResourcesql resource)
	{
		Assembly assembly = typeof(EmbeddedResources).Assembly;
		return new StreamReader(assembly.GetManifestResourceStream(GetResourceName(resource))!);
	}

	/// <summary>
	/// Gets the embedded resource's name in the format required by <c>GetManifestResourceStream</c>.
	/// </summary>
	/// <param name="resource">The embedded resource to retrieve the name for.</param>
	/// <returns>The name to access the embedded resource.</returns>
	public static string GetResourceName(this EmbeddedResourcesql resource)
	{
		return resource switch 
		{
			EmbeddedResourcesql.createDB_sql => "EmbedDemo.sql.createDB.sql",
			_ => throw new InvalidOperationException(),
		};
	}
}

/// <summary>
/// Auto-generated enumeration for all embedded resources in the assembly.
/// </summary>
public enum EmbeddedResource
{
	/// <summary>
	/// Represents the embedded resource 'sql.createDB.sql'.
	/// </summary>
	sql_createDB_sql,
}

/// <summary>
/// Auto-generated enumeration for all embedded resources in 'sql'.
/// </summary>
public enum EmbeddedResourcesql
{
	/// <summary>
	/// Represents the embedded resource 'createDB.sql' in sql.
	/// </summary>
	createDB_sql,
}
#nullable restore

Code and pdf at

https://ignatandrei.github.io/RSCG_Examples/v2/docs/Chorn.EmbeddedResourceAccessGenerator

RSCG – BuildInfo

RSCG – BuildInfo
 
 

name BuildInfo
nuget https://www.nuget.org/packages/BuildInfo/
link https://github.com/linkdotnet/BuildInformation
author Steven Giesel

Generating build information

 

This is how you can use BuildInfo .

The code that you start with is


<Project Sdk="Microsoft.NET.Sdk">
	<PropertyGroup>
		<OutputType>Exe</OutputType>
		<TargetFramework>netcoreapp7.0</TargetFramework>
	</PropertyGroup>
	<PropertyGroup>
		<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
		<CompilerGeneratedFilesOutputPath>$(BaseIntermediateOutputPath)\GX</CompilerGeneratedFilesOutputPath>
	</PropertyGroup>
	<PropertyGroup>
		<UseRootNamespaceForBuildInformation>true</UseRootNamespaceForBuildInformation>
	</PropertyGroup>

	<ItemGroup>
		<CompilerVisibleProperty Include="UseRootNamespaceForBuildInformation" />
	</ItemGroup>

	<ItemGroup>
	  <PackageReference Include="LinkDotNet.BuildInformation" Version="1.0.0" />
		
	</ItemGroup>
	<PropertyGroup>
		<Version>2024.01.20</Version>
	</PropertyGroup>
</Project>


The code that you will use is


var strVersion = RSCG_Version.BuildInformation.AssemblyVersion;
System.Console.WriteLine(strVersion);


 

The code that is generated is

// <auto-generated>
// This file was generated by the LinkDotNet.BuildInformation package.
//
// Changes to this file may cause incorrect behavior and will be lost if
// the code is regenerated.
// </auto-generated>

using System;
using System.Globalization;

namespace RSCG_Version;

internal static class BuildInformation
{
    /// <summary>
    /// Returns the build date (UTC).
    /// </summary>
    /// <remarks>Value is: 2024-01-21T07:37:28.4648410Z</remarks>
    public static readonly DateTime BuildAt = DateTime.ParseExact("2024-01-21T07:37:28.4648410Z", "O", CultureInfo.InvariantCulture, DateTimeStyles.RoundtripKind);

    /// <summary>
    /// Returns the platform.
    /// </summary>
    /// <remarks>Value is: AnyCpu</remarks>
    public const string Platform = "AnyCpu";

    /// <summary>
    /// Returns the warning level.
    /// </summary>
    /// <remarks>Value is: 7</remarks>
    public const int WarningLevel = 7;

    /// <summary>
    /// Returns the configuration.
    /// </summary>
    /// <remarks>Value is: Release</remarks>
    public const string Configuration = "Release";

    /// <summary>
    /// Returns the assembly version.
    /// </summary>
    /// <remarks>Value is: 2024.1.20.0</remarks>
    public const string AssemblyVersion = "2024.1.20.0";

    /// <summary>
    /// Returns the assembly file version.
    /// </summary>
    /// <remarks>Value is: 2024.1.20.0</remarks>
    public const string AssemblyFileVersion = "2024.1.20.0";

    /// <summary>
    /// Returns the assembly name.
    /// </summary>
    /// <remarks>Value is: RSCG_Version</remarks>
    public const string AssemblyName = "RSCG_Version";

    /// <summary>
    /// Returns the target framework moniker.
    /// </summary>
    /// <remarks>Value is: netcoreapp7.0</remarks>
    public const string TargetFrameworkMoniker = "netcoreapp7.0";

    /// <summary>
    /// Returns the nullability level.
    /// </summary>
    /// <remarks>Value is: Disable</remarks>
    public const string Nullability = "Disable";

    /// <summary>
    /// Returns whether the build is deterministic.
    /// </summary>
    /// <remarks>Value is: true</remarks>
    public const bool Deterministic = true;
}

Code and pdf at

https://ignatandrei.github.io/RSCG_Examples/v2/docs/BuildInfo

RSCG – MakeInterface.Generator

RSCG – MakeInterface.Generator
 
 

name MakeInterface.Generator
nuget https://www.nuget.org/packages/MakeInterface.Generator/
link https://github.com/Frederik91/MakeInterface
author Frederik

Generating interface from class definition

 

This is how you can use MakeInterface.Generator .

The code that you start with is


<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>net8.0</TargetFramework>
    <ImplicitUsings>enable</ImplicitUsings>
    <Nullable>enable</Nullable>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="MakeInterface.Contracts" Version="0.4.0" />
    <PackageReference Include="MakeInterface.Generator" Version="0.4.0" OutputItemType="Analyzer" >
      <PrivateAssets>all</PrivateAssets>
      <IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
    </PackageReference>
  </ItemGroup>
	<PropertyGroup>
		<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
		<CompilerGeneratedFilesOutputPath>$(BaseIntermediateOutputPath)\GX</CompilerGeneratedFilesOutputPath>
	</PropertyGroup>
</Project>


The code that you will use is


// See https://aka.ms/new-console-template for more information
using Class2Interface;

Console.WriteLine("Hello, World!");
IPerson person=new Person();
person.FirstName="Andrei";
person.LastName="Ignat";
Console.WriteLine(person.FullName());


using MakeInterface.Contracts.Attributes;

namespace Class2Interface;
[GenerateInterface]
internal class Person:IPerson
{
    public int ID { get; set; }
    public string FirstName { get; set; }
    public string LastName { get; set; }
    public string Name
    {
        get
        {
            return $"{FirstName} {LastName}";
        }
    }
    public string FullName()
    {
        return $"{FirstName} {LastName}";
    }
}


 

The code that is generated is

using MakeInterface.Contracts.Attributes;

// <auto-generated/>
#pragma warning disable
#nullable enable
namespace Class2Interface;
public partial interface IPerson
{
    int ID { get; set; }

    string FirstName { get; set; }

    string LastName { get; set; }

    string Name { get; }

    string FullName();
}

Code and pdf at

https://ignatandrei.github.io/RSCG_Examples/v2/docs/MakeInterface.Generator

RSCG – Funcky.DiscriminatedUnion

RSCG – Funcky.DiscriminatedUnion
 
 

name Funcky.DiscriminatedUnion
nuget https://www.nuget.org/packages/Funcky.DiscriminatedUnion/
link https://github.com/polyadic/funcky-discriminated-union
author Polyadic

Generating discriminated unions for C# 9.0 and above.

 

This is how you can use Funcky.DiscriminatedUnion .

The code that you start with is


<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>net8.0</TargetFramework>
    <ImplicitUsings>enable</ImplicitUsings>
    <Nullable>enable</Nullable>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="Funcky.DiscriminatedUnion" Version="1.1.0"  />
  </ItemGroup>
	<PropertyGroup>
		<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
		<CompilerGeneratedFilesOutputPath>$(BaseIntermediateOutputPath)\GX</CompilerGeneratedFilesOutputPath>
	</PropertyGroup>
</Project>


The code that you will use is


using Union;

Console.WriteLine("Save or not");
var data = SaveToDatabase.Save(0);

Console.WriteLine(data.Match(ok => true, error => false));
data = SaveToDatabase.Save(1);
Console.WriteLine(data.Match(ok => true, error => false));



namespace Union;

[Funcky.DiscriminatedUnion]
public abstract partial record ResultSave
{
    public partial record Success(int Value): ResultSave;
    public partial record ValidationError(string Message):ResultSave;

    //public sealed partial record Ok(T Value) : ResultSave<T>;

    //public sealed partial record Error(Exception Exception) : ResultSave<T>;
}


using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Union;
internal class SaveToDatabase
{
    public static ResultSave Save(int i)
    {
        if (i == 0)
        {
            return new ResultSave.ValidationError(" cannot save 0");
        }
        return new ResultSave.Success(i);
    }
}


 

The code that is generated is

// <auto-generated/>
#nullable enable

namespace Funcky
{
    [global::System.Diagnostics.Conditional("Funcky_DiscriminatedUnion")]
    [global::System.AttributeUsage(global::System.AttributeTargets.Class)]
    internal sealed class DiscriminatedUnionAttribute : global::System.Attribute
    {
        /// <summary>Allow only consumers in the same assembly to use the exhaustive <c>Match</c> and <c>Switch</c> methods.</summary>
        public bool NonExhaustive { get; set; }

        /// <summary>Generates exhaustive <c>Match</c> and <c>Switch</c> methods for the entire type hierarchy.</summary>
        public bool Flatten { get; set; }

        /// <summary>Customized the generic type name used for the result in the generated <c>Match</c> methods. Defaults to <c>TResult</c>.</summary>
        public string? MatchResultTypeName { get; set; }
    }
}

// <auto-generated/>
#nullable enable

namespace Union
{
    partial record ResultSave
    {
        [global::System.CodeDom.Compiler.GeneratedCode("Funcky.DiscriminatedUnion.SourceGeneration", "1.1.0.0")]
        public abstract TResult Match<TResult>(global::System.Func<Success, TResult> success, global::System.Func<ValidationError, TResult> validationError);
        
        [global::System.CodeDom.Compiler.GeneratedCode("Funcky.DiscriminatedUnion.SourceGeneration", "1.1.0.0")]
        public abstract void Switch(global::System.Action<Success> success, global::System.Action<ValidationError> validationError);
        
        partial record Success
        {
            [global::System.CodeDom.Compiler.GeneratedCode("Funcky.DiscriminatedUnion.SourceGeneration", "1.1.0.0")]
            public override TResult Match<TResult>(global::System.Func<Success, TResult> success, global::System.Func<ValidationError, TResult> validationError) => success(this);
            
            [global::System.CodeDom.Compiler.GeneratedCode("Funcky.DiscriminatedUnion.SourceGeneration", "1.1.0.0")]
            public override void Switch(global::System.Action<Success> success, global::System.Action<ValidationError> validationError) => success(this);
        }
        
        partial record ValidationError
        {
            [global::System.CodeDom.Compiler.GeneratedCode("Funcky.DiscriminatedUnion.SourceGeneration", "1.1.0.0")]
            public override TResult Match<TResult>(global::System.Func<Success, TResult> success, global::System.Func<ValidationError, TResult> validationError) => validationError(this);
            
            [global::System.CodeDom.Compiler.GeneratedCode("Funcky.DiscriminatedUnion.SourceGeneration", "1.1.0.0")]
            public override void Switch(global::System.Action<Success> success, global::System.Action<ValidationError> validationError) => validationError(this);
        }
    }
}

Code and pdf at

https://ignatandrei.github.io/RSCG_Examples/v2/docs/Funcky.DiscriminatedUnion

RSCG – DomainPrimitives

RSCG – DomainPrimitives
 
 

name DomainPrimitives
nuget https://www.nuget.org/packages/AltaSoft.DomainPrimitives.Generator
https://www.nuget.org/packages/AltaSoft.DomainPrimitives.Abstractions
link https://github.com/altasoft/DomainPrimitives
author Alta Software – Teimuraz Nikolaishvili

One of the most complete and mature libraries for DomainPrimitives in .NET

 

This is how you can use DomainPrimitives .

The code that you start with is


<Project Sdk="Microsoft.NET.Sdk">

	<PropertyGroup>
		<OutputType>Exe</OutputType>
		<TargetFramework>net8.0</TargetFramework>
		<ImplicitUsings>enable</ImplicitUsings>
		<Nullable>enable</Nullable>
	</PropertyGroup>

	<ItemGroup>
		<PackageReference Include="AltaSoft.DomainPrimitives.Abstractions" Version="1.0.3" />
		<PackageReference Include="AltaSoft.DomainPrimitives.Generator" Version="1.0.3" OutputItemType="Analyzer" ReferenceOutputAssembly="false" PrivateAssets="all" ExcludeAssets="runtime" />
	</ItemGroup>
	<PropertyGroup>
		<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
		<CompilerGeneratedFilesOutputPath>$(BaseIntermediateOutputPath)\GX</CompilerGeneratedFilesOutputPath>
	</PropertyGroup>

	<PropertyGroup>
		<!--<DomainPrimitiveGenerator_GenerateJsonConverters>false</DomainPrimitiveGenerator_GenerateJsonConverters>-->
		<!--<DomainPrimitiveGenerator_GenerateTypeConverters>false</DomainPrimitiveGenerator_GenerateTypeConverters>-->
		<DomainPrimitiveGenerator_GenerateSwaggerConverters>false</DomainPrimitiveGenerator_GenerateSwaggerConverters>
	</PropertyGroup>
	<ItemGroup>
		<!--<CompilerVisibleProperty Include="DomainPrimitiveGenerator_GenerateTypeConverters" />-->
		<!--<CompilerVisibleProperty Include="DomainPrimitiveGenerator_GenerateJsonConverters" />-->
		<CompilerVisibleProperty Include="DomainPrimitiveGenerator_GenerateSwaggerConverters" />
	</ItemGroup>

</Project>


The code that you will use is


// See https://aka.ms/new-console-template for more information
using DomainPrimitives;

var year = new YearDate(1970);
var month = new MonthDate(4);
var day = new DayDate(16);
year += 1;
var p=new Person(year,month,day);

Console.WriteLine(p.DOB);


using AltaSoft.DomainPrimitives.Abstractions;

namespace DomainPrimitives;

public readonly partial record struct YearDate : IDomainValue<int>
{
    public static void Validate(int value)
    {
        if (value <= 0)
            throw new InvalidDomainValueException("year must be positive");
    }
    public static int Default => 1;
}
public readonly partial record struct MonthDate : IDomainValue<int>
{
    public static void Validate(int value)
    {
        if (value <= 0)
            throw new InvalidDomainValueException("year must be positive");
    }
    public static int Default => 1;
}

public readonly partial record struct DayDate : IDomainValue<int>
{
    public static void Validate(int value)
    {
        if (value <= 0)
            throw new InvalidDomainValueException("year must be positive");
    }
    public static int Default => 1;
}



namespace DomainPrimitives;
internal class Person
{
    public Person(YearDate year,MonthDate month,DayDate day)
    {
        DOB = new DateOnly(year,month,day);
    }
    public DateOnly DOB { get; private set; }

    
}


 

The code that is generated is

//------------------------------------------------------------------------------
// <auto-generated>
//     This code was generated by a AltaSoft.DomainPrimitives.Generator v1.0.0
//     Changes to this file may cause incorrect behavior and will be lost if the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------

#nullable enable

using System;
using System.Numerics;
using System.Diagnostics;
using System.Diagnostics.CodeAnalysis;
using System.Text.Json.Serialization;
using DomainPrimitives.Converters;
using System.ComponentModel;

namespace DomainPrimitives;

[JsonConverter(typeof(DayDateJsonConverter))]
[TypeConverter(typeof(DayDateTypeConverter))]
[DebuggerDisplay("{_valueOrDefault}")]
public readonly partial record struct DayDate :
		IAdditionOperators<DayDate, DayDate, DayDate>,
		ISubtractionOperators<DayDate, DayDate, DayDate>,
		IMultiplyOperators<DayDate, DayDate, DayDate>,
		IDivisionOperators<DayDate, DayDate, DayDate>,
		IModulusOperators<DayDate, DayDate, DayDate>,
		IComparisonOperators<DayDate, DayDate, bool>,
		IComparable,
		IComparable<DayDate>,
		IParsable<DayDate>,
		IConvertible
{
	private int _valueOrDefault => _isInitialized ? _value : Default;
	[DebuggerBrowsable(DebuggerBrowsableState.Never)]
	private readonly int _value;
	[DebuggerBrowsable(DebuggerBrowsableState.Never)]
	private readonly bool _isInitialized;
	
	/// <summary>
	/// Initializes a new instance of the <see cref="DayDate"/> class by validating the specified <see cref="int"/> value using <see cref="Validate"/> static method.
	/// </summary>
	/// <param name="value">The value to be validated..</param>
	public DayDate(int value)
	{
			Validate(value);
			_value = value;
			_isInitialized = true;
	}
	
	[Obsolete("Domain primitive cannot be created using empty Ctor", true)]
	public DayDate() : this(Default)
	{
	}
	
	/// <summary>
	/// <summary>Implicit conversion from <see cref = "int"/> to <see cref = "DayDate"/></summary>
	/// </summary>
	public static implicit operator DayDate(int value) => new(value);

	/// <summary>
	/// <summary>Implicit conversion from <see cref = "int?"/> to <see cref = "DayDate?"/></summary>
	/// </summary>
	[return: NotNullIfNotNull(nameof(value))]
	public static implicit operator DayDate?(int? value) => value is null ? null : new(value.Value);

	/// <summary>
	/// <summary>Implicit conversion from <see cref = "DayDate"/> to <see cref = "int"/></summary>
	/// </summary>
	public static implicit operator int(DayDate value) => (int)value._valueOrDefault;

	/// <inheritdoc/>
	public static DayDate operator +(DayDate left, DayDate right) => new(left._valueOrDefault + right._valueOrDefault);

	/// <inheritdoc/>
	public static DayDate operator -(DayDate left, DayDate right) => new(left._valueOrDefault - right._valueOrDefault);

	/// <inheritdoc/>
	public static DayDate operator *(DayDate left, DayDate right) => new(left._valueOrDefault * right._valueOrDefault);

	/// <inheritdoc/>
	public static DayDate operator /(DayDate left, DayDate right) => new(left._valueOrDefault / right._valueOrDefault);

	/// <inheritdoc/>
	public static DayDate operator %(DayDate left, DayDate right) => new(left._valueOrDefault % right._valueOrDefault);

	/// <inheritdoc/>
	public int CompareTo(object? value)
	{
		if (value is null)
			return 1;

		if (value is DayDate c)
			return CompareTo(c);

		throw new ArgumentException("Object is not a DayDate", nameof(value));
	}

	/// <inheritdoc/>
	public int CompareTo(DayDate other) => _valueOrDefault.CompareTo(other._valueOrDefault);

	/// <inheritdoc/>
	public static bool operator <(DayDate left, DayDate right) => left._valueOrDefault < right._valueOrDefault;

	/// <inheritdoc/>
	public static bool operator <=(DayDate left, DayDate right) => left._valueOrDefault <= right._valueOrDefault;

	/// <inheritdoc/>
	public static bool operator >(DayDate left, DayDate right) => left._valueOrDefault > right._valueOrDefault;

	/// <inheritdoc/>
	public static bool operator >=(DayDate left, DayDate right) => left._valueOrDefault >= right._valueOrDefault;


	/// <inheritdoc/>
	public static DayDate Parse(string s, IFormatProvider? provider) => int.Parse(s, provider);

	/// <inheritdoc/>
	public static bool TryParse(string? s, IFormatProvider? provider, out DayDate result)
	{
		if (int.TryParse(s, provider, out var value))
		{
			result = new DayDate(value);
			return true;
		}
		result = default;
		return false;
	}


	/// <inheritdoc/>
	public override string ToString() => _valueOrDefault.ToString();

	/// <inheritdoc/>
	TypeCode IConvertible.GetTypeCode() => ((IConvertible)_valueOrDefault).GetTypeCode();

	/// <inheritdoc/>
	bool IConvertible.ToBoolean(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToBoolean(provider);

	/// <inheritdoc/>
	byte IConvertible.ToByte(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToByte(provider);

	/// <inheritdoc/>
	char IConvertible.ToChar(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToChar(provider);

	/// <inheritdoc/>
	DateTime IConvertible.ToDateTime(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToDateTime(provider);

	/// <inheritdoc/>
	decimal IConvertible.ToDecimal(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToDecimal(provider);

	/// <inheritdoc/>
	double IConvertible.ToDouble(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToDouble(provider);

	/// <inheritdoc/>
	short IConvertible.ToInt16(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToInt16(provider);

	/// <inheritdoc/>
	int IConvertible.ToInt32(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToInt32(provider);

	/// <inheritdoc/>
	long IConvertible.ToInt64(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToInt64(provider);

	/// <inheritdoc/>
	sbyte IConvertible.ToSByte(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToSByte(provider);

	/// <inheritdoc/>
	float IConvertible.ToSingle(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToSingle(provider);

	/// <inheritdoc/>
	string IConvertible.ToString(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToString(provider);

	/// <inheritdoc/>
	object IConvertible.ToType(Type conversionType, IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToType(conversionType, provider);

	/// <inheritdoc/>
	ushort IConvertible.ToUInt16(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToUInt16(provider);

	/// <inheritdoc/>
	uint IConvertible.ToUInt32(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToUInt32(provider);

	/// <inheritdoc/>
	ulong IConvertible.ToUInt64(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToUInt64(provider);
}

//------------------------------------------------------------------------------
// <auto-generated>
//     This code was generated by a AltaSoft.DomainPrimitives.Generator v1.0.0
//     Changes to this file may cause incorrect behavior and will be lost if the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------

#nullable enable

using DomainPrimitives;
using System;
using System.Text.Json;
using System.Text.Json.Serialization;
using System.Globalization;
using System.Text.Json.Serialization.Metadata;
using AltaSoft.DomainPrimitives.Abstractions;

namespace DomainPrimitives.Converters;

/// <summary>
/// JsonConverter for <see cref = "DayDate"/>
/// </summary>
public sealed class DayDateJsonConverter : JsonConverter<DayDate>
{
	/// <inheritdoc/>
	public override DayDate Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
	{
		try
		{
			return JsonInternalConverters.Int32Converter.Read(ref reader, typeToConvert, options);
		}
		catch (InvalidDomainValueException ex)
		{
			throw new JsonException(ex.Message);
		}
	}

	/// <inheritdoc/>
	public override void Write(Utf8JsonWriter writer, DayDate value, JsonSerializerOptions options)
	{
		JsonInternalConverters.Int32Converter.Write(writer, (int)value, options);
	}

	/// <inheritdoc/>
	public override DayDate ReadAsPropertyName(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
	{
		try
		{
			return JsonInternalConverters.Int32Converter.ReadAsPropertyName(ref reader, typeToConvert, options);
		}
		catch (InvalidDomainValueException ex)
		{
			throw new JsonException(ex.Message);
		}
	}

	/// <inheritdoc/>
	public override void WriteAsPropertyName(Utf8JsonWriter writer, DayDate value, JsonSerializerOptions options)
	{
		JsonInternalConverters.Int32Converter.WriteAsPropertyName(writer, (int)value, options);
	}
}

//------------------------------------------------------------------------------
// <auto-generated>
//     This code was generated by a AltaSoft.DomainPrimitives.Generator v1.0.0
//     Changes to this file may cause incorrect behavior and will be lost if the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------

#nullable enable

using DomainPrimitives;
using System;
using System.ComponentModel;
using System.Globalization;
using AltaSoft.DomainPrimitives.Abstractions;

namespace DomainPrimitives.Converters;

/// <summary>
/// TypeConverter for <see cref = "DayDate"/>
/// </summary>
public sealed class DayDateTypeConverter : Int32Converter
{
	/// <inheritdoc/>
	public override object? ConvertFrom(ITypeDescriptorContext? context, CultureInfo? culture, object value)
	{
		var result = base.ConvertFrom(context, culture, value);
		if (result is null)
			return null;
		try
		{
			return new DayDate((int)result);
		}
		catch (InvalidDomainValueException ex)
		{
			throw new FormatException("Cannot parse DayDate", ex);
		}
	}
}

//------------------------------------------------------------------------------
// <auto-generated>
//     This code was generated by a AltaSoft.DomainPrimitives.Generator v1.0.0
//     Changes to this file may cause incorrect behavior and will be lost if the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------

#nullable enable

using System;
using System.Numerics;
using System.Diagnostics;
using System.Diagnostics.CodeAnalysis;
using System.Text.Json.Serialization;
using DomainPrimitives.Converters;
using System.ComponentModel;

namespace DomainPrimitives;

[JsonConverter(typeof(MonthDateJsonConverter))]
[TypeConverter(typeof(MonthDateTypeConverter))]
[DebuggerDisplay("{_valueOrDefault}")]
public readonly partial record struct MonthDate :
		IAdditionOperators<MonthDate, MonthDate, MonthDate>,
		ISubtractionOperators<MonthDate, MonthDate, MonthDate>,
		IMultiplyOperators<MonthDate, MonthDate, MonthDate>,
		IDivisionOperators<MonthDate, MonthDate, MonthDate>,
		IModulusOperators<MonthDate, MonthDate, MonthDate>,
		IComparisonOperators<MonthDate, MonthDate, bool>,
		IComparable,
		IComparable<MonthDate>,
		IParsable<MonthDate>,
		IConvertible
{
	private int _valueOrDefault => _isInitialized ? _value : Default;
	[DebuggerBrowsable(DebuggerBrowsableState.Never)]
	private readonly int _value;
	[DebuggerBrowsable(DebuggerBrowsableState.Never)]
	private readonly bool _isInitialized;
	
	/// <summary>
	/// Initializes a new instance of the <see cref="MonthDate"/> class by validating the specified <see cref="int"/> value using <see cref="Validate"/> static method.
	/// </summary>
	/// <param name="value">The value to be validated..</param>
	public MonthDate(int value)
	{
			Validate(value);
			_value = value;
			_isInitialized = true;
	}
	
	[Obsolete("Domain primitive cannot be created using empty Ctor", true)]
	public MonthDate() : this(Default)
	{
	}
	
	/// <summary>
	/// <summary>Implicit conversion from <see cref = "int"/> to <see cref = "MonthDate"/></summary>
	/// </summary>
	public static implicit operator MonthDate(int value) => new(value);

	/// <summary>
	/// <summary>Implicit conversion from <see cref = "int?"/> to <see cref = "MonthDate?"/></summary>
	/// </summary>
	[return: NotNullIfNotNull(nameof(value))]
	public static implicit operator MonthDate?(int? value) => value is null ? null : new(value.Value);

	/// <summary>
	/// <summary>Implicit conversion from <see cref = "MonthDate"/> to <see cref = "int"/></summary>
	/// </summary>
	public static implicit operator int(MonthDate value) => (int)value._valueOrDefault;

	/// <inheritdoc/>
	public static MonthDate operator +(MonthDate left, MonthDate right) => new(left._valueOrDefault + right._valueOrDefault);

	/// <inheritdoc/>
	public static MonthDate operator -(MonthDate left, MonthDate right) => new(left._valueOrDefault - right._valueOrDefault);

	/// <inheritdoc/>
	public static MonthDate operator *(MonthDate left, MonthDate right) => new(left._valueOrDefault * right._valueOrDefault);

	/// <inheritdoc/>
	public static MonthDate operator /(MonthDate left, MonthDate right) => new(left._valueOrDefault / right._valueOrDefault);

	/// <inheritdoc/>
	public static MonthDate operator %(MonthDate left, MonthDate right) => new(left._valueOrDefault % right._valueOrDefault);

	/// <inheritdoc/>
	public int CompareTo(object? value)
	{
		if (value is null)
			return 1;

		if (value is MonthDate c)
			return CompareTo(c);

		throw new ArgumentException("Object is not a MonthDate", nameof(value));
	}

	/// <inheritdoc/>
	public int CompareTo(MonthDate other) => _valueOrDefault.CompareTo(other._valueOrDefault);

	/// <inheritdoc/>
	public static bool operator <(MonthDate left, MonthDate right) => left._valueOrDefault < right._valueOrDefault;

	/// <inheritdoc/>
	public static bool operator <=(MonthDate left, MonthDate right) => left._valueOrDefault <= right._valueOrDefault;

	/// <inheritdoc/>
	public static bool operator >(MonthDate left, MonthDate right) => left._valueOrDefault > right._valueOrDefault;

	/// <inheritdoc/>
	public static bool operator >=(MonthDate left, MonthDate right) => left._valueOrDefault >= right._valueOrDefault;


	/// <inheritdoc/>
	public static MonthDate Parse(string s, IFormatProvider? provider) => int.Parse(s, provider);

	/// <inheritdoc/>
	public static bool TryParse(string? s, IFormatProvider? provider, out MonthDate result)
	{
		if (int.TryParse(s, provider, out var value))
		{
			result = new MonthDate(value);
			return true;
		}
		result = default;
		return false;
	}


	/// <inheritdoc/>
	public override string ToString() => _valueOrDefault.ToString();

	/// <inheritdoc/>
	TypeCode IConvertible.GetTypeCode() => ((IConvertible)_valueOrDefault).GetTypeCode();

	/// <inheritdoc/>
	bool IConvertible.ToBoolean(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToBoolean(provider);

	/// <inheritdoc/>
	byte IConvertible.ToByte(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToByte(provider);

	/// <inheritdoc/>
	char IConvertible.ToChar(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToChar(provider);

	/// <inheritdoc/>
	DateTime IConvertible.ToDateTime(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToDateTime(provider);

	/// <inheritdoc/>
	decimal IConvertible.ToDecimal(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToDecimal(provider);

	/// <inheritdoc/>
	double IConvertible.ToDouble(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToDouble(provider);

	/// <inheritdoc/>
	short IConvertible.ToInt16(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToInt16(provider);

	/// <inheritdoc/>
	int IConvertible.ToInt32(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToInt32(provider);

	/// <inheritdoc/>
	long IConvertible.ToInt64(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToInt64(provider);

	/// <inheritdoc/>
	sbyte IConvertible.ToSByte(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToSByte(provider);

	/// <inheritdoc/>
	float IConvertible.ToSingle(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToSingle(provider);

	/// <inheritdoc/>
	string IConvertible.ToString(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToString(provider);

	/// <inheritdoc/>
	object IConvertible.ToType(Type conversionType, IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToType(conversionType, provider);

	/// <inheritdoc/>
	ushort IConvertible.ToUInt16(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToUInt16(provider);

	/// <inheritdoc/>
	uint IConvertible.ToUInt32(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToUInt32(provider);

	/// <inheritdoc/>
	ulong IConvertible.ToUInt64(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToUInt64(provider);
}

//------------------------------------------------------------------------------
// <auto-generated>
//     This code was generated by a AltaSoft.DomainPrimitives.Generator v1.0.0
//     Changes to this file may cause incorrect behavior and will be lost if the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------

#nullable enable

using DomainPrimitives;
using System;
using System.Text.Json;
using System.Text.Json.Serialization;
using System.Globalization;
using System.Text.Json.Serialization.Metadata;
using AltaSoft.DomainPrimitives.Abstractions;

namespace DomainPrimitives.Converters;

/// <summary>
/// JsonConverter for <see cref = "MonthDate"/>
/// </summary>
public sealed class MonthDateJsonConverter : JsonConverter<MonthDate>
{
	/// <inheritdoc/>
	public override MonthDate Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
	{
		try
		{
			return JsonInternalConverters.Int32Converter.Read(ref reader, typeToConvert, options);
		}
		catch (InvalidDomainValueException ex)
		{
			throw new JsonException(ex.Message);
		}
	}

	/// <inheritdoc/>
	public override void Write(Utf8JsonWriter writer, MonthDate value, JsonSerializerOptions options)
	{
		JsonInternalConverters.Int32Converter.Write(writer, (int)value, options);
	}

	/// <inheritdoc/>
	public override MonthDate ReadAsPropertyName(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
	{
		try
		{
			return JsonInternalConverters.Int32Converter.ReadAsPropertyName(ref reader, typeToConvert, options);
		}
		catch (InvalidDomainValueException ex)
		{
			throw new JsonException(ex.Message);
		}
	}

	/// <inheritdoc/>
	public override void WriteAsPropertyName(Utf8JsonWriter writer, MonthDate value, JsonSerializerOptions options)
	{
		JsonInternalConverters.Int32Converter.WriteAsPropertyName(writer, (int)value, options);
	}
}

//------------------------------------------------------------------------------
// <auto-generated>
//     This code was generated by a AltaSoft.DomainPrimitives.Generator v1.0.0
//     Changes to this file may cause incorrect behavior and will be lost if the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------

#nullable enable

using DomainPrimitives;
using System;
using System.ComponentModel;
using System.Globalization;
using AltaSoft.DomainPrimitives.Abstractions;

namespace DomainPrimitives.Converters;

/// <summary>
/// TypeConverter for <see cref = "MonthDate"/>
/// </summary>
public sealed class MonthDateTypeConverter : Int32Converter
{
	/// <inheritdoc/>
	public override object? ConvertFrom(ITypeDescriptorContext? context, CultureInfo? culture, object value)
	{
		var result = base.ConvertFrom(context, culture, value);
		if (result is null)
			return null;
		try
		{
			return new MonthDate((int)result);
		}
		catch (InvalidDomainValueException ex)
		{
			throw new FormatException("Cannot parse MonthDate", ex);
		}
	}
}

//------------------------------------------------------------------------------
// <auto-generated>
//     This code was generated by a AltaSoft.DomainPrimitives.Generator v1.0.0
//     Changes to this file may cause incorrect behavior and will be lost if the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------

#nullable enable

using System;
using System.Numerics;
using System.Diagnostics;
using System.Diagnostics.CodeAnalysis;
using System.Text.Json.Serialization;
using DomainPrimitives.Converters;
using System.ComponentModel;

namespace DomainPrimitives;

[JsonConverter(typeof(YearDateJsonConverter))]
[TypeConverter(typeof(YearDateTypeConverter))]
[DebuggerDisplay("{_valueOrDefault}")]
public readonly partial record struct YearDate :
		IAdditionOperators<YearDate, YearDate, YearDate>,
		ISubtractionOperators<YearDate, YearDate, YearDate>,
		IMultiplyOperators<YearDate, YearDate, YearDate>,
		IDivisionOperators<YearDate, YearDate, YearDate>,
		IModulusOperators<YearDate, YearDate, YearDate>,
		IComparisonOperators<YearDate, YearDate, bool>,
		IComparable,
		IComparable<YearDate>,
		IParsable<YearDate>,
		IConvertible
{
	private int _valueOrDefault => _isInitialized ? _value : Default;
	[DebuggerBrowsable(DebuggerBrowsableState.Never)]
	private readonly int _value;
	[DebuggerBrowsable(DebuggerBrowsableState.Never)]
	private readonly bool _isInitialized;
	
	/// <summary>
	/// Initializes a new instance of the <see cref="YearDate"/> class by validating the specified <see cref="int"/> value using <see cref="Validate"/> static method.
	/// </summary>
	/// <param name="value">The value to be validated..</param>
	public YearDate(int value)
	{
			Validate(value);
			_value = value;
			_isInitialized = true;
	}
	
	[Obsolete("Domain primitive cannot be created using empty Ctor", true)]
	public YearDate() : this(Default)
	{
	}
	
	/// <summary>
	/// <summary>Implicit conversion from <see cref = "int"/> to <see cref = "YearDate"/></summary>
	/// </summary>
	public static implicit operator YearDate(int value) => new(value);

	/// <summary>
	/// <summary>Implicit conversion from <see cref = "int?"/> to <see cref = "YearDate?"/></summary>
	/// </summary>
	[return: NotNullIfNotNull(nameof(value))]
	public static implicit operator YearDate?(int? value) => value is null ? null : new(value.Value);

	/// <summary>
	/// <summary>Implicit conversion from <see cref = "YearDate"/> to <see cref = "int"/></summary>
	/// </summary>
	public static implicit operator int(YearDate value) => (int)value._valueOrDefault;

	/// <inheritdoc/>
	public static YearDate operator +(YearDate left, YearDate right) => new(left._valueOrDefault + right._valueOrDefault);

	/// <inheritdoc/>
	public static YearDate operator -(YearDate left, YearDate right) => new(left._valueOrDefault - right._valueOrDefault);

	/// <inheritdoc/>
	public static YearDate operator *(YearDate left, YearDate right) => new(left._valueOrDefault * right._valueOrDefault);

	/// <inheritdoc/>
	public static YearDate operator /(YearDate left, YearDate right) => new(left._valueOrDefault / right._valueOrDefault);

	/// <inheritdoc/>
	public static YearDate operator %(YearDate left, YearDate right) => new(left._valueOrDefault % right._valueOrDefault);

	/// <inheritdoc/>
	public int CompareTo(object? value)
	{
		if (value is null)
			return 1;

		if (value is YearDate c)
			return CompareTo(c);

		throw new ArgumentException("Object is not a YearDate", nameof(value));
	}

	/// <inheritdoc/>
	public int CompareTo(YearDate other) => _valueOrDefault.CompareTo(other._valueOrDefault);

	/// <inheritdoc/>
	public static bool operator <(YearDate left, YearDate right) => left._valueOrDefault < right._valueOrDefault;

	/// <inheritdoc/>
	public static bool operator <=(YearDate left, YearDate right) => left._valueOrDefault <= right._valueOrDefault;

	/// <inheritdoc/>
	public static bool operator >(YearDate left, YearDate right) => left._valueOrDefault > right._valueOrDefault;

	/// <inheritdoc/>
	public static bool operator >=(YearDate left, YearDate right) => left._valueOrDefault >= right._valueOrDefault;


	/// <inheritdoc/>
	public static YearDate Parse(string s, IFormatProvider? provider) => int.Parse(s, provider);

	/// <inheritdoc/>
	public static bool TryParse(string? s, IFormatProvider? provider, out YearDate result)
	{
		if (int.TryParse(s, provider, out var value))
		{
			result = new YearDate(value);
			return true;
		}
		result = default;
		return false;
	}


	/// <inheritdoc/>
	public override string ToString() => _valueOrDefault.ToString();

	/// <inheritdoc/>
	TypeCode IConvertible.GetTypeCode() => ((IConvertible)_valueOrDefault).GetTypeCode();

	/// <inheritdoc/>
	bool IConvertible.ToBoolean(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToBoolean(provider);

	/// <inheritdoc/>
	byte IConvertible.ToByte(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToByte(provider);

	/// <inheritdoc/>
	char IConvertible.ToChar(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToChar(provider);

	/// <inheritdoc/>
	DateTime IConvertible.ToDateTime(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToDateTime(provider);

	/// <inheritdoc/>
	decimal IConvertible.ToDecimal(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToDecimal(provider);

	/// <inheritdoc/>
	double IConvertible.ToDouble(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToDouble(provider);

	/// <inheritdoc/>
	short IConvertible.ToInt16(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToInt16(provider);

	/// <inheritdoc/>
	int IConvertible.ToInt32(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToInt32(provider);

	/// <inheritdoc/>
	long IConvertible.ToInt64(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToInt64(provider);

	/// <inheritdoc/>
	sbyte IConvertible.ToSByte(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToSByte(provider);

	/// <inheritdoc/>
	float IConvertible.ToSingle(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToSingle(provider);

	/// <inheritdoc/>
	string IConvertible.ToString(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToString(provider);

	/// <inheritdoc/>
	object IConvertible.ToType(Type conversionType, IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToType(conversionType, provider);

	/// <inheritdoc/>
	ushort IConvertible.ToUInt16(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToUInt16(provider);

	/// <inheritdoc/>
	uint IConvertible.ToUInt32(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToUInt32(provider);

	/// <inheritdoc/>
	ulong IConvertible.ToUInt64(IFormatProvider? provider) => ((IConvertible)_valueOrDefault).ToUInt64(provider);
}

//------------------------------------------------------------------------------
// <auto-generated>
//     This code was generated by a AltaSoft.DomainPrimitives.Generator v1.0.0
//     Changes to this file may cause incorrect behavior and will be lost if the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------

#nullable enable

using DomainPrimitives;
using System;
using System.Text.Json;
using System.Text.Json.Serialization;
using System.Globalization;
using System.Text.Json.Serialization.Metadata;
using AltaSoft.DomainPrimitives.Abstractions;

namespace DomainPrimitives.Converters;

/// <summary>
/// JsonConverter for <see cref = "YearDate"/>
/// </summary>
public sealed class YearDateJsonConverter : JsonConverter<YearDate>
{
	/// <inheritdoc/>
	public override YearDate Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
	{
		try
		{
			return JsonInternalConverters.Int32Converter.Read(ref reader, typeToConvert, options);
		}
		catch (InvalidDomainValueException ex)
		{
			throw new JsonException(ex.Message);
		}
	}

	/// <inheritdoc/>
	public override void Write(Utf8JsonWriter writer, YearDate value, JsonSerializerOptions options)
	{
		JsonInternalConverters.Int32Converter.Write(writer, (int)value, options);
	}

	/// <inheritdoc/>
	public override YearDate ReadAsPropertyName(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
	{
		try
		{
			return JsonInternalConverters.Int32Converter.ReadAsPropertyName(ref reader, typeToConvert, options);
		}
		catch (InvalidDomainValueException ex)
		{
			throw new JsonException(ex.Message);
		}
	}

	/// <inheritdoc/>
	public override void WriteAsPropertyName(Utf8JsonWriter writer, YearDate value, JsonSerializerOptions options)
	{
		JsonInternalConverters.Int32Converter.WriteAsPropertyName(writer, (int)value, options);
	}
}

//------------------------------------------------------------------------------
// <auto-generated>
//     This code was generated by a AltaSoft.DomainPrimitives.Generator v1.0.0
//     Changes to this file may cause incorrect behavior and will be lost if the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------

#nullable enable

using DomainPrimitives;
using System;
using System.ComponentModel;
using System.Globalization;
using AltaSoft.DomainPrimitives.Abstractions;

namespace DomainPrimitives.Converters;

/// <summary>
/// TypeConverter for <see cref = "YearDate"/>
/// </summary>
public sealed class YearDateTypeConverter : Int32Converter
{
	/// <inheritdoc/>
	public override object? ConvertFrom(ITypeDescriptorContext? context, CultureInfo? culture, object value)
	{
		var result = base.ConvertFrom(context, culture, value);
		if (result is null)
			return null;
		try
		{
			return new YearDate((int)result);
		}
		catch (InvalidDomainValueException ex)
		{
			throw new FormatException("Cannot parse YearDate", ex);
		}
	}
}

Code and pdf at

https://ignatandrei.github.io/RSCG_Examples/v2/docs/DomainPrimitives

Andrei Ignat weekly software news(mostly .NET)

* indicates required

Please select all the ways you would like to hear from me:

You can unsubscribe at any time by clicking the link in the footer of our emails. For information about our privacy practices, please visit our website.

We use Mailchimp as our marketing platform. By clicking below to subscribe, you acknowledge that your information will be transferred to Mailchimp for processing. Learn more about Mailchimp's privacy practices here.