Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion samples/SimpleServiceSample/PrintTimeService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;

namespace SimpleWebSample
namespace SimpleServiceSample
{
public class PrintTimeService : IHostedService, IDisposable
{
Expand Down
6 changes: 3 additions & 3 deletions samples/SimpleServiceSample/Program.cs
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
using System;
using System.IO;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Configuration;
using Serilog;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Serilog;

namespace SimpleWebSample
namespace SimpleServiceSample
{
public class Program
{
Expand Down
3 changes: 3 additions & 0 deletions serilog-extensions-hosting.sln.DotSettings
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
<wpf:ResourceDictionary xml:space="preserve" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:s="clr-namespace:System;assembly=mscorlib" xmlns:ss="urn:shemas-jetbrains-com:settings-storage-xaml" xmlns:wpf="http://schemas.microsoft.com/winfx/2006/xaml/presentation">
<s:Boolean x:Key="/Default/UserDictionary/Words/=appsettings/@EntryIndexedValue">True</s:Boolean>
<s:Boolean x:Key="/Default/UserDictionary/Words/=Serilog/@EntryIndexedValue">True</s:Boolean></wpf:ResourceDictionary>
Original file line number Diff line number Diff line change
Expand Up @@ -12,18 +12,23 @@
// See the License for the specific language governing permissions and
// limitations under the License.

using System;
using Microsoft.Extensions.Logging;
using Serilog.Debugging;
using Serilog.Extensions.Logging;

// To line up with the convention used elsewhere in the *.Extensions libraries, this
// should have been Serilog.Extensions.Hosting.
// ReSharper disable once CheckNamespace
namespace Serilog.Hosting
{
/// <summary>
/// Implements <see cref="ILoggerFactory"/> so that we can inject Serilog Logger.
/// </summary>
[Obsolete("Replaced with Serilog.Extensions.Logging.SerilogLoggerFactory")]
public class SerilogLoggerFactory : ILoggerFactory
{
private readonly SerilogLoggerProvider _provider;
readonly SerilogLoggerProvider _provider;

/// <summary>
/// Initializes a new instance of the <see cref="SerilogLoggerFactory"/> class.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

<PropertyGroup>
<Description>Serilog support for .NET Core logging in hosted services</Description>
<VersionPrefix>2.0.1</VersionPrefix>
<VersionPrefix>3.0.0</VersionPrefix>
<Authors>Microsoft;Serilog Contributors</Authors>
<TargetFrameworks>netstandard2.0</TargetFrameworks>
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
Expand All @@ -23,8 +23,8 @@
</PropertyGroup>

<ItemGroup>
<PackageReference Include="Serilog" Version="2.5.0" />
<PackageReference Include="Serilog.Extensions.Logging" Version="2.0.0" />
<PackageReference Include="Serilog" Version="2.8.0" />
<PackageReference Include="Serilog.Extensions.Logging" Version="3.0.0-*" />
<PackageReference Include="Microsoft.Extensions.Hosting.Abstractions" Version="2.1.0" />
<PackageReference Include="Microsoft.Extensions.DependencyInjection.Abstractions" Version="2.1.0" />
<PackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="2.1.0" />
Expand Down
89 changes: 71 additions & 18 deletions src/Serilog.Extensions.Hosting/SerilogHostBuilderExtensions.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
// Copyright 2018 Serilog Contributors
// Copyright 2019 Serilog Contributors
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
Expand All @@ -15,8 +15,8 @@
using System;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;
using Serilog.Hosting;
using Microsoft.Extensions.DependencyInjection;
using Serilog.Extensions.Logging;

namespace Serilog
{
Expand All @@ -30,49 +30,102 @@ public static class SerilogHostBuilderExtensions
/// </summary>
/// <param name="builder">The host builder to configure.</param>
/// <param name="logger">The Serilog logger; if not supplied, the static <see cref="Serilog.Log"/> will be used.</param>
/// <param name="dispose">When <c>true</c>, dispose <paramref name="logger"/> when the framework disposes the provider. If the
/// logger is not specified but <paramref name="dispose"/> is <c>true</c>, the <see cref="Log.CloseAndFlush()"/> method will be
/// <param name="dispose">When true, dispose <paramref name="logger"/> when the framework disposes the provider. If the
/// logger is not specified but <paramref name="dispose"/> is true, the <see cref="Log.CloseAndFlush()"/> method will be
/// called on the static <see cref="Log"/> class instead.</param>
/// <returns>The (generic) host builder.</returns>
public static IHostBuilder UseSerilog(this IHostBuilder builder, Serilog.ILogger logger = null, bool dispose = false)
/// <param name="providers">A <see cref="LoggerProviderCollection"/> registered in the Serilog pipeline using the
/// <c>WriteTo.Providers()</c> configuration method, enabling other <see cref="ILoggerProvider"/>s to receive events. By
/// default, only Serilog sinks will receive events.</param>
/// <returns>The host builder.</returns>
public static IHostBuilder UseSerilog(
this IHostBuilder builder,
ILogger logger = null,
bool dispose = false,
LoggerProviderCollection providers = null)
{
if (builder == null) throw new ArgumentNullException(nameof(builder));
builder.ConfigureServices((context, collection) =>
collection.AddSingleton<ILoggerFactory>(services => new SerilogLoggerFactory(logger, dispose)));

builder.ConfigureServices((_, collection) =>
{
if (providers != null)
{
collection.AddSingleton<ILoggerFactory>(services =>
{
var factory = new SerilogLoggerFactory(logger, dispose, providers);

foreach (var provider in services.GetServices<ILoggerProvider>())
factory.AddProvider(provider);

return factory;
});
}
else
{
collection.AddSingleton<ILoggerFactory>(services => new SerilogLoggerFactory(logger, dispose));
}
});

return builder;
}

/// <summary>
/// Sets Serilog as the logging provider.
/// </summary>
/// <summary>Sets Serilog as the logging provider.</summary>
/// <remarks>
/// A <see cref="HostBuilderContext"/> is supplied so that configuration and hosting information can be used.
/// The logger will be shut down when application services are disposed.
/// </remarks>
/// <param name="builder">The host builder to configure.</param>
/// <param name="configureLogger">The delegate for configuring the <see cref="LoggerConfiguration" /> that will be used to construct a <see cref="Logger" />.</param>
/// <param name="preserveStaticLogger">Indicates whether to preserve the value of <see cref="Log.Logger"/>.</param>
/// <returns>The (generic) host builder.</returns>
public static IHostBuilder UseSerilog(this IHostBuilder builder, Action<HostBuilderContext, LoggerConfiguration> configureLogger, bool preserveStaticLogger = false)
/// <param name="writeToProviders">By default, Serilog does not write events to <see cref="ILoggerProvider"/>s registered through
/// the Microsoft.Extensions.Logging API. Normally, equivalent Serilog sinks are used in place of providers. Specify
/// <c>true</c> to write events to all providers.</param>
/// <returns>The host builder.</returns>
public static IHostBuilder UseSerilog(
this IHostBuilder builder,
Action<HostBuilderContext, LoggerConfiguration> configureLogger,
bool preserveStaticLogger = false,
bool writeToProviders = false)
{
if (builder == null) throw new ArgumentNullException(nameof(builder));
if (configureLogger == null) throw new ArgumentNullException(nameof(configureLogger));
builder.ConfigureServices((context, collection) =>
{
var loggerConfiguration = new LoggerConfiguration();

LoggerProviderCollection loggerProviders = null;
if (writeToProviders)
{
loggerProviders = new LoggerProviderCollection();
loggerConfiguration.WriteTo.Providers(loggerProviders);
}

configureLogger(context, loggerConfiguration);
var logger = loggerConfiguration.CreateLogger();

ILogger registeredLogger = null;
if (preserveStaticLogger)
{
collection.AddSingleton<ILoggerFactory>(services => new SerilogLoggerFactory(logger, true));
}
else
{
// Passing a `null` logger to `SerilogLoggerFactory` results in disposal via
// `Log.CloseAndFlush()`, which additionally replaces the static logger with a no-op.
Log.Logger = logger;
collection.AddSingleton<ILoggerFactory>(services => new SerilogLoggerFactory(null, true));
}
else
{
registeredLogger = logger;
}

collection.AddSingleton<ILoggerFactory>(services =>
{
var factory = new SerilogLoggerFactory(registeredLogger, true, loggerProviders);

if (writeToProviders)
{
foreach (var provider in services.GetServices<ILoggerProvider>())
factory.AddProvider(provider);
}

return factory;
});
});
return builder;
}
Expand Down