'How to use iOS OSLog with Xamarin?

How can I use the iOS OSLog in Xamarin.iOS?

I did succeed in using NSLog as follows, but I see no way of setting the subsystem (to the bundle identifier) with NSLog so that I can use that to filter the logs in Console.app.

public class Logger
{
    #if DEBUG
    [DllImport(ObjCRuntime.Constants.FoundationLibrary)]
    private extern static void NSLog(IntPtr message);
    #endif

    public void WriteLine(string line)
    {
        #if DEBUG
        using (var nss = new NSString(line))
        {
            NSLog(nss.Handle);
        }
        #endif
    }
}


Solution 1:[1]

In Xamarin.iOS, there is a static CoreFoundation.OSLog object called Default that one can use straight away which will log messages with the specified OSLogLevel argument such as OSLogLevel.Debug, OSLogLevel.Error etc. You could have a method in your Xamarin.iOS code that logs a message at the Debug level:

using CoreFoundation;
// ...

public void Write(string message)
{
    OSLog.Default.Log(OSLogLevel.Debug, message);
}

If you want to use the subsystem and category, you have to instantiate an instance of OSLog using the appropriate constructor and use that instance to log your messages. Presumably you'd want to hold a static reference to your created instance and use it like you'd use OSLog.Default.

public partial class AppDelegate : Xamarin.Forms.Platform.iOS.FormsApplicationDelegate
{
    public static OSLog LoggerInstance;

    public override bool FinishedLaunching(UIApplication app, NSDictionary launchOptions)
    {
        LoggerInstance = new OSLog(subsystem: "subsystem", category: "category");
//...

public class SomeClass
{
    public void SomeMethod()
    {
        AppDelegate.LoggerInstance?.Log(OSLogLevel.Debug, "log message");
        // ...
    }

This will print a fairly nice message in the device log with a timestamp and showing the specified category.

Solution 2:[2]

OSLog is a ObjC struct (of two const chars) and a kernel method, os_log_create, is provided to allocate one.

Note: Refer to the os/log.h for details.

Define:

[DllImport("__Internal", EntryPoint = "os_log_create")]
public static extern IntPtr os_log_create(string subsystem, string category);

Usage:

var oslog = os_log_create("some.bundle.id", "StackOverflowCategory");

FYI: your NSLog should include a printf format string as a NSString

[DllImport (Constants.FoundationLibrary, EntryPoint = "NSLog")]
extern static void NSLog (IntPtr format, [MarshalAs (UnmanagedType.LPStr)] string s);

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 bcr
Solution 2