I have arguments passed in via the command-line
private static int Main(string[] args)
{
const string PORT = "12345" ;
var listeningUrl = $"http://localhost:{PORT}";
var builder = new WebHostBuilder()
.UseStartup<Startup>()
.UseKestrel()
.UseUrls(listeningUrl);
var host = builder.Build();
WriteLine($"Running on {PORT}");
host.Run();
return 0;
}
One of these arguments is a logging output directory. How do I get this value into my Startup
class so I can write out to this directory when I receive a request?
I'd like to avoid using a static class. Would a service that supplies the value be the right way? If so, how do I get services injected into my middleware?
How to Pass or Access Command-line Arguments in C#? In C#, the Main() method is an entry point of the Console, Windows, or Web application (. NET Core). It can have a string[] args parameter that can be used to retrieve the arguments passed while running the application.
The startup class contains two methods: ConfigureServices(): Registers the services that your application will need. Configure(): Configures the middleware pipeline that controls how the application processes the HTTP requests and sends the response.
The arguments which are passed by the user or programmer to the Main() method is termed as Command-Line Arguments. Main() method is the entry point of execution of a program. Main() method accepts array of strings. But it never accepts parameters from any other method in the program.
You should be able to use the AddCommandLine()
extension. First install the Nuget package Microsoft.Extensions.Configuration.CommandLine
and ensure you have the correct import:
using Microsoft.Extensions.Configuration;
Now update your Main
method to include the new config:
var config = new ConfigurationBuilder()
.AddJsonFile("hosting.json", optional: true) //this is not needed, but could be useful
.AddCommandLine(args)
.Build();
var builder = new WebHostBuilder()
.UseConfiguration(config) //<-- Add this
.UseStartup<Startup>()
.UseKestrel()
.UseUrls(listeningUrl);
Now you treat the command line options as configuration:
dotnet run /MySetting:SomeValue=123
And read in code:
var someValue = Configuration.GetValue<int>("MySetting:SomeValue");
Dotnet Core 2
You don't need most of the code as in dotnet core 1.0 to achieve this.
AddCommandLine
arguments are automatically injected when you BuildWebHost using the following syntax
Step 1.
public static IWebHost BuildWebHost(string[] args)
{
return WebHost.CreateDefaultBuilder(args)
.UseStartup<Startup>()
.Build();
}
Step 2. Inject configurations to Startup.cs using DI using the following code
public class Startup
{
private readonly IConfiguration Configuration;
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
...
}
Step 3. Access your arguments using configurations object.
var seed = Configuration.GetValue<bool>("seed");
Console.WriteLine($"seed: {seed}");
Step 4. Start application with arguments
dotnet run seed=True
ASP.NET Core 2 answer:
Change the default Program.cs to be:
using System;
using System.IO;
using Microsoft.AspNetCore;
using Microsoft.AspNetCore.Hosting;
using Microsoft.Extensions.Configuration;
public class Program
{
public static void Main(string[] args)
{
BuildWebHost(args).Run();
}
public static IWebHost BuildWebHost(string[] args) =>
WebHost.CreateDefaultBuilder(args)
.ConfigureAppConfiguration((hostingContext, config) =>
{
config.SetBasePath(Directory.GetCurrentDirectory());
config.AddJsonFile("appsettings.json", optional: true, reloadOnChange: true)
.AddJsonFile($"appsettings.{hostingContext.HostingEnvironment.EnvironmentName}.json", optional: true, reloadOnChange: true);
config.AddEnvironmentVariables();
config.AddCommandLine(args);
})
.UseStartup<Startup>()
.Build();
}
I removed other bits just to make the configuration explanation easier.
Note the .AddCommandLine(args)
line in the configuration builder.
Unlike @BanksySan's answer you DON'T need to create a static property, instead let DI inject the IConfiguration into the startup class.
public class Startup
{
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
private IConfiguration Configuration { get; }
You can now use the configuration entries from any of the config providers, file, env variables and commandline.
Example:
dotnet run --seed true
public void Configure(IApplicationBuilder app)
{
app.UseExceptionHandler("/Home/Error");
var seed = Configuration.GetValue<bool>("seed");
if (seed)
SeedData.Initialize(app);
app.UseStaticFiles();
app.UseMvcWithDefaultRoute();
}
Hope this helps someone further.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With