SmallSharp 2.0.0

dotnet add package SmallSharp --version 2.0.0
                    
NuGet\Install-Package SmallSharp -Version 2.0.0
                    
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="SmallSharp" Version="2.0.0">
  <PrivateAssets>all</PrivateAssets>
  <IncludeAssets>runtime; build; native; contentfiles; analyzers</IncludeAssets>
</PackageReference>
                    
For projects that support PackageReference, copy this XML node into the project file to reference the package.
<PackageVersion Include="SmallSharp" Version="2.0.0" />
                    
Directory.Packages.props
<PackageReference Include="SmallSharp">
  <PrivateAssets>all</PrivateAssets>
  <IncludeAssets>runtime; build; native; contentfiles; analyzers</IncludeAssets>
</PackageReference>
                    
Project file
For projects that support Central Package Management (CPM), copy this XML node into the solution Directory.Packages.props file to version the package.
paket add SmallSharp --version 2.0.0
                    
#r "nuget: SmallSharp, 2.0.0"
                    
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
#:package SmallSharp@2.0.0
                    
#:package directive can be used in C# file-based apps starting in .NET 10 preview 4. Copy this into a .cs file before any lines of code to reference the package.
#addin nuget:?package=SmallSharp&version=2.0.0
                    
Install as a Cake Addin
#tool nuget:?package=SmallSharp&version=2.0.0
                    
Install as a Cake Tool

Create, edit and run multiple C# top-level programs in the same project, respecting per-file #:package references and #:property project values 😍

Open Source Maintenance Fee

To ensure the long-term sustainability of this project, use of SmallSharp requires an Open Source Maintenance Fee. While the source code is freely available under the terms of the MIT License, this package and other aspects of the project require adherence to the Maintenance Fee.

In short, if you use this project to generate revenue, the Maintenance Fee is required.

To pay the Maintenance Fee, become a Sponsor.

Overview

C# top-level programs allow a very intuitive, simple and streamlined experience for quickly spiking or learning C#. The addition of dotnet run app.cs in .NET 10 takes this further by allowing package references and even MSBuild properties to be specified per file:

#:package Humanizer@2.14.1

using Humanizer;

var dotNet9Released = DateTimeOffset.Parse("2024-12-03");
var since = DateTimeOffset.Now - dotNet9Released;

Console.WriteLine($"It has been {since.Humanize()} since .NET 9 was released.");

Editing these standalone files in VSCode, however, is suboptimal compared with the full C# experience in Visual Studio. In Visual Studio, though, you can only have one top-level program in a project, and as of now, you cannot leverage the #:package and #:property directives at all.

SmallSharp allows dynamically selecting the file to run, right from the Start button/dropdown (for compilation and launch/debug). It also automatically restores the #:package references so the project system can resolve them, and even emits the #:property directives if present to customize the build as needed.

start button

This list is automatically kept in sync as you add more .cs files to the project. When you select one target C# file, that becomes the only top-level program to be compiled, so you don't have to modify any of the others since they automatically become None items.

An initial build after selection change migh be needed to restore the packages and compile the selected file

All compile files directly under the project directory root are considered top-level programs for selection and compilation purposes. If you need to share code among them, you can place additional files in subdirectories and those will behave like normal compile items.

Usage

SmallSharp works by just installing the SmallSharp nuget package in a C# console project.

Recommended installation as an SDK:

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

  <Sdk Name="SmallSharp" Version="2.0.0" />

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>net10.0</TargetFramework>
  </PropertyGroup>

</Project>

Or as a regular package reference:

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

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>net10.0</TargetFramework>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="SmallSharp" Version="*" />
  </ItemGroup>

</Project>

Keep adding as many top-level programs as you need, and switch between them easily by simply selecting the desired file from the Start button dropdown.

How It Works

This nuget package leverages in concert the following standalone and otherwise unrelated features of the compiler, nuget and MSBuild:

  1. The C# compiler only allows one top-level program per compilation.
  2. Launch profiles (the entries in the Run dropdown) are populated from the Properties\launchSettings.json file
  3. Whenever changed, the dropdown selection is persisted as the $(ActiveDebugProfile) MSBuild property in a file named after the project with the .user extension
  4. This file is imported before NuGet-provided MSBuild targets

Using the above features in concert, SmallSharp essentially does the following:

  • Emit top-level files as a launchSettings.json profile and set the $(ActiveDebugProfile).

  • Exclude .cs files at the project level from being included as <Compile> by the default SDK includes and include them explicitly as <None> instead so they show up in the solution explorer. This prevents the compiler from causing an error for multiple top-level programs.

  • Explicitly include as <Compile> only the $(ActiveDebugProfile) property value.

  • Emit #:package and #:property directive to an automatically imported obj\SmallSharp.targets file

  • SmallSharp MSBuild SDK automatically imports the SmallSharp.targets file, which causes a new restore to automatically happen in Visual Studio, bringing all required dependencies automatically.

This basically mean that this it will also work consistently if you use dotnet run from the command-line, since the "Main" file selection is performed exclusively via MSBuild item manipulation.

It is recommended to keep the project file to its bare minimum, usually having just the SmallSharp SDK reference, and do all project/package references in the top-level files using the #:package and #:property directives for improved isolation between the top-level programs.

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

  <Sdk Name="SmallSharp" Version="2.0.0" />

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>net10.0</TargetFramework>
  </PropertyGroup>

</Project>

run humanizer file

run mcp file

Sponsors

Clarius Org MFB Technologies, Inc. Torutek DRIVE.NET, Inc. Keith Pickford Thomas Bolon Kori Francis Toni Wenzel Uno Platform Reuben Swartz Jacob Foshee alternate text is missing from this package README image Eric Johnson David JENNI Jonathan Charley Wu Ken Bonny Simon Cropp agileworks-eu Zheyu Shen Vezel ChilliCream 4OTC Vincent Limo Jordan S. Jones domischell Justin Wendlandt Adrian Alonso Michael Hagedorn Alex Rønne Petersen

Sponsor this project  

Learn more about GitHub Sponsors

Product Compatible and additional computed target framework versions.
.NET net5.0 was computed.  net5.0-windows was computed.  net6.0 was computed.  net6.0-android was computed.  net6.0-ios was computed.  net6.0-maccatalyst was computed.  net6.0-macos was computed.  net6.0-tvos was computed.  net6.0-windows was computed.  net7.0 was computed.  net7.0-android was computed.  net7.0-ios was computed.  net7.0-maccatalyst was computed.  net7.0-macos was computed.  net7.0-tvos was computed.  net7.0-windows was computed.  net8.0 was computed.  net8.0-android was computed.  net8.0-browser was computed.  net8.0-ios was computed.  net8.0-maccatalyst was computed.  net8.0-macos was computed.  net8.0-tvos was computed.  net8.0-windows was computed.  net9.0 was computed.  net9.0-android was computed.  net9.0-browser was computed.  net9.0-ios was computed.  net9.0-maccatalyst was computed.  net9.0-macos was computed.  net9.0-tvos was computed.  net9.0-windows was computed.  net10.0 was computed.  net10.0-android was computed.  net10.0-browser was computed.  net10.0-ios was computed.  net10.0-maccatalyst was computed.  net10.0-macos was computed.  net10.0-tvos was computed.  net10.0-windows was computed. 
.NET Core netcoreapp2.0 was computed.  netcoreapp2.1 was computed.  netcoreapp2.2 was computed.  netcoreapp3.0 was computed.  netcoreapp3.1 was computed. 
.NET Standard netstandard2.0 is compatible.  netstandard2.1 was computed. 
.NET Framework net461 was computed.  net462 was computed.  net463 was computed.  net47 was computed.  net471 was computed.  net472 was computed.  net48 was computed.  net481 was computed. 
MonoAndroid monoandroid was computed. 
MonoMac monomac was computed. 
MonoTouch monotouch was computed. 
Tizen tizen40 was computed.  tizen60 was computed. 
Xamarin.iOS xamarinios was computed. 
Xamarin.Mac xamarinmac was computed. 
Xamarin.TVOS xamarintvos was computed. 
Xamarin.WatchOS xamarinwatchos was computed. 
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.

NuGet packages

This package is not used by any NuGet packages.

GitHub repositories

This package is not used by any popular GitHub repositories.

Version Downloads Last Updated
2.0.0 476 7/22/2025
1.3.0 279 7/20/2025
1.2.0 307 7/17/2024
1.1.7 1,242 11/16/2022
1.1.6 368 11/16/2022
1.1.5 603 2/3/2022
1.1.4 510 7/5/2021
1.1.2 429 5/17/2021
1.1.1 435 4/8/2021
1.1.0 438 2/15/2021
1.0.3 422 2/12/2021
1.0.2 405 2/12/2021
1.0.1 498 11/20/2020
1.0.0 522 11/18/2020
0.3.0 496 10/19/2020
0.2.0 495 10/1/2020