import re

def get_content_file(file_path):
    with open(file_path, 'r') as file:
        content = file.readlines()
        return content

def set_content_file(file_path, content):
    with open(file_path, 'w') as file:
        file.writelines(content)

def update_android_version():
    print('Updating Android version')
    file_path = 'android/app/build.gradle'
    content = get_content_file(file_path)
    new_version_name = None
    regex_version_name = re.compile(r'^\s*versionName\s+"(\d+\.\d+\.\d+)"')

    for i, line in enumerate(content):
        match_version_name = regex_version_name.match(line)
        if match_version_name:
            current_version_name = match_version_name.group(1)
            version_parts = list(map(int, current_version_name.split('.')))
            
            # Increment path
            version_parts[2] += 1
            
            # Increment minor if path is 10
            if version_parts[2] == 10:
                version_parts[2] = 0
                version_parts[1] += 1
            
            # Increment major if minor is 10
            if version_parts[1] == 10:
                version_parts[1] = 0
                version_parts[0] += 1

            new_version_name = '.'.join(map(str, version_parts))
            content[i] = f'        versionName "{new_version_name}"\n'
            break

    set_content_file(file_path, content)

    if new_version_name:
        strings_path = 'android/app/src/main/res/values/strings.xml'
        strings_content = get_content_file(strings_path)
        regex_strings_version = re.compile(r'^\s*<string name="expo_runtime_version">(\d+\.\d+\.\d+)<\/string>')

        for i, line in enumerate(strings_content):
            match_strings_version = regex_strings_version.match(line)
            if match_strings_version:
                strings_content[i] = f'    <string name="expo_runtime_version">{new_version_name}</string>\n'
                break

        set_content_file(strings_path, strings_content)

    return new_version_name

def update_ios_version(new_version):
    print('Updating iOS version')
    file_path = 'ios/humand.xcodeproj/project.pbxproj'
    content = get_content_file(file_path)
    regex_marketing_version = re.compile(r'^\s*MARKETING_VERSION\s*=\s*([^\s;]+)\s*;')
    marketing_version_updated = False
    
    for i, line in enumerate(content):
        match_marketing_version = regex_marketing_version.match(line)
        if match_marketing_version:
            content[i] = f'\t\t\t\tMARKETING_VERSION = {new_version};\n'
            marketing_version_updated = True

    set_content_file(file_path, content)

    return new_version if marketing_version_updated else None

def update_eas_runtime_version():
    print('Updating Expo Runtime Version')
    file_path = 'app.config.ts'
    content = get_content_file(file_path)
    new_version = None
    regex_runtime_version = re.compile(r'^\s*runtimeVersion:\s*[\'"](\d+\.\d+\.\d+)[\'"]')

    for i, line in enumerate(content):
        match_runtime_version = regex_runtime_version.match(line)
        if match_runtime_version:
            current_version = match_runtime_version.group(1)
            new_version = increment_version(f"{current_version}", part="patch")
            content[i] = f'    runtimeVersion: \'{new_version}\',\n'
            break

    set_content_file(file_path, content)

    return new_version

def get_current_version():
    content = get_content_file('app.config.ts')
    regex_runtime_version = re.compile(r'^\s*runtimeVersion:\s*[\'"](\d+\.\d+\.\d+)[\'"]')
    current_version = None

    for i, line in enumerate(content):
        match_runtime_version = regex_runtime_version.match(line)
        if match_runtime_version:
            current_version = match_runtime_version.group(1)
            break

    return current_version

def bump_branch_version(version: str, part: str = "patch") -> str:
    return f"v{increment_version(version.lstrip('v'), part)}"

def increment_version(version: str, part: str = "patch") -> str:
    match = re.match(r'(\d+)\.(\d+)\.(\d+)', version)
    if not match:
        raise ValueError(f"Invalid version format: {version}")
    
    major, minor, patch = map(int, match.groups())

    if part == "patch":
        patch += 1
        if patch > 9:
            patch = 0
            minor += 1
            if minor > 9:
                minor = 0
                major += 1

    elif part == "minor":
        minor += 1
        patch = 0
        if minor > 9:
            minor = 0
            major += 1

    elif part == "major":
        major += 1
        minor, patch = 0, 0
    else:
        raise ValueError("part must be 'major', 'minor', or 'patch'")

    return f"{major}.{minor}.{patch}"


def set_android_version(version: str) -> None:
    """Writes the given version (e.g. "4.2.2") to build.gradle versionName
    and strings.xml expo_runtime_version. Unlike update_android_version,
    this does not bump — it sets the value explicitly."""
    print(f'Setting Android version to {version}')
    gradle_path = 'android/app/build.gradle'
    gradle_content = get_content_file(gradle_path)
    regex_version_name = re.compile(r'^(\s*versionName\s+)"(\d+\.\d+\.\d+)"')
    for i, line in enumerate(gradle_content):
        if regex_version_name.match(line):
            gradle_content[i] = regex_version_name.sub(rf'\g<1>"{version}"', line)
            break
    set_content_file(gradle_path, gradle_content)

    strings_path = 'android/app/src/main/res/values/strings.xml'
    strings_content = get_content_file(strings_path)
    regex_strings_version = re.compile(
        r'^(\s*<string name="expo_runtime_version">)(\d+\.\d+\.\d+)(</string>)'
    )
    for i, line in enumerate(strings_content):
        if regex_strings_version.match(line):
            strings_content[i] = regex_strings_version.sub(rf'\g<1>{version}\g<3>', line)
            break
    set_content_file(strings_path, strings_content)


def set_eas_runtime_version(version: str) -> None:
    """Writes the given version (e.g. "4.2.2") to app.config.ts runtimeVersion.
    Unlike update_eas_runtime_version, this does not bump — it sets the value explicitly."""
    print(f'Setting Expo runtime version to {version}')
    file_path = 'app.config.ts'
    content = get_content_file(file_path)
    regex_runtime_version = re.compile(
        r'^(\s*runtimeVersion:\s*[\'"])(\d+\.\d+\.\d+)([\'"])'
    )
    for i, line in enumerate(content):
        if regex_runtime_version.match(line):
            content[i] = regex_runtime_version.sub(rf'\g<1>{version}\g<3>', line)
            break
    set_content_file(file_path, content)
