handover.v

2.0 KB · raw

1//! The cut-over hand-off.2//!3//! While repos with an unmigrated Koh 2 `.koh/` directory still exist on this4//! machine, `koh` is Koh 3 but those repos belong to Koh 2. Rather than let a5//! command fail confusingly, Koh 3 hands it to `koh2` unchanged — same6//! arguments, same terminal. Agents always type `koh`, and every repo gets the7//! Koh that owns it.8//!9//! `migrate` is the exception: it is how such a repo stops being a Koh 2 repo.1011module cli1213import os14import src.fmt1516// hand_over reports whether this invocation belongs to Koh 2, and if so runs17// it. It never returns when the hand-off happens.18pub fn hand_over(argv []string) {19	if argv.len < 2 {20		return21	}22	command := argv[1]23	if command in ['migrate', 'man', 'help', '--help', '-h', '--version', '-v'] {24		return25	}26	if !inside_koh2_repo(os.getwd()) {27		return28	}29	target := koh2_binary()30	if target == '' {31		eprintln('  ${fmt.red(fmt.glyph_fail)} this folder holds a Koh 2 repo, and koh2 is not on PATH')32		eprintln('  install koh2, or run "koh migrate" to convert this repo')33		exit(1)34	}35	os.execvp(target, argv) or {36		eprintln('  ${fmt.red(fmt.glyph_fail)} could not hand this command to ${target}: ${err.msg()}')37		exit(1)38	}39}4041// koh2_binary finds the Koh 2 binary. Before the cutover it is still called42// `koh`, so that name is a fallback — never this binary itself, which would43// hand the command straight back to us for ever.44fn koh2_binary() string {45	if found := os.find_abs_path_of_executable('koh2') {46		return found47	}48	if legacy := os.find_abs_path_of_executable('koh') {49		if os.real_path(legacy) != os.real_path(os.executable()) {50			return legacy51		}52	}53	return ''54}5556// inside_koh2_repo looks upward for a `.koh` that is a directory. A `.koh`57// file is Koh 3's.58fn inside_koh2_repo(start string) bool {59	mut dir := os.real_path(start)60	for {61		path := os.join_path(dir, '.koh')62		if os.is_dir(path) {63			return true64		}65		if os.is_file(path) {66			return false67		}68		parent := os.dir(dir)69		if parent == dir || parent == '' {70			return false71		}72		dir = parent73	}74	return false75}