Referencing another project in .Net Core


#1

Hi guys. I’m writing a post about using .Net Core as a cross-platform / OS development platform. My idea is to show how to deploy a simple application composed by two projects: A console application using a class library as an application tier.

From what I’ve read about configuring multi-project apps with .Net Core I’ve created the following structure:

SolutionProjectFolder
|-- global.json
|
|-- ConsoleAppProjectFolder
|   |-- Sources
|   |-- project.json
|
|-- ClassLibraryProjectFolder
    |-- Sources
    |-- project.json

And added a dependency to the Class Library project in the Console app project.json file.

However, it was not until I added a project.json file at the solution level that it worked.

SolutionProjectFolder
|-- global.json
|-- project.json      <---
|
|-- ConsoleAppProjectFolder
|   |-- Sources
|   |-- project.json
|
|-- ClassLibraryProjectFolder
    |-- Sources
    |-- project.json

Solution level poject.json:

{
  "version": "1.0.0-*",
  "dependencies": {
    "ConsoleAppProjectFolder": "1.0.0-*",
    "ClassLibraryProjectFolder": "1.0.0-*"
  },
  "frameworks": {
    "dnx451": {},
    "dnxcore50": {}
  }

}

Before adding this project.json file I was getting different errors.

  • If I ran dnx run from the Console app project folder I got the error: “Predefined type ‘System.String’ is not defined or importer”
  • If I ran it from the solution folder I got “Enable to resolve project” error.

Is this the correct approach to handle multi-project apps? I mean, it is really necessary to add a project.json file in the container folder even if there is no source file there? I’m missing something?.

Thank you very much for your help!


#2

Hey @jrebagliatti, it looks like you’re 95% of the way there!

Just to make things quick if you’re short on time, I’ve reproduced the same structure you have – a console app that takes a dependency on a class library – and put it up on github for you to browse.

Two things to call out here:

  • Your general structure is correct, but there’s no need for a project.json file at the root level
  • Referring to things as folders may have messed up one of your stated dependencies in a project.json file

To expound on that last point, you should be thinking of the folders as the library instead of a folder containing the library. Renaming gives this structure:

SolutionProjectFolder
|-- global.json
|
|-- ConsoleApp
|   |-- Sources
|   |-- project.json
|
|-- ClassLibrary
    |-- Sources
    |-- project.json

In the code I put on Github, ClassLibrary is a single class which contains a method which returns a string. ConsoleApp calls WriteLine on that string. The key things are as follows:

Note: Some details here may change in the future as we flesh out the tooling more!

  1. The global.json file contains an array of the project names:

    {
        "projects":[
            "ConsoleApp",
            "ClassLibrary"
        ]
    }
    
  2. The project.json for ClassLibrary targets dotnet55 and System.Runtime:

        {
            "frameworks":{
                "dotnet55":{
                    "dependencies":{
                         "System.Runtime":"4.0.0-rc1-*"
                     }
                }
            }
        }
    
  3. The project.json for ConsoleApp targets dnxcore50 for now (to allow dnx to run it):

{
    "dependencies":{
        "ClassLibrary":"",
    },
    "frameworks":{
        "dnxcore50":{
            "dependencies":{
                "System.Runtime":"4.0.0-rc1-*",
                "System.Console":"4.0.0-beta-*"
            }
        }
    }
}

Note the -beta-* on System.Console. This is needed for now, but you should be able to target non-beta versions when they’re available. The platform is still evolving, so doing things like referencing a beta package may be required from time to time until we reach an RTM release for .NET Core.

To build and run:

$ cd ClassLibrary
$ dotnet restore
$ dotnet compile
$ cd ConsoleApp
$ dotnet restore
$ dnx run

As of this time (2015-11-13) there are some issues with $ dotnet run and console apps, so $ dnx run is being used for now.

I hope this helps!


#3

Cool!. I’ve installed the latest coreclr and followed your directions and it worked.

I also had forgotten to build the class library before running the console app. I’ve used the dnu build command instead of dotnet compile to do so.

Thank @cartermp very much for taking the time to explain it so clearly.


#4

Thanks for the info @cartermp!

I’m porting a few projects to .NET Core and have a question for developers working outside Visual Studio.

If a modification is made to a dependency (in the example above, ClassLibrary) and ConsoleApp has been modified as well, can I compile ConsoleApp along with its dependencies with a single command? If not, would the correct solution be to create a “build all” script to build everything in the correct order?

Thanks, take care.


#5

@justinhhorner yup! All you have to do is change the dependency and when you run $ dotnet build from ConsoleApp it’ll recompile ClassLibrary.

Here’s what it looks like on my machine using this demo project:

This was built using the latest tools as of today. Note that there will be some more changes in store for the .NET CLI for our eventual RC2 release. I’m happy to help you out with any quirks in the tooling right now; things are still coming together so there’s a bit more for you have to do to get everything up and running. If you follow what’s in the repo I linked, then you should be fine for now. It will be stable when we’re at RC2 :slight_smile:.


#6

Thank you for the explanation @cartermp!

Should this work the same way for the restore command? Meaning if I clone a repository and run restore from within ConsoleApp, should it run restore for the dependencies?


#7

@justinhhorner in this case, no. You’ll have to run it from the top-level directory, or on a per-project basis.


#8

How do you get vscode debugging working with this? I have configured my launch.json to reference the sub directory for my runable project but upon launch it fails to find the source, as its looking in the root dir still.


#9

I notice in this demo project there is no longer a global.json file. When you run dotnet restore how does it know that the class library dependency sits in a sibling folder, does it traverse up the folders looking for that project?

If so how do you ensure it only looks within the “solution” folder for the project dependency?


#10

@matthewrk great question!

Yes, you need to configure the launch.json file, specifically the program entry:

Here’s an example of what I put in just a .NET Core Console App called “SimpleApp”:

"program": "${workspaceRoot}/bin/Debug/netcoreapp1.0/SimpleApp".

In this case, started the console app and opened up VSCode at the project level. If it were at a solution level, then {workspaceRoot} would be pointing to a parent folder.


#11

Hey @jamest222, the demo project I put together there is now out of date. For more information, check out Writing Libraries with Cross Platform Tools.


#12

Hmm… So its not possible to debug across multiple projects with vscode? For example a common pattern may be to have a web app with a data access class library, ideally you may want to debug the web app, firstly from within the solution (a bit of an inconvenience to open at the project level but not a deal breaker), and secondly by using breakpoints that traverse down from that app into the class libraries if necessary. I work on a solution with several projects and we typically do that kind of thing very often, so its a bit of a road block to my being able to code .net from my mac at the moment, which I was hoping to achieve when we upgrade our app to .net core.


#13

I second that, with so many new stuff and changes coming down with .NET Core RTM, this was very helpful! Thanks @cartertmp


#14

How would you do this for a web project ? And will this work with the new release?


#15

Yep, this will work with the new release, and the mechanism for referencing something is the same for any type of project that uses project.json. You can learn more here: https://docs.microsoft.com/en-us/dotnet/articles/core/tutorials/libraries#how-to-use-multiple-projects


.NET Foundation Website | Blog | Projects | Code of Conduct