diff options
| author | ewy <ewy0@protonmail.com> | 2026-05-02 18:28:40 +0200 |
|---|---|---|
| committer | ewy <ewy0@protonmail.com> | 2026-05-02 18:28:40 +0200 |
| commit | e8b9ca135642c76000bc0ec2e78674c602a748dd (patch) | |
| tree | 4e502ce767a4a4f70e40d6e72a3817bc139f1300 /runner | |
| parent | 35e6ac334f6a62cf63b743182cd5355f6baf4406 (diff) | |
add .js and .ts support
also: remove unused/duplicate method runner.Hydrate
Diffstat (limited to 'runner')
| -rw-r--r-- | runner/exc/runner.go | 8 | ||||
| -rw-r--r-- | runner/js/indexer.go | 39 | ||||
| -rw-r--r-- | runner/js/js.go | 106 | ||||
| -rw-r--r-- | runner/js/runner.go | 28 | ||||
| -rw-r--r-- | runner/js/target_npm.go | 42 | ||||
| -rw-r--r-- | runner/js/target_script.go | 55 | ||||
| -rw-r--r-- | runner/python/runner.go | 5 | ||||
| -rw-r--r-- | runner/shell/hydrated.go | 14 | ||||
| -rw-r--r-- | runner/shell/target.go | 4 |
9 files changed, 274 insertions, 27 deletions
diff --git a/runner/exc/runner.go b/runner/exc/runner.go index 092fd80..2eae44c 100644 --- a/runner/exc/runner.go +++ b/runner/exc/runner.go @@ -9,14 +9,6 @@ import ( "path/filepath" ) -func (e *exc) Hydrate(target model.Target) (model.HydratedTarget, error) { - return &Hydrated{ - BaseHydration: &runner.BaseHydration[*Executable]{ - Self: target.(*Executable), - }, - }, nil -} - func (e *exc) Wants(fs fs.FS, file string, entry fs.DirEntry) (bool, error) { if entry.IsDir() { return false, nil diff --git a/runner/js/indexer.go b/runner/js/indexer.go new file mode 100644 index 0000000..8a2a6b2 --- /dev/null +++ b/runner/js/indexer.go @@ -0,0 +1,39 @@ +package js + +import ( + "encoding/json" + "errors" + "github.com/ewy1/pik/model" + "io/fs" + "os" + "path/filepath" +) + +type Package struct { + Scripts map[string]string `json:"scripts"` +} + +func (n *js) Index(path string, f fs.FS, runners []model.Runner) ([]model.Target, error) { + p := &Package{} + // are there any other package.jsons? i hope not, because i don't know them + content, err := os.ReadFile(filepath.Join(path, "package.json")) + if errors.Is(err, fs.ErrNotExist) { + return nil, nil + } else if err != nil { + return nil, err + } + err = json.Unmarshal(content, p) + if err != nil { + return nil, err + } + + var targets []model.Target + if n.Npm == "" { + return nil, NoNpm + } + for k, s := range p.Scripts { + targets = append(targets, n.CreateRun(k, s)) + } + + return targets, nil +} diff --git a/runner/js/js.go b/runner/js/js.go new file mode 100644 index 0000000..7c2af58 --- /dev/null +++ b/runner/js/js.go @@ -0,0 +1,106 @@ +package js + +import ( + "errors" + "github.com/ewy1/pik/identity" + "github.com/ewy1/pik/model" + "github.com/ewy1/pik/runner" + "os/exec" + "path/filepath" + "slices" +) + +var jsExtensions = []string{ + ".js", + ".cjs", +} + +var tsExtensions = []string{ + ".ts", +} + +var extensions = append(jsExtensions, tsExtensions...) + +var managers = []string{ + "pnpm", + "yarn", + "npm", +} + +var jsInterpreters = []string{ + "node", + "bun", +} + +var tsInterpeters = []string{ + "ts", + "ts-node", + "bun", +} + +type js struct { + JsInterpreter string + TsInterpreter string + Npm string +} + +var Js = &js{} + +var UnsupportedFile = errors.New("unsupported file") +var NoJsInterpreter = errors.New("no js interpreter found in $PATH") +var NoTsInterpreter = errors.New("no ts interpreter found in $PATH") +var NoNpm = errors.New("npm not found in $PATH") + +func (n *js) Interpreter(file string) (string, error) { + ext := filepath.Ext(file) + if slices.Contains(jsInterpreters, ext) { + if n.JsInterpreter == "" { + return "", NoJsInterpreter + } + return n.JsInterpreter, nil + } + if slices.Contains(tsInterpeters, ext) { + if n.TsInterpreter == "" { + return "", NoTsInterpreter + } + return n.TsInterpreter, nil + } + return "", UnsupportedFile +} + +func (n *js) Init() error { + for _, p := range jsInterpreters { + if r, err := exec.LookPath(p); err != nil { + n.JsInterpreter = r + } + } + for _, p := range tsInterpeters { + if r, err := exec.LookPath(p); err != nil { + n.TsInterpreter = r + } + } + + for _, m := range managers { + if r, err := exec.LookPath(m); err == nil { + n.Npm = r + } + } + + return nil +} + +var npmSub = []string{ + "npm", +} + +func (n *js) CreateRun(name, cmd string) model.Target { + return &Npm{ + BaseTarget: runner.BaseTarget{ + Identity: identity.New(cmd), + MyTags: model.TagsFromFilename(cmd), + MySub: npmSub, + }, + Name: name, + Cmd: cmd, + } +} diff --git a/runner/js/runner.go b/runner/js/runner.go new file mode 100644 index 0000000..8b5f4f1 --- /dev/null +++ b/runner/js/runner.go @@ -0,0 +1,28 @@ +package js + +import ( + "github.com/ewy1/pik/identity" + "github.com/ewy1/pik/model" + "github.com/ewy1/pik/runner" + "io/fs" + "path/filepath" + "slices" +) + +func (n *js) Wants(fs fs.FS, file string, entry fs.DirEntry) (bool, error) { + ext := filepath.Ext(entry.Name()) + return slices.Contains(extensions, ext), nil +} + +func (n *js) CreateTarget(fs fs.FS, source string, file string, entry fs.DirEntry) (model.Target, error) { + ext := filepath.Ext(entry.Name()) + typed := slices.Contains(tsExtensions, ext) + return &Script{ + BaseTarget: runner.BaseTarget{ + Identity: identity.New(entry.Name()), + MyTags: model.TagsFromFilename(entry.Name()), + MySub: runner.SubFromFile(file), + }, + Typed: typed, + }, nil +} diff --git a/runner/js/target_npm.go b/runner/js/target_npm.go new file mode 100644 index 0000000..8319fad --- /dev/null +++ b/runner/js/target_npm.go @@ -0,0 +1,42 @@ +package js + +import ( + "github.com/ewy1/pik/model" + "github.com/ewy1/pik/runner" + "os/exec" + "path/filepath" +) + +type Npm struct { + runner.BaseTarget + Name string + Cmd string +} + +func (n *Npm) Icon() string { + return "\uE60B" +} + +func (n *Npm) Description(src *model.HydratedSource) string { + return n.Cmd +} + +func (n *Npm) Target() model.Target { + return n +} + +func (n *Npm) Create(s *model.Source) *exec.Cmd { + return exec.Command(Js.Npm, "run", n.Name) +} + +func (n *Npm) Label() string { + return n.Name +} + +func (n *Npm) Hydrate(src *model.Source) (model.HydratedTarget, error) { + return n, nil +} + +func (n *Npm) File(src *model.Source) string { + return filepath.Join(src.Path, "package.json") +} diff --git a/runner/js/target_script.go b/runner/js/target_script.go new file mode 100644 index 0000000..6ad213d --- /dev/null +++ b/runner/js/target_script.go @@ -0,0 +1,55 @@ +package js + +import ( + "github.com/ewy1/pik/describe" + "github.com/ewy1/pik/model" + "github.com/ewy1/pik/runner" + "github.com/ewy1/pik/spool" + "os/exec" + "path/filepath" +) + +type Script struct { + runner.BaseTarget + Typed bool +} + +func (t *Script) Icon() string { + if t.Typed { + return "\uE628" + } else { + return "\uE60C" + } +} + +func (t *Script) Description(src *model.HydratedSource) string { + d, err := describe.Describe(t, t.File(src.Source)) + if err != nil { + _, _ = spool.Warn("%v\n", err) + } + return d +} + +func (t *Script) Target() model.Target { + return t +} + +func (t *Script) Create(s *model.Source) *exec.Cmd { + if t.Typed { + return exec.Command(Js.TsInterpreter, t.File(s)) + } else { + return exec.Command(Js.JsInterpreter, t.File(s)) + } +} + +func (t *Script) Label() string { + return t.Identity.Full +} + +func (t *Script) Hydrate(src *model.Source) (model.HydratedTarget, error) { + return t, nil +} + +func (t *Script) File(src *model.Source) string { + return filepath.Join(src.Path, "package.json") +} diff --git a/runner/python/runner.go b/runner/python/runner.go index 6aa6017..8d03f52 100644 --- a/runner/python/runner.go +++ b/runner/python/runner.go @@ -30,11 +30,6 @@ func (p python) Init() error { return err } -func (p python) Hydrate(target model.Target) (model.HydratedTarget, error) { - //TODO implement me - panic("implement me") -} - func (p python) Wants(fs fs.FS, file string, entry fs.DirEntry) (bool, error) { return !entry.IsDir() && filepath.Ext(entry.Name()) == ".py", nil } diff --git a/runner/shell/hydrated.go b/runner/shell/hydrated.go index fec74f1..440d9cd 100644 --- a/runner/shell/hydrated.go +++ b/runner/shell/hydrated.go @@ -1,7 +1,6 @@ package shell import ( - "errors" "github.com/ewy1/pik/describe" "github.com/ewy1/pik/model" "github.com/ewy1/pik/runner" @@ -19,19 +18,8 @@ func (h *Hydrated) Icon() string { func (h *Hydrated) Description(src *model.HydratedSource) string { desc, err := describe.Describe(h.Target(), h.Target().File(src.Source)) if err != nil { - spool.Warn("%v\n", err) + _, _ = spool.Warn("%v\n", err) return "" } return desc } - -var WrongTargetError = errors.New("wrong target type") - -func (s *shell) Hydrate(target model.Target) (model.HydratedTarget, error) { - cast, ok := target.(*Target) - if !ok { - return nil, WrongTargetError - } - hyd := &Hydrated{BaseHydration: runner.Hydrated(cast)} - return hyd, nil -} diff --git a/runner/shell/target.go b/runner/shell/target.go index 49f7a18..d1262af 100644 --- a/runner/shell/target.go +++ b/runner/shell/target.go @@ -21,7 +21,9 @@ func (s *Target) String() string { } func (s *Target) Hydrate(_ *model.Source) (model.HydratedTarget, error) { - return Runner.Hydrate(s) + return &Hydrated{ + BaseHydration: runner.Hydrated(s), + }, nil } func (s *Target) Sub() []string { |
