use crate::Result;
use rusqlite::{params, Connection};
use std::path::Path;
use super::walk_source_files;
const MAX_FILE_SIZE: u64 = 1_048_576;
pub fn load(conn: &Connection, repo_path: &Path) -> Result<()> {
conn.execute_batch(
"CREATE TABLE IF NOT EXISTS source_lines (
file_path TEXT,
line_number INTEGER,
content TEXT,
is_blank INTEGER,
PRIMARY KEY (file_path, line_number)
)",
)?;
let files = walk_source_files(repo_path);
conn.execute_batch("BEGIN")?;
let mut stmt = conn.prepare(
"INSERT OR IGNORE INTO source_lines
(file_path, line_number, content, is_blank)
VALUES (?1, ?2, ?3, ?4)",
)?;
for file_info in &files {
if file_info.size > MAX_FILE_SIZE {
continue;
}
let abs_path = repo_path.join(&file_info.path);
let Ok(bytes) = std::fs::read(&abs_path) else {
continue;
};
let content = String::from_utf8_lossy(&bytes);
for (i, line) in content.lines().enumerate() {
let line_number = (i + 1) as i64;
let is_blank: i64 = if line.trim().is_empty() { 1 } else { 0 };
stmt.execute(params![file_info.path, line_number, line, is_blank])?;
}
}
drop(stmt);
conn.execute_batch("COMMIT")?;
conn.execute_batch(
"CREATE INDEX IF NOT EXISTS idx_source_lines_content ON source_lines(content)",
)?;
Ok(())
}