Log Parsing, split into two parts.
Problem Overview
Part 1
You need to build a tool that parses and queries a set of server logs.
The input is a list of log lines as strings (List[str]), which get parsed for use by the rest of the tool.
Part 1: Parse and Filter
Implement a function that reads logs coming from different services and parses them into structured objects.
Things to watch out for:
- The input logs may be malformed or not conform to the expected format. Any log that can't be parsed should just be discarded.
- Each valid log should be parsed into the following shape:
{
"timestamp": datetime or string,
"level": "INFO" | "WARN" | "ERROR" | "DEBUG",
"service": string,
"message": string,
"user_id": string or None # fill this in if a user_id can be extracted from the message, otherwise None
}
Return value: List[ParsedLog] — that is, the list of all logs that were parsed successfully.
Part 2: Search Query with Operators
Using the structured logs from Part 1, implement a search function.
The user passes in a query string. The query string can be preceded by a number of filter conditions (operators), in the fixed format type:value. All operators sit at the start of the query string.
Supported filters:
- Log level (
level):level:info,level:warn,level:error,level:debug— filters logs by the given level. - Service name (
service): e.g.service:auth,service:payment,service:user— filters logs produced by the given service. - User ID (
userid): e.g.userid:12345— returns only logs belonging to that user. - Start time (
start): e.g.start:2024-01-01— meanstimestamp >= 2024-01-01(inclusive). - End time (
end): e.g.end:2024-01-31— meanstimestamp < 2024-01-31(exclusive).
Whatever plain text is left in the query string after all the operators is used as a keyword search against the message. For example, level:error service:auth timeout means: level = ERROR and service = auth, and the message contains "timeout".
Example queries:
- Example 1:
level:error service:auth— query all ERROR logs from the auth service. - Example 2:
level:info payment processed— query wherelevel = INFOand the message contains "payment processed". - Example 3:
userid:12345— query all logs produced by that user. - Example 4:
start:2024-01-01 end:2024-02-01— query the time range2024-01-01 <= timestamp < 2024-02-01.
Return value:
Return all logs matching the conditions, along with the count of matching logs. For example:
{ "count": 12, "logs": [ {...}, {...}, ... ] }
or:
(List[ParsedLog], count)
The exact return format is up to you, as long as it returns both the list of matched logs and the match count.
Discussion
Loading comments…