Add free search for your website. Sign up now! https://webveta.alightservices.com/
Categories
.Net C# Logging NLog

How to log debug level logs only when an exception occurs in ASP.Net using NLog

In the past I have written few blog posts on NLog and discussed several techniques:

Programatically configuring NLog in C#

NLog in .Net Applications

Some NLog configuration examples for writing into different log management systems

And I have discussed about a possibility of capturing more information in logs only when needed such as in the case of errors or exceptions in the following blog post:

An abnormal way of logging – open for discussion

This blog post is for Asp.Net Core only.

This should be possible by combining AspNetBufferingWrapper and PostFilteringWrapper.

Sample configuration provided below:

AspNetBufferingWrapper:

AspNetBufferingWrapper buffers all the messages in a ASP.Net request and sends all the messages to the wrapped target.

Remember to set this logger properly. This involves:

  1. Adding the NLog.Web.AspNetCore nuget package
  2. Properly configuring nlog.config file
  3. Registering the middleware
dotnet add package NLog.Web.AspNetCore --version 5.2.1
<extensions>
    <add assembly="NLog.Web.AspNetCore"/>
</extensions>
using NLog.Web;

app.UseMiddleware<NLogBufferingTargetWrapperMiddleware>();

PostFilteringWrapper:

This wrapper evaluates a specified condition and filters logs, then sends the logs to the wrapped target:

<target xsi:type="PostFilteringWrapper" defaultFilter="level &gt;= LogLevel.Info">
    <target .... />
    <when exists="level &gt;= LogLevel.Warn" filter="level &gt;= LogLevel.Debug"/>
</target>

The above configuration by default logs Info and above logs, but if there is a Warn or higher, logs debug or higher. For this to work properly obviously this logger has to receive Debug messages otherwise there is no point in using this logger.

Now combing these two loggers, here is an example:

<extensions>
    <add assembly="NLog.Web.AspNetCore"/>
</extensions>

<targets>
    <target xsi:type="AspNetBufferingWrapper" name="aspnetbuffer" bufferGrowLimit="1000" growBufferAsNeeded="true">
        <target xsi:type="PostFilteringWrapper" defaultFilter="level &gt;= LogLevel.Info">
            <target xsi:type="File" fileName="c:\temp\nlog-AspNetCore-all-${shortdate}.log"
 layout="${longdate}|${event-properties:item=EventId:whenEmpty=0}|${level:uppercase=true}|${logger}|${message} ${exception:format=tostring}" />
        <when exists="level &gt;= LogLevel.Warn" filter="level &gt;= LogLevel.Debug"/>
        </target>
    </target>
</targets>

<rules>
    <logger name="*" minlevel="Debug" writeTo="aspnetbuffer" />
</rules>

Hoping this post helps someone!

Happy development.

Mr. Kanti Kalyan Arumilli

Arumilli Kanti Kalyan, Founder & CEO
Arumilli Kanti Kalyan, Founder & CEO

B.Tech, M.B.A

Facebook

LinkedIn

Threads

Instagram

Youtube

Founder & CEO, Lead Full-Stack .Net developer

ALight Technology And Services Limited

ALight Technologies USA Inc

Youtube

Facebook

LinkedIn

Phone / SMS / WhatsApp on the following 3 numbers:

+91-789-362-6688, +1-480-347-6849, +44-07718-273-964

kantikalyan@gmail.com, kantikalyan@outlook.com, admin@alightservices.com, kantikalyan.arumilli@alightservices.com, KArumilli2020@student.hult.edu, KantiKArumilli@outlook.com and 3 more rarely used email addresses – hardly once or twice a year.

Categories
.Net AWS C#

How to export logs from cloudwatch to S3.

There might be a business case for log retention whether it’s for compliance or any other reason.

This is the approach being used by ALight Technology And Services Limited for longer term log retention.

I have created a bucket in S3 with the following retention policies:

AWS S3 Object Lock Policy

I personally don’t have to follow compliance yet, but nothing wrong in implementing compliance policies.

I have also defined a life-cycle policy to transition objects into Standard-IA (Infrequent Access) after 30 days.

Now I am developing a Lambda that would create Export tasks in CloudWatch once a week.

Here are some relevant C# code snippets:

var _client = new AmazonCloudWatchLogsClient(RegionEndpoint.EUWest2);
// Initialized AmazonCloudWatchLogsClient

var response = await _client.DescribeLogGroupsAsync();
// Get a list of LogGroups

foreach(var logGroup in response.LogGroups)
{
    var prefix = $"{from}-{to}-{logGroup.LogGroupName}";
    // You can define your own prefix
   
    var exportResult = await _client.CreateExportTaskAsync(new
        CreateExportTaskRequest
{
            Destination = "<NAME_OF_S3_BUCKET>",
            DestinationPrefix = prefix,
            From = GetUnixMilliSeconds(from),
            LogGroupName = logGroup.LogGroupName,
            TaskName = prefix,
            To = GetUnixMilliSeconds(to),
        })
    };

The above code is pretty much self-explantory. Here is a code snippet for getting Unix MilliSeconds from epoch.

long GetUnixMilliSeconds(DateTime dateTime)
{
    var _epoch = new DateTime(1970, 1, 1, 0, 0, 0, 0);
    return (dateTime.Ticks - _epoch.Ticks) / 10000;
}

Happy development!

Stay away from psycoSpies!

Mr. Kanti Kalyan Arumilli

Arumilli Kanti Kalyan, Founder & CEO
Arumilli Kanti Kalyan, Founder & CEO

B.Tech, M.B.A

Facebook

LinkedIn

Threads

Instagram

Youtube

Founder & CEO, Lead Full-Stack .Net developer

ALight Technology And Services Limited

ALight Technologies USA Inc

Youtube

Facebook

LinkedIn

Phone / SMS / WhatsApp on the following 3 numbers:

+91-789-362-6688, +1-480-347-6849, +44-07718-273-964

kantikalyan@gmail.com, kantikalyan@outlook.com, admin@alightservices.com, kantikalyan.arumilli@alightservices.com, KArumilli2020@student.hult.edu, KantiKArumilli@outlook.com and 3 more rarely used email addresses – hardly once or twice a year.

Categories
.Net C# Security

C# code for reading sensitive information from Console

I had a need to generate random passwords and / keys and update various config files. For example, keys and passwords used by log ingesting utilities such as FileBeat, PromTail, MetricBeat etc…

In earlier blog posts, I have mentioned, that at this point log ingestion, retention and major alerts implementation is complete. So, obviously the next part is securing the keys.

I know the hacker spies – India’s psychopath R&AW spies can and are seeing any plain-text items on screen and if I am not wrong, they might have even hacked into my accounts several times. Yes, they say they are investigation teams etc… bull-shit but in reality they are corrupted and are the criminals i.e greedy investigators / spies who did crime and are trying to get away from crime.

Anyway, because I know how the “prying eyes” equipment works, I need to defend myself from the hacker spies as much as possible. For more info about this scam: https://www.simplepro.site.

Here is a small C# code snippet for reading from console without echoing back:

string GetSensitiveText()
{
    StringBuilder password = new StringBuilder();
    ConsoleKeyInfo keyInfo = Console.ReadKey(true);

    while (keyInfo.Key != ConsoleKey.Enter)
    {
        password.Append(keyInfo.KeyChar);

        keyInfo = Console.ReadKey(true);
    }

    return password.ToString();
}

Now everyone knows how to do open a file, read content and replace content. A simple program can be developed that would take the path of config file, old value, new value and replace.

i.e for example during test, alpha modes if a key is “KEY” and then later if you use a random password generator that would generate password and copy into memory, this type of small tool can help with replacing “KEY” with the “RAND0M P@$$W0rd”.

Some code sample:

Console.WriteLine("Enter filepath:");
var fileName = Console.ReadLine();
var sr = new StreamReader(fileName);
var content = sr.ReadToEnd();
sr.Close();
Console.WriteLine("Enter Search Phrase:");
var searchPhrase = Console.ReadLine();
var matchedIndex = content.IndexOf(searchPhrase);
if(matchedIndex >= 0)
{
    Console.WriteLine("Match found.");
    Console.WriteLine("Enter replacement text:");
    var replacementText = GetSensitiveText();

    var sw = new StreamWriter(fileName);
    sw.Write(content.Replace(searchPhrase, replacementText));
    sw.Flush();
    sw.Close();
}

We prompt for the path to the config file, prompt for the search text. If the search text is found, we prompt for the secret i.e the replace text. But, we don’t echo the new sensitive info to the Console. Then the search text is replaced with new sensitive info and then we write the contents back to the file.

Happy secure coding! 🙂

Mr. Kanti Kalyan Arumilli

Arumilli Kanti Kalyan, Founder & CEO
Arumilli Kanti Kalyan, Founder & CEO

B.Tech, M.B.A

Facebook

LinkedIn

Threads

Instagram

Youtube

Founder & CEO, Lead Full-Stack .Net developer

ALight Technology And Services Limited

ALight Technologies USA Inc

Youtube

Facebook

LinkedIn

Phone / SMS / WhatsApp on the following 3 numbers:

+91-789-362-6688, +1-480-347-6849, +44-07718-273-964

kantikalyan@gmail.com, kantikalyan@outlook.com, admin@alightservices.com, kantikalyan.arumilli@alightservices.com, KArumilli2020@student.hult.edu, KantiKArumilli@outlook.com and 3 more rarely used email addresses – hardly once or twice a year.

Categories
.Net C# gRPC

Metrics gathering using CollectD, C# over GRPC

In the past, I have written about a little known utility for collecting metrics known as CollectD. CollectD samples various metrics at configured interval and outputs to various destinations. This particular blog post is about having CollectD send the metrics to a GRPC endpoint, the endpoint can decide how to further process the received data. In this blog post, I would be writing about C# GRPC server for receiving data, but in reality most programming languages that support GRPC can be used.

One more thing, having CollectD use GRPC is slightly complex, because several different libraries need to be installed. Here is a list for Ubuntu, this is not an exhaustive list, but the list of libraries that I had to install on Ubuntu to allow CollectD report metrics using GRPC – gcc, gpp, build-essential, protobuf-compiler-grpc, libprotobuf-dev, protobuf-compiler, libgrpc++-dev. The best way to find any missing libraries is to compile CollectD from source as mentioned in https://collectd.org/download.shtml, and after ./configure look for missing libraries beside grpc until the output shows grpc – yes.

Now for the C# server, here is the .proto file, I have used:

syntax = "proto3";

package collectd;

import "google/protobuf/duration.proto";
import "google/protobuf/timestamp.proto";

service Collectd {
  rpc PutValues(stream PutValuesRequest) returns(PutValuesResponse);
}

message PutValuesRequest {
  ValueList value_list = 1;
}

message PutValuesResponse {}

message Identifier {
  string host = 1;
  string plugin = 2;
  string plugin_instance = 3;
  string type = 4;
  string type_instance = 5;
}

message Value {
  oneof value {
    uint64 counter = 1;
    double gauge = 2;
    int64 derive = 3;
    uint64 absolute = 4;
  };
}

message ValueList {
  repeated Value values = 1;

  google.protobuf.Timestamp time = 2;
  google.protobuf.Duration interval = 3;

  Identifier identifier = 4;

  repeated string ds_names = 5;
}

The .proto file is largely based on the proto files available at https://github.com/sandtable/collectd-grpc.

The implementation for the C# server is very simple. I have set the protobuf compiler to only generate the server side code. Create class that inherits from CollectdBase. Override the method PutValues. Remember the request is a stream.

public override async Task<PutValuesResponse> PutValues(IAsyncStreamReader<PutValuesRequest> requestStream, ServerCallContext context)
{
    while (await requestStream.MoveNext())
    {
        var currentItem = requestStream.Current;
        //Do something with currentItem
    }

    return new PutValuesResponse();
}

Mr. Kanti Kalyan Arumilli

Arumilli Kanti Kalyan, Founder & CEO
Arumilli Kanti Kalyan, Founder & CEO

B.Tech, M.B.A

Facebook

LinkedIn

Threads

Instagram

Youtube

Founder & CEO, Lead Full-Stack .Net developer

ALight Technology And Services Limited

ALight Technologies USA Inc

Youtube

Facebook

LinkedIn

Phone / SMS / WhatsApp on the following 3 numbers:

+91-789-362-6688, +1-480-347-6849, +44-07718-273-964

kantikalyan@gmail.com, kantikalyan@outlook.com, admin@alightservices.com, kantikalyan.arumilli@alightservices.com, KArumilli2020@student.hult.edu, KantiKArumilli@outlook.com and 3 more rarely used email addresses – hardly once or twice a year.

Categories
.Net C#

Live C# development session – 1

In this video, I explained the purpose and kind of setup the basic application architecture. More videos would be done soon.

Mr. Kanti Kalyan Arumilli

Arumilli Kanti Kalyan, Founder & CEO
Arumilli Kanti Kalyan, Founder & CEO

B.Tech, M.B.A

Facebook

LinkedIn

Threads

Instagram

Youtube

Founder & CEO, Lead Full-Stack .Net developer

ALight Technology And Services Limited

ALight Technologies USA Inc

Youtube

Facebook

LinkedIn

Phone / SMS / WhatsApp on the following 3 numbers:

+91-789-362-6688, +1-480-347-6849, +44-07718-273-964

kantikalyan@gmail.com, kantikalyan@outlook.com, admin@alightservices.com, kantikalyan.arumilli@alightservices.com, KArumilli2020@student.hult.edu, KantiKArumilli@outlook.com and 3 more rarely used email addresses – hardly once or twice a year.

Categories
.Net C#

Some useful C# code snippets:

I have shown some code and discussed some general best practices earlier this morning in a live Youtube video – Some C# reusable code snippets (https://www.youtube.com/watch?v=9SyZjDukvhE) in ALight Technology And Service’s official Youtube channel (https://www.youtube.com/@alighttechnologyandservicesltd). As promised in the video, this blog post has the code snippets.

Some C# reusable code snippets

Concept – 1:

Centralizing config generation into a re-usable library, having a wrapper class around reading the config. Now the consuming classes do not need to know the details of where or how to get config values. For example, the config can be stored in plain-text / encrypted, can be stored in text files or something like AWS Secrets Manager.

public static void GenerateConfig()
{
    var retVal = new ConfigurationBuilder()
                .SetBasePath(Directory.GetCurrentDirectory())
                .AddJsonFile(<ConfigFile>, optional: false, reloadOnChange: true)
                .AddJsonFile(<ConfigFile2>, optional: false, reloadOnChange: true)
                .AddEnvironmentVariables()
                .Build();

    ConfigHelper.Configuration = retVal;
}

Code for converting DateTime into Unix epoch and back to DateTime

private static DateTime epoch = new DateTime(1970, 1, 1, 0, 0, 0);

public static long GetUNIXDate(DateTime value)
{
    return (Int64)value.Subtract(epoch).TotalSeconds;
}

public static DateTime GetNormalDateFromUnix(long value)
{
    return epoch.AddSeconds(value);
}

Code for determining if a string consists entirely of ASCII text or not

public static bool IsASCII(this string value)
{
    return Encoding.UTF8.GetByteCount(value) == value.Length;
}

Code for removing non-ASCII characters and retrieving just the ASCII characters from a string

private static readonly Regex asciiRegex = new Regex(@"[^\u0000-\u007F]+", RegexOptions.Compiled);

public static string GetASCIIOnly(string value)
{
    if (value == null) return String.Empty;
    return asciiRegex.Replace(value, String.Empty);
}

Code for getting a smaller chunk of a long string and if necessary append … at the end – useful on web pages showing first few characters of a longer text.

public static string GetSnippet(string value, int length, bool appendDots)
{
    if (String.IsNullOrWhiteSpace(value)) return String.Empty;

    if (value.Length < length - 3) return value;

    if (appendDots)
    {
        return $"{value.Substring(0, length - 3)}...";
    }
    else
    {
        return value.Substring(0, length);
    }
}

Mr. Kanti Kalyan Arumilli

Arumilli Kanti Kalyan, Founder & CEO
Arumilli Kanti Kalyan, Founder & CEO

B.Tech, M.B.A

Facebook

LinkedIn

Threads

Instagram

Youtube

Founder & CEO, Lead Full-Stack .Net developer

ALight Technology And Services Limited

ALight Technologies USA Inc

Youtube

Facebook

LinkedIn

Phone / SMS / WhatsApp on the following 3 numbers:

+91-789-362-6688, +1-480-347-6849, +44-07718-273-964

kantikalyan@gmail.com, kantikalyan@outlook.com, admin@alightservices.com, kantikalyan.arumilli@alightservices.com, KArumilli2020@student.hult.edu, KantiKArumilli@outlook.com and 3 more rarely used email addresses – hardly once or twice a year.

Categories
.Net Architecture C#

Some C# reusable code snippets – Video

Some C# reusable code snippets – Video

Categories
.Net C#

File tailer in C#

As mentioned in a previous post – Cancelling all activities at ALight Technology And Services Limited. I am not seriously working on anything within ALight Technology And Services Limited, but I am still .Net developer. I have some internal logging and monitoring implemented. I have used Cloudwatch Agent and Promtail for ingesting logs into AWS Cloudwatch and Grafana. Both are great platforms but I wanted to implement a similar tool in C#. Here is some sample code, explanation capable of doing something similar.

First store the name of file, Creation Date, Size, Last Modified Date. These can be accessed from FileInfo object.

var fi = new FileInfo("path");
fi.CreationTimeUtc	
fi.LastWriteTimeUtc	
fi.Length

Now, in a loop read the file, if new file i.e CreationTime is different read from beginning. If Length or LastWriteTime are different but same CreationTime, do a seek.

long seek = 0;

while(<some condition>)
{
   using(sr = new StreamReader(fi.OpenRead()){
      sr.BaseStream.Seek(seek, SeekOrigin.Begin);
      var data = await sr.ReadToEndAsync();
      seek += data.Length;
      // Do something with data
      // Store filename, seek in some persistent storage like a file
}

The above code block shows some sample code for using seek, we would store the variable seek along with FileCreation, Update, Length. Even if the application is restarted, the application would work properly.

Mr. Kanti Kalyan Arumilli

Arumilli Kanti Kalyan, Founder & CEO
Arumilli Kanti Kalyan, Founder & CEO

B.Tech, M.B.A

Facebook

LinkedIn

Threads

Instagram

Youtube

Founder & CEO, Lead Full-Stack .Net developer

ALight Technology And Services Limited

ALight Technologies USA Inc

Youtube

Facebook

LinkedIn

Phone / SMS / WhatsApp on the following 3 numbers:

+91-789-362-6688, +1-480-347-6849, +44-07718-273-964

kantikalyan@gmail.com, kantikalyan@outlook.com, admin@alightservices.com, kantikalyan.arumilli@alightservices.com, KArumilli2020@student.hult.edu, KantiKArumilli@outlook.com and 3 more rarely used email addresses – hardly once or twice a year.

Categories
.Net C# DailyReads

DailyReads 20/12/2022

How to Secure Passwords with BCrypt.NET

“In this article, we are going to learn how to secure passwords with BCrypt.NET to ensure we are up to the industry standards when it comes to security in our .NET environment.”

Schedule Jobs with Quartz.NET

“Recurring, background tasks are widespread and very common when building applications. These tasks can be long-running or repetitive and we don’t want to run them in the foreground, as they could affect the user’s experience of the application. So instead we must schedule these jobs to run in the background somewhere. To achieve this in .NET, we can use the Quartz.NET library to manage the creation and scheduling of these jobs.”

Mr. Kanti Kalyan Arumilli

Arumilli Kanti Kalyan, Founder & CEO
Arumilli Kanti Kalyan, Founder & CEO

B.Tech, M.B.A

Facebook

LinkedIn

Threads

Instagram

Youtube

Founder & CEO, Lead Full-Stack .Net developer

ALight Technology And Services Limited

ALight Technologies USA Inc

Youtube

Facebook

LinkedIn

Phone / SMS / WhatsApp on the following 3 numbers:

+91-789-362-6688, +1-480-347-6849, +44-07718-273-964

kantikalyan@gmail.com, kantikalyan@outlook.com, admin@alightservices.com, kantikalyan.arumilli@alightservices.com, KArumilli2020@student.hult.edu, KantiKArumilli@outlook.com and 3 more rarely used email addresses – hardly once or twice a year.

Categories
.Net C# DailyReads

Daily Reads 19/12/2022

Nullable Types in C#

In this article, we will extensively break down the concept of Nullable types in C#. We will discuss the kinds of Nullable types in C#, their characteristics, and how we can use them when building applications...”

How To Structure Your .NET Solutions: Architecture And Trade-Offs

“How should you design the structure of your .NET solutions? Microservices? Monolith? Feature folders? Clean architecture? Shared databases?…”

Frozen collections in .NET 8

“.NET 7 was freshly released but Microsoft does not sleep. .NET 8 is already in the making and I want to showcase to you one new area where the dotnet team is working on Frozen collections…”

PriorityQueues on .NET 7 and C# 11

“Starting from .NET 6 and C# 10, we finally have built-in support for PriorityQueues…”

Mr. Kanti Kalyan Arumilli

Arumilli Kanti Kalyan, Founder & CEO
Arumilli Kanti Kalyan, Founder & CEO

B.Tech, M.B.A

Facebook

LinkedIn

Threads

Instagram

Youtube

Founder & CEO, Lead Full-Stack .Net developer

ALight Technology And Services Limited

ALight Technologies USA Inc

Youtube

Facebook

LinkedIn

Phone / SMS / WhatsApp on the following 3 numbers:

+91-789-362-6688, +1-480-347-6849, +44-07718-273-964

kantikalyan@gmail.com, kantikalyan@outlook.com, admin@alightservices.com, kantikalyan.arumilli@alightservices.com, KArumilli2020@student.hult.edu, KantiKArumilli@outlook.com and 3 more rarely used email addresses – hardly once or twice a year.