"""Foundation functions for project shell operations"""

# AUTOGENERATED! DO NOT EDIT! File to edit: ../nbs/00_core.ipynb.

# %% auto 0
__all__ = ['hr', 'kill_processes', 'find_free_port', 'setup_dark_theme', 'check_cmd', 'run_cmd', 'get_git_config']

# %% ../nbs/00_core.ipynb 3
import os
import socket
import argparse
import subprocess
import sys
from pathlib import Path
import shutil

# %% ../nbs/00_core.ipynb 5
hr = "_"

# %% ../nbs/00_core.ipynb 7
def kill_processes(args):
    """Kill all running pj-related processes"""
    print("🛑 Stopping all background processes...")
    
    processes = [
        ("jupyter", "Jupyter Lab servers and kernels"),
        ("nbdev_preview", "nbdev preview servers"),
        ("quarto.js preview", "Quarto.js Deno process"),
        ("quarto preview", "Quarto preview servers"),
    ]
    
    for pattern, name in processes:
        result = subprocess.run(["pkill", "-f", pattern], capture_output=True)
        if result.returncode == 0: print(f"   ✓ Stopped {name}")
        else: print(f"   - No {name} running")
    
    print("\n✅ All processes stopped!")

# %% ../nbs/00_core.ipynb 10
def find_free_port(start=64000):
    """Find first available port starting from given port"""
    for port in range(start, start + 100):
        with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s:
            if s.connect_ex(('localhost', port)) != 0: return port
    return start

# %% ../nbs/00_core.ipynb 13
def setup_dark_theme(project_path, log_file=None, verbose=False):
    """Set up dark mode theme for nbdev docs"""
    nbs_path = project_path / "nbs"
    
    # 1. Update _quarto.yml
    quarto_yml = nbs_path / "_quarto.yml"
    quarto_content = """project:
  type: website

format:
  html:
    theme:
      light: cosmo
      dark: [cosmo, dark.scss]
    css: styles.css
    toc: true
    keep-md: true
  commonmark: default

website:
  twitter-card: true
  open-graph: true
  repo-actions: [issue]
  navbar:
    background: primary
    search: true
  sidebar:
    style: floating

metadata-files: [nbdev.yml, sidebar.yml]
"""
    quarto_yml.write_text(quarto_content)
    
    # 2. Update styles.css
    styles_css = nbs_path / "styles.css"
    styles_content = """.cell {
  margin-bottom: 1rem;
}

.cell > .sourceCode {
  margin-bottom: 0;
}

.cell-output > pre {
  margin-bottom: 0;
}

.cell-output > pre, .cell-output > .sourceCode > pre, .cell-output-stdout > pre {
  margin-left: 0.8rem;
  margin-top: 0;
  background: none;
  border-left: 2px solid lightsalmon;
  border-top-left-radius: 0;
  border-top-right-radius: 0;
}

.cell-output > .sourceCode {
  border: none;
}

.cell-output > .sourceCode {
  background: none;
  margin-top: 0;
}

div.description {
  padding-left: 2px;
  padding-top: 5px;
  font-style: italic;
  font-size: 135%;
  opacity: 70%;
}
"""
    styles_css.write_text(styles_content)
    
    # 3. Create dark.scss
    dark_scss = nbs_path / "dark.scss"
    dark_content = """/*-- scss:defaults --*/

// Base document colors for dark mode
$body-bg: #181818;
$body-color: #ccc;
$link-color: #75AADB;

// Code blocks
$code-block-bg-alpha: -.9;

// Navbar
$navbar-bg: #2a2a2a;

/*-- scss:rules --*/

// Fix cell output text visibility in dark mode
.cell-output,
.cell-output-display {
  color: #ccc;
}

.cell-output pre {
  color: #ccc;
  background-color: #1e1e1e;
}

// Ensure code output is visible
.cell-output > pre code,
.cell-output-stdout pre {
  color: #ccc;
}

// Fix inline code in dark mode
code:not(pre > code) {
  background-color: #2a2a2a !important;
  color: #ab8dff;
}

// Fix blockquote code blocks in dark mode
blockquote pre,
blockquote pre code {
  color: #ccc;
  background-color: #1e1e1e;
}

blockquote {
  border-left-color: #555;
  color: #bbb;
}
"""
    dark_scss.write_text(dark_content)
    
    if log_file:
        with open(log_file, 'a') as f:
            f.write("\n" + hr*60 + "\n")
            f.write("Set up dark theme customization\n")
            f.write(hr*60 + "\n")

# %% ../nbs/00_core.ipynb 16
def check_cmd(cmd, install_hint):
    """Check if a command exists in PATH"""
    if not shutil.which(cmd):
        print(f"❌ Error: '{cmd}' is not installed")
        print(f"   Install with: {install_hint}")
        return False
    return True

# %% ../nbs/00_core.ipynb 19
def run_cmd(cmd, cwd=None, check=True, capture_output=False, log_file=None, verbose=False):
    """Run a shell command with optional logging and pretty output"""
    
    # Show command if verbose
    if verbose and not capture_output: print(f"   > {' '.join(cmd)}")
    
    # Log command to file
    if log_file:
        with open(log_file, 'a') as f:
            f.write(f"\n{hr*60}\n")
            f.write(f"Command: {' '.join(cmd)}\n")
            f.write(f"{hr*60}\n")
    
    # Handle capture_output mode (for getting return values)
    if capture_output:
        result = subprocess.run(cmd, cwd=cwd, check=check, capture_output=True, text=True)
        if log_file:
            with open(log_file, 'a') as f:
                f.write(result.stdout)
                if result.stderr: f.write(result.stderr)
        return result
    
    # Verbose mode: stream output with box drawing
    if verbose:
        print("   ┌──────────")
        process = subprocess.Popen(cmd, cwd=cwd, stdout=subprocess.PIPE, stderr=subprocess.STDOUT, text=True)
        for line in process.stdout:
            line = line.rstrip()
            print(f"   │ {line}")
            if log_file:
                with open(log_file, 'a') as f: f.write(line + '\n')
        process.wait()
        print("   └─")
        
        if check and process.returncode != 0: raise subprocess.CalledProcessError(process.returncode, cmd)
        
        # Create a mock result object for compatibility
        class Result:
            def __init__(self, returncode):
                self.returncode = returncode
                self.stdout = ""
                self.stderr = ""
        return Result(process.returncode)
    
    # Silent mode: just log to file
    else:
        if log_file:
            with open(log_file, 'a') as f:
                result = subprocess.run(cmd, cwd=cwd, check=check, stdout=f, stderr=subprocess.STDOUT, text=True)
        else:
            result = subprocess.run(cmd, cwd=cwd, check=check, stdout=subprocess.DEVNULL, stderr=subprocess.STDOUT, text=True)
        return result

# %% ../nbs/00_core.ipynb 22
def get_git_config(key):
    """Get git config value"""
    try:
        result = subprocess.run(["git", "config", "--get", key], capture_output=True, text=True, check=True)
        return result.stdout.strip()
    except: return None
