Last active
August 29, 2021 18:58
-
-
Save sogaiu/95a3d36ba840eaf05bcec2d9ac53c1fa to your computer and use it in GitHub Desktop.
jsrc
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#! /usr/bin/env janet | |
# jsrc - display source associated with some janet symbol | |
# thanks to bakpakin and yumaikas | |
########################################################################### | |
## requirements ## | |
# janet | |
# git | |
# git clone of janet source code, preferably the latest | |
# web browser | |
########################################################################### | |
## tweakables ## | |
# program to open urls -- but may need to modify `os/execute` call below | |
(var browser-opener nil) | |
# non-windows | |
(set browser-opener "xdg-open") | |
#(set browser-opener "chromium") | |
#(set browser-opener "firefox") | |
#(set browser-opener "brave") | |
# windows | |
(when (= :windows (os/which)) | |
(set browser-opener "explorer")) | |
# locally reachable path of janet source code -- latest for best results | |
(var janet-source-path nil) | |
# non-windows | |
(set janet-source-path "/tmp/janet") | |
# windows | |
(when (= :windows (os/which)) | |
(set janet-source-path (string (os/getenv "TMP") `\janet`))) | |
########################################################################### | |
(def start-dir (os/cwd)) | |
(unless (os/stat janet-source-path) | |
(eprin "failed to find local janet source code, fetch? [y/N] ") | |
(def response (string/ascii-lower (string/trimr (getline)))) | |
(when (not= response "y") | |
(eprintf "please git clone janet's source to: %s" janet-source-path) | |
(os/exit 1)) | |
# | |
(def janet-src-parent # remove trailing dir separator + janet | |
(string/reverse (string/slice (string/reverse janet-source-path) 5))) | |
# `os/cs` returns `nil` for success... | |
(def success (not (os/cd janet-src-parent))) | |
(unless success | |
(eprintf "failed to change directory to: %s" janet-src-parent) | |
(os/exit 1)) | |
# | |
(try | |
(os/execute ["git" | |
"clone" | |
"https://github.com/janet-lang/janet"] | |
:px) | |
([err] | |
(eprintf "failed to clone janet source: %p" err) | |
(os/exit 1)))) | |
(unless (os/stat janet-source-path) | |
(eprintf "please git clone janet's source to: %s" janet-source-path) | |
(os/exit 1)) | |
(def arg (get (dyn :args) 1)) | |
(var doc-arg nil) | |
(var sym-arg nil) | |
(if arg | |
(if ((curenv) (symbol arg)) | |
(set sym-arg arg) | |
(set doc-arg (string `"` arg `"`))) | |
(let [all (all-bindings) | |
idx (math/rng-int (math/rng (os/cryptorand 3)) | |
(length all))] | |
(set sym-arg (get all idx)))) | |
(when doc-arg | |
(def code-string (string "(doc " doc-arg ")")) | |
(eval-string code-string) | |
(eprinf "failed to find symbol: %s" doc-arg) | |
(eprintf " -- see above for possible alternatives") | |
(os/exit 1)) | |
# XXX: should not happen | |
(unless sym-arg | |
(eprintf "failed to find symbol or alternatives for: %s" arg) | |
(os/exit 1)) | |
# find source file info | |
(def code-string (string "(dyn '" sym-arg ")")) | |
(def entry (eval-string code-string)) | |
(unless entry | |
(eprintf "failed to determine entry for: %p" sym-arg) | |
(os/exit 1)) | |
(var [path line] (entry :source-map)) | |
(unless (and path line) | |
(eprintf "failed to find source path and/or line for: %p" sym-arg) | |
(os/exit 1)) | |
# XXX: paths without a slash should be tweaked...is this only boot.janet? | |
(unless (string/find "/" path) | |
(set path (string "src/boot/" path))) | |
# `os/cd` returns `nil` on success...kind of weird | |
(def success (not (os/cd janet-source-path))) | |
(unless success | |
(eprintf "failed to set working directory to janet source at: %p" | |
janet-source-path) | |
(os/exit 1)) | |
(def build-type | |
(cond | |
(peg/match ~(some :h) janet/build) | |
:sha | |
# XXX: will be inaccurate -- how to figure out which commit was built with? | |
(= "local" janet/build) | |
:local | |
# | |
nil)) | |
(unless build-type | |
(eprintf "unexpected janet/build value: %p" janet/build) | |
(os/exit 1)) | |
(var sha nil) | |
(if (= build-type :local) | |
(try | |
(let [proc (os/spawn ["git" | |
"show-ref" "--tags" | |
(string "v" janet/version)] | |
:px | |
{:out :pipe}) | |
output (string/trimr (ev/read (proc :out) :all))] | |
(unless output | |
(error "failed to read output from git")) | |
(set sha (first (peg/match ~(capture (some :h)) output)))) | |
([err] | |
(eprintf "failed to determine full sha for janet/version: %s" | |
janet/version) | |
(error err))) | |
(try | |
(let [proc (os/spawn ["git" | |
"rev-list" "--max-count=1" | |
janet/build] | |
:px | |
{:out :pipe}) | |
output (string/trimr (ev/read (proc :out) :all))] | |
(if output | |
(set sha output) | |
(error "failed to read output from git"))) | |
([err] | |
(eprintf "failed to determine full sha for: %p" janet/build) | |
(error err)))) | |
(def url (string "https://github.com/janet-lang/janet/blob/" | |
sha | |
"/" | |
path | |
"#L" | |
line)) | |
(print url) | |
# XXX: on windows always an error? | |
(try | |
(os/execute [browser-opener url] | |
:px) | |
([err] | |
(unless (= :windows (os/which)) | |
(eprintf "problem trying to open url with: %p" browser-opener)))) | |
# XXX: only restores starting dir when no errors... | |
(os/cd start-dir) | |
########################################################################### | |
## future possibilities ## | |
# * option to open source via editor | |
# * update existing cloned janet source? | |
# * option to just print url without opening a browser | |
# * search within sources associated with pkgs (leverage short name)? |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment