from datetime import datetime, timezone
import jenkins
import netrc
import re
import sys
from pprint import pp


epoch = datetime.fromisoformat('2025-01-31T00:00:00Z')
auth = netrc.netrc().authenticators('integration.wikimedia.org')

if auth is None:
    raise SystemExit('no netrc entry for integration.wikimedia.org')

username, _, password = auth

server = jenkins.Jenkins(
    'https://integration.wikimedia.org/ci/',
    username=username,
    password=password,
)

hit_miss_re = re.compile('Success cache: (HIT|MISS)')
cache_key_re = re.compile('Saving success cache entry: successcache/([a-f0-9]+)')

def print_builds(job_name):
    job = server.get_job_info(job_name, 0, True)
    for build in job['builds']:
        build = server.get_build_info(job_name, build['number'], depth=2)

        if build['building']:
            continue

        timestamp = datetime.fromtimestamp(build['timestamp'] / 1000.0, tz=timezone.utc)
        if timestamp < epoch:
            return

        console = server.get_build_console_output(job_name, build['number'])
        match = hit_miss_re.search(console)
        key_match = cache_key_re.search(console)
        if match is not None:
            parameters = build_parameters(build)
            print(
                '\t'.join([
                    timestamp.isoformat(),
                    match[1],
                    job_name,
                    str(build['number']),
                    str(build['duration']),
                    parameters.get('ZUUL_PIPELINE', ''),
                    parameters.get('ZUUL_PROJECT', ''),
                    parameters.get('ZUUL_CHANGE', ''),
                    parameters.get('ZUUL_PATCHSET', ''),
                    key_match[1] if key_match is not None else '',
                    build['url'],
                ]),
                flush=True,
            )

def build_parameters(build):
    for action in build['actions']:
        if '_class' in action and action['_class'] == 'hudson.plugins.gearman.NodeParametersAction':
            return {
                (param['name']): param['value']
                for param in action['parameters']
            }

    return {}

print('\t'.join([
    'timestamp',
    'cache',
    'job',
    'build',
    'duration',
    'pipeline',
    'project',
    'change',
    'patchset',
    'cache_key',
    'build_url',
]))

jobs = [
    'api-testing-mysql-php74',
    'api-testing-sqlite-php74',
    'mediawiki-phpbench-patch',
    'mediawiki-quibble-apitests-composer-php74',
    'mediawiki-quibble-apitests-composer-php81',
    'mediawiki-quibble-apitests-composer-php82',
    'mediawiki-quibble-apitests-composer-php83',
    'mediawiki-quibble-apitests-composer-php84',
    'mediawiki-quibble-apitests-vendor-php74',
    'mediawiki-quibble-apitests-vendor-php81',
    'mediawiki-quibble-apitests-vendor-php82',
    'mediawiki-quibble-apitests-vendor-php83',
    'mediawiki-quibble-apitests-vendor-php84',
    'mediawiki-quibble-composer-mysql-php74',
    'mediawiki-quibble-composer-mysql-php81',
    'mediawiki-quibble-composer-mysql-php82',
    'mediawiki-quibble-composer-mysql-php83',
    'mediawiki-quibble-composer-mysql-php84',
    'mediawiki-quibble-composer-postgres-php74',
    'mediawiki-quibble-composer-postgres-php81',
    'mediawiki-quibble-composer-postgres-php82',
    'mediawiki-quibble-composer-postgres-php83',
    'mediawiki-quibble-composer-postgres-php84',
    'mediawiki-quibble-composer-sqlite-php74',
    'mediawiki-quibble-composer-sqlite-php81',
    'mediawiki-quibble-composer-sqlite-php82',
    'mediawiki-quibble-composer-sqlite-php83',
    'mediawiki-quibble-composer-sqlite-php84',
    'mediawiki-quibble-selenium-composer-mysql-php74',
    'mediawiki-quibble-selenium-composer-mysql-php81',
    'mediawiki-quibble-selenium-composer-mysql-php82',
    'mediawiki-quibble-selenium-composer-mysql-php83',
    'mediawiki-quibble-selenium-composer-mysql-php84',
    'mediawiki-quibble-selenium-composer-postgres-php74',
    'mediawiki-quibble-selenium-composer-postgres-php81',
    'mediawiki-quibble-selenium-composer-postgres-php82',
    'mediawiki-quibble-selenium-composer-postgres-php83',
    'mediawiki-quibble-selenium-composer-postgres-php84',
    'mediawiki-quibble-selenium-composer-sqlite-php74',
    'mediawiki-quibble-selenium-composer-sqlite-php81',
    'mediawiki-quibble-selenium-composer-sqlite-php82',
    'mediawiki-quibble-selenium-composer-sqlite-php83',
    'mediawiki-quibble-selenium-composer-sqlite-php84',
    'mediawiki-quibble-selenium-vendor-mysql-php74',
    'mediawiki-quibble-selenium-vendor-mysql-php81',
    'mediawiki-quibble-selenium-vendor-mysql-php82',
    'mediawiki-quibble-selenium-vendor-mysql-php83',
    'mediawiki-quibble-selenium-vendor-mysql-php84',
    'mediawiki-quibble-selenium-vendor-postgres-php74',
    'mediawiki-quibble-selenium-vendor-postgres-php81',
    'mediawiki-quibble-selenium-vendor-postgres-php82',
    'mediawiki-quibble-selenium-vendor-postgres-php83',
    'mediawiki-quibble-selenium-vendor-postgres-php84',
    'mediawiki-quibble-selenium-vendor-sqlite-php74',
    'mediawiki-quibble-selenium-vendor-sqlite-php81',
    'mediawiki-quibble-selenium-vendor-sqlite-php82',
    'mediawiki-quibble-selenium-vendor-sqlite-php83',
    'mediawiki-quibble-selenium-vendor-sqlite-php84',
    'mediawiki-quibble-vendor-mysql-php74',
    'mediawiki-quibble-vendor-mysql-php81',
    'mediawiki-quibble-vendor-mysql-php82',
    'mediawiki-quibble-vendor-mysql-php83',
    'mediawiki-quibble-vendor-mysql-php84',
    'mediawiki-quibble-vendor-postgres-php74',
    'mediawiki-quibble-vendor-postgres-php81',
    'mediawiki-quibble-vendor-postgres-php82',
    'mediawiki-quibble-vendor-postgres-php83',
    'mediawiki-quibble-vendor-postgres-php84',
    'mediawiki-quibble-vendor-sqlite-php74',
    'mediawiki-quibble-vendor-sqlite-php81',
    'mediawiki-quibble-vendor-sqlite-php82',
    'mediawiki-quibble-vendor-sqlite-php83',
    'mediawiki-quibble-vendor-sqlite-php84',
    'mwext-phpunit-coverage',
    'mwext-phpunit-coverage-patch',
    'mwskin-phpunit-coverage-patch',
    'quibble-composer-mysql-php74',
    'quibble-composer-mysql-php74-noselenium',
    'quibble-composer-mysql-php74-phpunit-standalone',
    'quibble-composer-mysql-php74-selenium',
    'quibble-composer-mysql-php81',
    'quibble-composer-mysql-php81-noselenium',
    'quibble-composer-mysql-php81-phpunit-standalone',
    'quibble-composer-mysql-php81-selenium',
    'quibble-composer-mysql-php82',
    'quibble-composer-mysql-php82-noselenium',
    'quibble-composer-mysql-php82-phpunit-standalone',
    'quibble-composer-mysql-php82-selenium',
    'quibble-composer-mysql-php83',
    'quibble-composer-mysql-php83-noselenium',
    'quibble-composer-mysql-php83-phpunit-standalone',
    'quibble-composer-mysql-php83-selenium',
    'quibble-composer-mysql-php84',
    'quibble-composer-mysql-php84-noselenium',
    'quibble-composer-mysql-php84-phpunit-standalone',
    'quibble-composer-mysql-php84-selenium',
    'quibble-composer-postgres-php74',
    'quibble-composer-postgres-php74-noselenium',
    'quibble-composer-postgres-php74-phpunit-standalone',
    'quibble-composer-postgres-php74-selenium',
    'quibble-composer-postgres-php81',
    'quibble-composer-postgres-php81-noselenium',
    'quibble-composer-postgres-php81-phpunit-standalone',
    'quibble-composer-postgres-php81-selenium',
    'quibble-composer-postgres-php82',
    'quibble-composer-postgres-php82-noselenium',
    'quibble-composer-postgres-php82-phpunit-standalone',
    'quibble-composer-postgres-php82-selenium',
    'quibble-composer-postgres-php83',
    'quibble-composer-postgres-php83-noselenium',
    'quibble-composer-postgres-php83-phpunit-standalone',
    'quibble-composer-postgres-php83-selenium',
    'quibble-composer-postgres-php84',
    'quibble-composer-postgres-php84-noselenium',
    'quibble-composer-postgres-php84-phpunit-standalone',
    'quibble-composer-postgres-php84-selenium',
    'quibble-composer-sqlite-php74',
    'quibble-composer-sqlite-php74-noselenium',
    'quibble-composer-sqlite-php74-phpunit-standalone',
    'quibble-composer-sqlite-php74-selenium',
    'quibble-composer-sqlite-php81',
    'quibble-composer-sqlite-php81-noselenium',
    'quibble-composer-sqlite-php81-phpunit-standalone',
    'quibble-composer-sqlite-php81-selenium',
    'quibble-composer-sqlite-php82',
    'quibble-composer-sqlite-php82-noselenium',
    'quibble-composer-sqlite-php82-phpunit-standalone',
    'quibble-composer-sqlite-php82-selenium',
    'quibble-composer-sqlite-php83',
    'quibble-composer-sqlite-php83-noselenium',
    'quibble-composer-sqlite-php83-phpunit-standalone',
    'quibble-composer-sqlite-php83-selenium',
    'quibble-composer-sqlite-php84',
    'quibble-composer-sqlite-php84-noselenium',
    'quibble-composer-sqlite-php84-phpunit-standalone',
    'quibble-composer-sqlite-php84-selenium',
    'quibble-daily-Cognate-vendor-mysql-php74',
    'quibble-daily-InterwikiSorting-vendor-mysql-php74',
    'quibble-vendor-mysql-php74',
    'quibble-vendor-mysql-php74-noselenium',
    'quibble-vendor-mysql-php74-phpunit-standalone',
    'quibble-vendor-mysql-php74-selenium',
    'quibble-vendor-mysql-php81',
    'quibble-vendor-mysql-php81-noselenium',
    'quibble-vendor-mysql-php81-phpunit-standalone',
    'quibble-vendor-mysql-php81-selenium',
    'quibble-vendor-mysql-php82',
    'quibble-vendor-mysql-php82-noselenium',
    'quibble-vendor-mysql-php82-phpunit-standalone',
    'quibble-vendor-mysql-php82-selenium',
    'quibble-vendor-mysql-php83',
    'quibble-vendor-mysql-php83-noselenium',
    'quibble-vendor-mysql-php83-phpunit-standalone',
    'quibble-vendor-mysql-php83-selenium',
    'quibble-vendor-mysql-php84',
    'quibble-vendor-mysql-php84-noselenium',
    'quibble-vendor-mysql-php84-phpunit-standalone',
    'quibble-vendor-mysql-php84-selenium',
    'quibble-vendor-postgres-php74',
    'quibble-vendor-postgres-php74-noselenium',
    'quibble-vendor-postgres-php74-phpunit-standalone',
    'quibble-vendor-postgres-php74-selenium',
    'quibble-vendor-postgres-php81',
    'quibble-vendor-postgres-php81-noselenium',
    'quibble-vendor-postgres-php81-phpunit-standalone',
    'quibble-vendor-postgres-php81-selenium',
    'quibble-vendor-postgres-php82',
    'quibble-vendor-postgres-php82-noselenium',
    'quibble-vendor-postgres-php82-phpunit-standalone',
    'quibble-vendor-postgres-php82-selenium',
    'quibble-vendor-postgres-php83',
    'quibble-vendor-postgres-php83-noselenium',
    'quibble-vendor-postgres-php83-phpunit-standalone',
    'quibble-vendor-postgres-php83-selenium',
    'quibble-vendor-postgres-php84',
    'quibble-vendor-postgres-php84-noselenium',
    'quibble-vendor-postgres-php84-phpunit-standalone',
    'quibble-vendor-postgres-php84-selenium',
    'quibble-vendor-sqlite-php74',
    'quibble-vendor-sqlite-php74-noselenium',
    'quibble-vendor-sqlite-php74-phpunit-standalone',
    'quibble-vendor-sqlite-php74-selenium',
    'quibble-vendor-sqlite-php81',
    'quibble-vendor-sqlite-php81-noselenium',
    'quibble-vendor-sqlite-php81-phpunit-standalone',
    'quibble-vendor-sqlite-php81-selenium',
    'quibble-vendor-sqlite-php82',
    'quibble-vendor-sqlite-php82-noselenium',
    'quibble-vendor-sqlite-php82-phpunit-standalone',
    'quibble-vendor-sqlite-php82-selenium',
    'quibble-vendor-sqlite-php83',
    'quibble-vendor-sqlite-php83-noselenium',
    'quibble-vendor-sqlite-php83-phpunit-standalone',
    'quibble-vendor-sqlite-php83-selenium',
    'quibble-vendor-sqlite-php84',
    'quibble-vendor-sqlite-php84-noselenium',
    'quibble-vendor-sqlite-php84-phpunit-standalone',
    'quibble-vendor-sqlite-php84-selenium',
    'wikibase-client-php74',
    'wikibase-client-php81',
    'wikibase-client-php83',
    'wikibase-repo-php74',
    'wikibase-repo-php81',
    'wikibase-repo-php83',
    'wmf-quibble-core-vendor-mysql-php74',
    'wmf-quibble-core-vendor-mysql-php81',
    'wmf-quibble-selenium-php74',
    'wmf-quibble-selenium-php81',
    'wmf-quibble-vendor-mysql-php74',
    'wmf-quibble-vendor-mysql-php81',
]

for job_name in jobs:
    print_builds(job_name)
