handover.v

2.1 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	// execvp builds argv as [path, ...cmdargs], so the arguments go without36	// our own argv[0].37	os.execvp(target, argv[1..]) or {38		eprintln('  ${fmt.red(fmt.glyph_fail)} could not hand this command to ${target}: ${err.msg()}')39		exit(1)40	}41}4243// koh2_binary finds the Koh 2 binary. Before the cutover it is still called44// `koh`, so that name is a fallback — never this binary itself, which would45// hand the command straight back to us for ever.46fn koh2_binary() string {47	if found := os.find_abs_path_of_executable('koh2') {48		return found49	}50	if legacy := os.find_abs_path_of_executable('koh') {51		if os.real_path(legacy) != os.real_path(os.executable()) {52			return legacy53		}54	}55	return ''56}5758// inside_koh2_repo looks upward for a `.koh` that is a directory. A `.koh`59// file is Koh 3's.60fn inside_koh2_repo(start string) bool {61	mut dir := os.real_path(start)62	for {63		path := os.join_path(dir, '.koh')64		if os.is_dir(path) {65			return true66		}67		if os.is_file(path) {68			return false69		}70		parent := os.dir(dir)71		if parent == dir || parent == '' {72			return false73		}74		dir = parent75	}76	return false77}