Пример #1
0
        // match entry like
        //  <186>: 2020 Mar  4 17:20:54.183 UTC:
        public static bool TryParseIfStartsWithColonThenYear(ParserContext ctx)
        {
            var year    = DateTime.UtcNow.Year;
            var savePos = ctx.Position;

            if (ctx.Match(": ") && (ctx.Match($"{year}") || ctx.Match($"{year - 1}"))) //check prior year
            {
                // we already matched beyond year; move back:
                ctx.Position = savePos + ": ".Length;
                var UTC    = "PST:"; // "UTC:";
                var utcPos = ctx.Text.IndexOf(UTC, ctx.Position);
                if (utcPos > 0)
                {
                    var dtStr = ctx.Text.Substring(ctx.Position, utcPos - ctx.Position);
                    ctx.Position = utcPos + UTC.Length;
                    if (DateTime.TryParse(dtStr, out var dt))
                    {
                        ctx.Entry.Header.Timestamp = DateTime.SpecifyKind(dt, DateTimeKind.Utc);
                        return(true);
                    }
                }
            }
            ctx.Position = savePos;
            return(false);
        }
Пример #2
0
        public bool TryParse(ParserContext ctx)
        {
            if (!ctx.Reset())
            {
                return(false);
            }
            if (!ctx.Match("1 "))
            {
                return(false);
            }

            // It is RFC-5424 entry
            var entry = ctx.Entry;

            entry.PayloadType = PayloadType.Rfc5424;
            try
            {
                entry.Header = this.ParseHeader(ctx);
                this.ParseStructuredData(ctx);
                entry.Message = this.ParseMessage(ctx);
                return(true);
            }
            catch (Exception ex)
            {
                ctx.AddError(ex.Message);
                return(false);
            }
        }
Пример #3
0
        // match entry like
        //  <134> 03/04/2020:17:20:58 GMT ams07....
        public static bool TryParseIfStartsWithSpace(ParserContext ctx)
        {
            ctx.Reset();
            if (ctx.Current != SyslogChars.Space)
            {
                return(false);
            }
            var prefix = ctx.Text.Substring(ctx.Position, 25);
            var year   = DateTime.UtcNow.Year;

            if (prefix.Contains($"/{year}:") || prefix.Contains($"/{year - 1}:")) //(also check prior year)
            {
                ctx.Position++;
                var spPos = ctx.Text.IndexOf(" ", ctx.Position);
                if (spPos > 0)
                {
                    var dtStr = ctx.Text.Substring(ctx.Position, spPos - ctx.Position);
                    ctx.Position = spPos + 1;
                    ctx.Match("GMT"); //skip also GMT
                    if (DateTime.TryParse(dtStr, out var dt) ||
                        DateTime.TryParseExact(dtStr, "MM/dd/yyyy:HH:mm:ss", CultureInfo.InvariantCulture, DateTimeStyles.AssumeUniversal, out dt))
                    {
                        ctx.Entry.Header.Timestamp = dt.ToUniversalTime();
                    }
                }
                return(true);
            }
            return(false);
        }
Пример #4
0
        public bool TryParse(ParserContext ctx)
        {
            if (ctx.Current == SyslogChars.Space)
            {
                ctx.SkipSpaces();
            }

            // typically entries start with 'device=' or 'date='
            var match = ctx.Match("device=") || ctx.Match("date=");

            if (!match)
            {
                match = TryMatchAnyKey(ctx);
            }
            if (!match)
            {
                return(false);
            }

            // It is the format for this parser
            ctx.Reset(); // Match(...) moved the position, so return to the start
            ctx.Entry.PayloadType = PayloadType.KeyValuePairs;
            var kvList = ReadKeyValuePairs(ctx);

            ctx.Entry.ExtractedData.AddRange(kvList);
            // try some known values and put them in the header
            var hdr = ctx.Entry.Header;

            hdr.HostName = kvList.GetValue("device_id");
            var date = kvList.GetValue("date");
            var time = kvList.GetValue("time");

            if (date != null)
            {
                var dateTimeStr = $"{date}T{time}";
                if (DateTime.TryParse(dateTimeStr, out var dt))
                {
                    hdr.Timestamp = dt;
                }
            }

            return(true);
        } //method
Пример #5
0
        // match entry like
        //  <141>2020-03-04T17:20:54.412705+00:00 MWH....
        public static bool TryParseIfStartsWithYear(ParserContext ctx)
        {
            var year    = DateTime.UtcNow.Year;
            var savePos = ctx.Position;

            if (ctx.Match($"{year}-") || ctx.Match($"{year - 1}-")) //(also check prior year)
            {
                ctx.Position = savePos;
                var spPos = ctx.Text.IndexOf(" ", ctx.Position);//
                if (spPos > 0)
                {
                    var dtStr = ctx.Text.Substring(ctx.Position, spPos - ctx.Position);
                    ctx.Position = spPos;
                    if (DateTime.TryParse(dtStr, out var dt))
                    {
                        ctx.Entry.Header.Timestamp = dt.ToUniversalTime();
                        return(true);
                    }
                }
            }
            ctx.Position = savePos;
            return(false);
        }
Пример #6
0
        // let try to match any key, like <120> abc = def
        private bool TryMatchAnyKey(ParserContext ctx)
        {
            if (!char.IsLetter(ctx.Current))
            {
                return(false);
            }
            var savePos = ctx.Position;
            var word    = ctx.ReadWord();

            ctx.SkipSpaces();
            var result = ctx.Match("=");

            ctx.Position = savePos;
            return(result);
        }
Пример #7
0
        public static bool TryParseTimestamp(ParserContext ctx)
        {
            // sometimes there's starting space
            if (ctx.Current == SyslogChars.Space)
            {
                ctx.SkipSpaces();
            }

            // some messages start with some numeric Id:
            // <139>36177473: Mar  4 17:21:18 UTC:
            if (char.IsDigit(ctx.Current))
            {
                // make sure it's not a year and at least 5 chars
                var fiveDigits = ctx.Text.Substring(ctx.Position, 5).All(ch => char.IsDigit(ch));
                if (fiveDigits)
                {
                    var savePos = ctx.Position;
                    var digits  = ctx.ReadDigits(20);
                    if (ctx.Match(": "))
                    {
                        // we swallowed this numeric prefix and ': ' after that, nothing to do
                    }
                    else
                    {
                        ctx.Position = savePos; // rollback, timestamp evaluation will go from string start
                    }
                }
            }
            try
            {
                // quick guess - if it contains current month name
                if (TryParseIfStartsWithYear(ctx) || TryParseTimestampWithMonthName(ctx) ||
                    TryParseIfStartsWithColonThenYear(ctx) || TryParseIfStartsWithSpace(ctx))
                {
                    return(true);
                }
            }
            catch (Exception ex)
            {
                ctx.ErrorMessages.Add(ex.ToString());
            }
            return(false);
        }