#!/usr/bin/env python3
# SPDX-License-Identifier: Apache-2.0
# Copyright 2019 The Meson development team

'''
  Generates release notes for new releases of Meson build system
'''
import argparse
import subprocess
import re
import shutil
import datetime
from pathlib import Path

RELNOTE_TEMPLATE = '''---
title: Release {}
short-description: Release notes for {}
...

# New features{}

'''


def add_to_sitemap(sitemap, output_sitemap):
    '''
       Adds release note entry to sitemap.txt.
    '''
    sitemapfile = Path(sitemap)
    with sitemapfile.open(encoding='utf-8') as s_f:
        lines = s_f.readlines()
    relnotes = None
    to_version = None
    output = Path(output_sitemap)
    output.parent.mkdir(exist_ok=True, parents=True)
    with output.open('w', encoding='utf-8') as s_f:
        for line in lines:
            if relnotes is None:
                m = re.match(r'[\s]*Release-notes-for-([0-9]+)\.([0-9]+)\.([0-9]+)\.md', line)
                if m:
                    from_version = f'{m[1]}.{m[2]}.{m[3]}'
                    if from_version == '0.64.0':
                        to_version = '1.0.0'
                    else:
                        to_version = f'{m[1]}.{int(m[2]) + 1}.{m[3]}'
                    new_line = line.replace(from_version, to_version)
                    relnotes = new_line.strip()
                    s_f.write(new_line)
            s_f.write(line)

    if sitemapfile == output:
        subprocess.check_call(['git', 'add', output])

    return relnotes, to_version

def generate(relnotes, to_version, source_dir, output_dir):
    '''
       Generate notes for Meson build next release.
    '''
    title_suffix = ' (in development)' if output_dir else ''
    title = f'{to_version}{title_suffix}'
    output = Path(output_dir, relnotes) if output_dir else Path('markdown', relnotes)
    output.parent.mkdir(exist_ok=True, parents=True)
    with output.open('w', encoding='utf-8') as ofile:
        ofile.write(RELNOTE_TEMPLATE.format(title, to_version, title_suffix))
        if not output_dir:
            date = datetime.date.today()
            date_str = date.strftime("%d %B %Y")
            ofile.write(f'Meson {to_version} was released on {date_str}\n')
        for snippetfile in sorted(Path(source_dir, 'markdown/snippets').glob('*.md')):
            snippet = snippetfile.read_text(encoding='utf-8')
            ofile.write(snippet)
            if not snippet.endswith('\n'):
                ofile.write('\n')
            ofile.write('\n')

    if not output_dir:
        subprocess.check_call(['git', 'rm', 'markdown/snippets/*.md'])
        subprocess.check_call(['git', 'add', output])

if __name__ == '__main__':
    parser = argparse.ArgumentParser(description='Generate meson docs')
    parser.add_argument('--input-sitemap', default='sitemap.txt')
    parser.add_argument('--output-sitemap', default='sitemap.txt')
    parser.add_argument('--source-dir', default='.')
    parser.add_argument('--output-dir')

    args = parser.parse_args()

    if Path(args.source_dir, 'markdown/snippets').glob('*.md'):
        relnotes, to_version = add_to_sitemap(args.input_sitemap, args.output_sitemap)
        generate(relnotes, to_version, args.source_dir, args.output_dir)
    elif args.input_sitemap != args.output_sitemap:
        shutil.copyfile(args.input_sitemap, args.output_sitemap)
