Lumberjack log DDLogInfo showing up as WARNING in console - ios

I am using Lumberjack as my logging framework.
I have this definition…
#ifdef DEBUG
static const int ddLogLevel = LOG_LEVEL_DEBUG;
#else
static const int ddLogLevel = LOG_LEVEL_WARN;
#endif
and this is my log statement…
DDLogInfo(#"Starting");
However when I look at the Console.app it shows this message as a WARNING instead of INFO like ASL can show. Is there something else that I need to do?
This does allow the statement to not be logged when not in DEBUG mode, so that is working as advertised.

This is the expected behavior.
The DDASLLogger map the Debug to ASL's Warning level, Info to Error etc.
Thats because by default, ASL will filter Notice level and above.
(In case DDLogInfo prints Warning, then you are using an older version of CocoaLumberjack)
Apple System Log documentation says:
The default filter mask is ASL_FILTER_MASK_UPTO(ASL_LEVEL_NOTICE).
This means that by default, and in the absence of remote-control changes
(described below), ASL_LEVEL_DEBUG and ASL_LEVEL_INFO priority level messages
are not sent to the server.
You could try and write your own custom ASL logger.
But I suggest that you will add a custom formatter to the ASL logger that will add the actual log level (faster approache).

Related

Adopting os_log APIs while keeping backward compatibility

I'm trying to add support for the new logging and activity tracing APIs to a library in a way that maintains backward compatibility for users of the library who haven't yet adopted the latest version of the OS (iOS or macOS). I'm defining custom logging macros for each level of logging, and then for older OSes, falling back to NSLog. I've gotten this working, with one problem.
The new APIs require you to mark any non-constant, non-scalar values as explicitly public if you want them to show up in log output. This is what an invocation of my macro looks like:
UZKLogInfo("Reading file %{public}# from archive", fileName);
This compiles fine with the SDK that includes os_log (e.g. iOS 10.0 or later), but when I compile with an earlier version so my macro falls back to NSLog, I get a compiler warning:
Using 'public' format specifier annotation outside of os_log()/os_trace()
And the log line printed looks like this:
Reading file <decode: missing data> from archive
This is a simplified version of my macro definition (only including the info definition and simplifying the conditional:
#if UNIFIED_LOGGING_SUPPORTED
#import os.log;
#define UZKLogInfo(format, ...) os_log_info(OS_LOG_DEFAULT, format, ##__VA_ARGS__);
#else // Fall back to regular NSLog
#define UZKLogInfo(format, ...) NSLog(#format, ##__VA_ARGS__);
#endif
Is there any way to strip the "{public}" text (some kind of string replacement?) from format in the fallback case? Or is there another way to support the old and new APIs without giving up the level of info I've always shown in the logs? I need to use a macro (according the last year's WWDC session on the topic, or else I lose the call site metadata.
I chose to do an NSString replace in the macro, and to suppress the compiler warnings as part of it, so it could be done for each line, rather than globally for the whole file or project. It looks like this:
#if UNIFIED_LOGGING_SUPPORTED
#import os.log;
#define UZKLogInfo(format, ...) os_log_info(OS_LOG_DEFAULT, format, ##__VA_ARGS__);
#else // Fall back to regular NSLog
#define _removeLogFormatTokens(format) [#format stringByReplacingOccurrencesOfString:#"{public}" withString:#""]
#define _stringify(a) #a
#define _nsLogWithoutWarnings(format, ...) \
_Pragma( _stringify( clang diagnostic push ) ) \
_Pragma( _stringify( clang diagnostic ignored "-Wformat-nonliteral" ) ) \
_Pragma( _stringify( clang diagnostic ignored "-Wformat-security" ) ) \
NSLog(_removeLogFormatTokens(format), ##__VA_ARGS__); \
_Pragma( _stringify( clang diagnostic pop ) )
#define UZKLogInfo(format, ...) _nsLogWithoutWarnings(format, ##__VA_ARGS__);
#endif
It's called like so:
UZKLogInfo("Message: %#", anObjectToLog);

Show debug messages if argument is set

In my project i'm showing debug messages with global variable:
struct GVariables {
static let debug = false
}
if GVariables.debug {
print("Debug mode enabled")
}
But is it possible to set argument here:
and check debug argument in code. How can i do this ? And is this a correct way ?
You can get access to those launch arguments and environment variables via NSProcessInfo
if NSProcessInfo.processInfo.arguments["DEBUGRPM"] ...
That's not unreasonable and allows you to change the behavior of a compiled app which can be useful in some cases. It does however have some overhead since you're always performing this check. If you would only ever enable debug logging in a debug build then setting a value in "Swift Compiler - Custom Flags" (as shown in the question #Larme linked) and using an #if DEBUGRPM expression will give you conditionally compiled code, saving the app the work of performing a runtime if test.
Which approach is more reasonable for you will depend on how you plan to use and when you plan to toggle this behavior.

How to disable Loggings of Apptentive in Xcode console?

Apptentive seems like a good addition to have. However it pollutes the Console with so many messages, that is unnecessary to see every time. It is distracting me from seeing important debug messages elsewhere.
Only an extract:
2015-05-10 10:15:45.134 xNews[34355:4228197] Loading ATSwizzle_NSObject_Bootstrap
2015-05-10 10:15:45.134 xNews[34355:4228197] Loading ATSwizzle_UIViewController_Bootstrap
According to the docs it's possible to disable them:
#import "ATConnect_Debugging.h"
[ATConnect sharedConnection].debuggingOptions = ATConnectDebuggingOptionsNone;
This doesn't work at all. I still get to see all those debug messages I don't care about. Any advice please?
The Apptentive debuggingOptions property does enable/disable some debug features, however it's true that we aren't tying that in with the log levels.
// #import "ATConnect_Debugging.h"
[ATConnect sharedConnection].debuggingOptions = ATConnectDebuggingOptionsNone;
I will make a note to add a new debuggingOptions option to silence all logging for an upcoming version of the SDK.
Apptentive does allow control over log levels via the ATLog.h file and preprocessor macros:
AT_LOGGING_ENABLED = 1
AT_LOGGING_LEVEL_INFO = 1
AT_LOGGING_LEVEL_DUBUG = 1
AT_LOGGING_LEVEL_WARNING = 1
AT_LOGGING_LEVEL_ERROR = 1
By default, release configuration of the Apptentive SDK will log only the warning and error log levels. Debug builds will log the more verbose info and debug levels.
In your Xcode project you should be able to set AT_LOGGING_ENABLED = 0 to silence all Apptentive warning. Or toggle the log levels as you see fit.
Thanks for using Apptentive! Let me know if you need any assistance with this.

Turn logging to lldb console off (Socket IO framework for iOS)

I am using pkyeck / socket.IO-objc framework. It is very good, however I am unable to debug with the verbose logs it produces to the lldb, which makes the console constantly full with descriptions about traffic, which are useless to me at the moment. I couldn't find a way how to turn it OFF. Anybody knows how to do it? I just can't imagine myself commenting out all the lines with NSLog...
Found the solution. It is rather undesired to tinker with the source code of the framework - usually it is a good practice to take it AS-IS but since there wasn't any other way...
In the file SocketIO.m, locate line numbers 32 - 39:
#define DEBUG_LOGS 1
#define DEBUG_CERTIFICATE 1
#if DEBUG_LOGS
#define DEBUGLOG(...) NSLog(__VA_ARGS__)
#else
#define DEBUGLOG(...)
#endif
Naturally, everybody now knows what comes next - change the value of DEBUG_LOGS to 0.
That's it, done. I recommend adding a //TODO: to the line above in order not to forget for the next time, when debugging logs are desired.

Is there a Clang diagnostic that is only a note?

Clang has several kinds of diagnostics, of which the three main kinds are errors, warnings, and notes.
Notes usually accompany certain warnings and errors, such as duplicate definitions:
error: conflicting types for 'square'
static double square(double x) {
^
note: previous declaration is here
static int square(int x);
^
What I want to know is, does Clang have any diagnostics—especially for Objective-C or C, but I'll settle for C++ if I have to—that consist of only a note, with no associated error or warning?
http://clang.llvm.org/docs/InternalsManual.html#the-diagnostic-kinds-td-files says:
These severities are mapped into a smaller set (the Diagnostic::Level
enum, {Ignored, Note, Warning, Error, Fatal}) of output levels by the
diagnostics subsystem based on various configuration options. Clang
internally supports a fully fine grained mapping mechanism that allows
you to map almost any diagnostic to the output level that you want.
The only diagnostics that cannot be mapped are NOTEs, which always
follow the severity of the previously emitted diagnostic and ERRORs,
which can only be mapped to Fatal (it is not possible to turn an error
into a warning, for example).
So unfortunately no; you can't do that without hacking Clang itself. Notes are intended only for linking to other diagnostics. I'd file a bug with the LLVM tracker; this would definitely be useful functionality.

Resources