Giter Site home page Giter Site logo

primaryconstructor's Introduction

PrimaryConstructor

Generate primary constructor from readonly fields & properties

NuGet

image

Get it

PM> Install-Package PrimaryConstructor

Prerequisites

Visual Studio version 16.8 and above is required as its first version to support source generators.

Usage

Declare class with partial, and annotate with [PrimaryConstructor].
And then you can declare your dependencies with readonly fields.

[PrimaryConstructor]
public partial class MyService
{
    private readonly MyDependency _myDependency;

    ...
}

When compile, following source will be injected.

partial class MyService
{
    public MyService(MyDependency myDependency)
    {
        this._myDependency = myDependency;
    }
}

Rules

  1. readonly fields & properties without initializer will be automatically injected.
  2. if the service has based type, based type must also annotated with PrimaryConstructor in order to inject members from based type.
  3. you can exclude members from injection by annotated with IgnorePrimaryConstructor.
  4. you can include members to injection by annotated with IncludePrimaryConstructor.

Emit generated files

Visual Studio still not fully support source generator, it sometimes shows error marker on symbols referred to the generated code. Emitting the generated files will allow you to see the code, and also solve Visual Studio error marker problem.

To emit generated files, add following code to your csproj file.

<PropertyGroup>
  <CompilerGeneratedFilesOutputPath>$(MSBuildProjectDirectory)/generated</CompilerGeneratedFilesOutputPath>
  <EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
</PropertyGroup>

<Target Name="ExcludeGenerated" BeforeTargets="AssignTargetPaths">
  <ItemGroup>
    <Generated Include="generated/**/*.g.cs" />
    <Compile Remove="@(Generated)" />
  </ItemGroup>
  <Delete Files="@(Generated)" />
</Target>

Please check PrimaryConstructor.Sample.csproj for sample.

primaryconstructor's People

Contributors

alexandersorokin avatar chaowlert avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar

primaryconstructor's Issues

Feature to enable Asp.Net project wide primary constructors on all controllers?

Would you consider a feature where all controllers in an Asp.Net project are automatically subject to having their constructor generated? So like, perhaps an assembly level [assembly: PrimaryConstructor] attribute would trigger it. Or maybe simply inclusion of an Asp.Net Mvc targeted nuget package like PrimaryConstructor.Mvc could be enough.
I think the logic could be to simply look for classes inheriting from ControllerBase instead of classes decorated with [PrimaryConstructor].

If you like the idea I would be interested in taking a crack at a pull request.

Property or indexer cannot be assigned to - it is read only

I'm getting compile error "Property or indexer 'MyDependency.name' cannot be assigned to -- it is read only" when there is read-only property with expression body.

Code to reproduce the bug:

    [PrimaryConstructor]
    public partial class MyDependency
    {
        public string GetName()
        {
            return "Hello";
        }
        private string name => GetName();
    }

Suggestion: AllArgsConstructor, RequiredArgsConstructor and NoArgsConstructor?

Hi
Thank you for this plugin. Project lombok (for java) has:

  • AllArgsConstructor : Generates a constructor with all members
  • RequiredArgsConstructor: Generates a constructor for all final/readonly members
  • NoArgsConstructor: Generates empty constructor

Any plans for implementing something like this? Currently I'm having some classes, that just needs a constructor that takes all arguments, but I cannot make them readonly as they need to be updated through their properties

Support Nested Classes

Seems there is no support for nested classes.

public static class Example
{
    [PrimaryConstructor]
    public partial class Nested
    {
        private readonly IDependency Dependency;
    }
}

[Bug] Readonly props are not injected

Seems readonly properties are not injected (v 1.3.1):

public MyDependency MyDependency { get; }

This property in the example project won't be injected until the [IncludePrimaryConstructor] attribute is added.

Same class name in different namespaces

The generation doesn't work correctly when there are two same name classes but in different namespaces.
A simple snippet to reproduce the bug:

namespace NS1
{
    [PrimaryConstructor]
    public partial class Foo
    {
        public Int32 _bar;
        public static Foo foo = new Foo(1);
    }
}

namespace NS2
{
    [PrimaryConstructor]
    public partial class Foo
    {
        public Int32 _bar;
        public static Foo foo = new Foo(1);
    }
}

Ability to decorate generated constructor parameters

For dependency injection purpose, I sometimes need to decorate constructor parameters with attributes. Is there a way to somehow copy the attributes defined on a field to the corresponding parameter in the primary constructor?

So this:

[PrimaryConstructor]
public partial class Apple
{
    [parameter: InjectValue]
    private readonly int seeds;
}

would generate:

partial class Apple
{
    public Apple([InjectValue] int seeds)
    {
        this.seeds = seeds;
    }
}

Namespace collisions

There can be namespace collisions when a namespace has a subspace and this subspace name is used as the root namespace in another project.
To resolve the problem the generated constructor should generate parameters with the global keyword:

global::Name.Space.TypeName x

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.