#!/usr/bin/env -S awk -f
# Copyright (c) 2022 Robin Jarry
# Modified 2022-06-16 by Simon Bruder to use ANSI colors
# Modified 2022-06-16 by Simon Bruder to a /usr/bin/env shebang

BEGIN {
	url = "\x1b[33m" # yellow
	header = "\x1b[35m" # purple
	signature = "\x1b[35m" # purple
	diff_meta = "\x1b[1;37m" # bold white
	diff_chunk = "\x1b[36m" # cyan
	diff_add = "\x1b[32m" # green
	diff_del = "\x1b[31m" # red
	quote_1 = "\x1b[34m"  # blue
	quote_2 = "\x1b[91m" # orange
	quote_3 = "\x1b[35m" # purple
	quote_4 = "\x1b[95m" # pink
	quote_x = "\x1b[37m" # gray
	reset = "\x1b[0m"
	# state
	in_diff = 0
	in_signature = 0
	in_headers = 0
	in_body = 0
	# patterns
	header_pattern = @/^[A-Z][[:alnum:]-]+:/
	url_pattern = @/[a-z]{2,6}:\/\/[[:graph:]]+|(mailto:)?[[:alnum:]_\+\.~\/-]*[[:alnum:]_]@[[:lower:]][[:alnum:]\.-]*[[:lower:]]/
}
function color_quote(line) {
	level = 0
	quotes = ""
	while (line ~ /^>/) {
		level += 1
		quotes = quotes ">"
		line = substr(line, 2)
		while (line ~ /^ /) {
			quotes = quotes " "
			line = substr(line, 2)
		}
	}
	if (level == 1) {
		color = quote_1
	} else if (level == 2) {
		color = quote_2
	} else if (level == 3) {
		color = quote_3
	} else if (level == 4) {
		color = quote_4
	} else {
		color = quote_x
	}
	if (line ~ /^\+/) {
		return color quotes diff_add line reset
	} else if (line ~ /^-/) {
		return color quotes diff_del line reset
	}
	gsub(url_pattern, url "&" color, line)
	return color quotes line reset
}
{
	# Strip carriage returns from line
	sub(/\r$/, "")

	if (in_diff) {
		if ($0 ~ /^-- ?$/) {
			in_signature = 1
			in_diff = 0
			in_headers = 0
			in_body = 0
			$0 = signature $0 reset
		} else if ($0 ~ /^@@ /) {
			$0 = diff_chunk $0 reset
		} else if ($0 ~ /^(diff --git|index|---|\+\+\+) /) {
			$0 = diff_meta $0 reset
		} else if ($0 ~ /^\+/) {
			$0 = diff_add $0 reset
		} else if ($0 ~ /^-/) {
			$0 = diff_del $0 reset
		}
	} else if (in_signature) {
		gsub(url_pattern, url "&" signature)
		$0 = signature $0 reset
	} else if (in_headers) {
		if ($0 ~ /^$/) {
			in_signature = 0
			in_diff = 0
			in_headers = 0
			in_body = 1
		} else {
			sub(header_pattern, header "&" reset)
			gsub(url_pattern, url "&" reset)
		}
	} else if (in_body) {
		if ($0 ~ /^>/) {
			$0 = color_quote($0)
		} else if ($0 ~ /^diff --git /) {
			in_signature = 0
			in_diff = 1
			in_headers = 0
			in_body = 0
			$0 = diff_meta $0 reset
		} else if ($0 ~ /^-- ?$/) {
			in_signature = 1
			in_diff = 0
			in_headers = 0
			in_body = 0
			$0 = signature $0 reset
		} else {
			gsub(url_pattern, url "&" reset)
		}
	} else if ($0 ~ /^diff --git /) {
		in_signature = 0
		in_diff = 1
		in_headers = 0
		in_body = 0
		$0 = diff_meta $0 reset
	} else if ($0 ~ /^-- ?$/) {
		in_signature = 1
		in_diff = 0
		in_headers = 0
		in_body = 0
		$0 = signature $0 reset
	} else if ($0 ~ header_pattern) {
		in_signature = 0
		in_diff = 0
		in_headers = 1
		in_body = 0
		sub(header_pattern, header "&" reset)
		gsub(url_pattern, url "&" reset)
	} else {
		in_signature = 0
		in_diff = 0
		in_headers = 0
		in_body = 1
		if ($0 ~ /^>/) {
			$0 = color_quote($0)
		} else {
			gsub(url_pattern, url "&" reset)
		}
	}

	print
}

