mirror of https://github.com/Hilbis/Hilbish
Compare commits
No commits in common. "79a24cc2b4fcd6e63a1a755f73e3ab95da8f0967" and "37d8b944e9b3993d91567c3e2ce11b762e781461" have entirely different histories.
79a24cc2b4
...
37d8b944e9
|
@ -2,14 +2,13 @@ name: Generate docs
|
||||||
|
|
||||||
on:
|
on:
|
||||||
push:
|
push:
|
||||||
branches:
|
branches: [master]
|
||||||
- master
|
|
||||||
|
|
||||||
jobs:
|
jobs:
|
||||||
gen:
|
gen:
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v3
|
- uses: actions/checkout@v2
|
||||||
- uses: actions/setup-go@v2
|
- uses: actions/setup-go@v2
|
||||||
- name: Run docgen
|
- name: Run docgen
|
||||||
run: go run cmd/docgen/docgen.go
|
run: go run cmd/docgen/docgen.go
|
||||||
|
|
|
@ -33,7 +33,6 @@ jobs:
|
||||||
- uses: actions/checkout@v3
|
- uses: actions/checkout@v3
|
||||||
with:
|
with:
|
||||||
submodules: true
|
submodules: true
|
||||||
fetch-depth: 0
|
|
||||||
- name: Download Task
|
- name: Download Task
|
||||||
run: 'sh -c "$(curl --location https://taskfile.dev/install.sh)" -- -d'
|
run: 'sh -c "$(curl --location https://taskfile.dev/install.sh)" -- -d'
|
||||||
- uses: wangyoucao577/go-release-action@v1.25
|
- uses: wangyoucao577/go-release-action@v1.25
|
||||||
|
|
|
@ -1,31 +0,0 @@
|
||||||
name: Build website
|
|
||||||
|
|
||||||
on:
|
|
||||||
push:
|
|
||||||
branches:
|
|
||||||
- master
|
|
||||||
- docs-refactor
|
|
||||||
|
|
||||||
jobs:
|
|
||||||
deploy:
|
|
||||||
runs-on: ubuntu-latest
|
|
||||||
steps:
|
|
||||||
- uses: actions/checkout@v3
|
|
||||||
with:
|
|
||||||
submodules: true
|
|
||||||
fetch-depth: 0
|
|
||||||
|
|
||||||
- name: Setup Hugo
|
|
||||||
uses: peaceiris/actions-hugo@v2
|
|
||||||
with:
|
|
||||||
hugo-version: 'latest'
|
|
||||||
extended: true
|
|
||||||
|
|
||||||
- name: Build
|
|
||||||
run: 'cd website && hugo --minify'
|
|
||||||
|
|
||||||
- name: Deploy
|
|
||||||
uses: peaceiris/actions-gh-pages@v3
|
|
||||||
with:
|
|
||||||
github_token: ${{ secrets.GITHUB_TOKEN }}
|
|
||||||
publish_dir: ./website/public
|
|
|
@ -1,8 +1,6 @@
|
||||||
*.exe
|
*.exe
|
||||||
hilbish
|
hilbish
|
||||||
!docs/api/hilbish
|
|
||||||
docgen
|
docgen
|
||||||
!cmd/docgen
|
|
||||||
|
|
||||||
.vim
|
.vim
|
||||||
petals/
|
petals/
|
||||||
|
|
16
CHANGELOG.md
16
CHANGELOG.md
|
@ -1,16 +1,9 @@
|
||||||
# 🎀 Changelog
|
# 🎀 Changelog
|
||||||
|
|
||||||
## Unreleased
|
## Unreleased
|
||||||
**NOTES FOR USERS/PACKAGERS UPDATING:**
|
**NOTE:** Hilbish now uses [Task] insead of Make for builds.
|
||||||
- Hilbish now uses [Task] insead of Make for builds.
|
Windows support is also now at a lower tier; The only thing guaranteed is
|
||||||
- The doc format has been changed from plain text to markdown.
|
Hilbish *compiling* on Windows.
|
||||||
**YOU MUST reinstall Hilbish to remove the duplicate, old docs.**
|
|
||||||
- Hilbish will by default install to **`/usr/local`** instead of just `/usr/`
|
|
||||||
when building via Task. This is mainly to avoid conflict of distro packages
|
|
||||||
and local installs, and is the correct place when building from git either way.
|
|
||||||
To keep Hilbish in `/usr`, you must have `PREFIX="/usr/"` when running `task build` or `task install`
|
|
||||||
- Windows is no longer supported. It will build and run, but **will** have problems.
|
|
||||||
If you want to help fix the situation, start a discussion or open an issue and contribute.
|
|
||||||
|
|
||||||
[Task]: https://taskfile.dev/#/
|
[Task]: https://taskfile.dev/#/
|
||||||
|
|
||||||
|
@ -110,7 +103,6 @@ of a dot. (ie. `job.stop()` -> `job:stop()`)
|
||||||
- All `fs` module functions which take paths now implicitly expand ~ to home.
|
- All `fs` module functions which take paths now implicitly expand ~ to home.
|
||||||
- **Breaking Change:** `hilbish.greeting` has been moved to an opt (`hilbish.opts.greeting`) and is
|
- **Breaking Change:** `hilbish.greeting` has been moved to an opt (`hilbish.opts.greeting`) and is
|
||||||
always printed by default. To disable it, set the opt to false.
|
always printed by default. To disable it, set the opt to false.
|
||||||
- **Breaking Change:** `command.no-perm` hook has been replaced with `command.not-executable`
|
|
||||||
- History is now fetched from Lua, which means users can override `hilbish.history`
|
- History is now fetched from Lua, which means users can override `hilbish.history`
|
||||||
methods to make it act how they want.
|
methods to make it act how they want.
|
||||||
- `guide` has been removed. See the [website](https://rosettea.github.io/Hilbish/)
|
- `guide` has been removed. See the [website](https://rosettea.github.io/Hilbish/)
|
||||||
|
@ -169,8 +161,6 @@ will result in the files being completed.
|
||||||
- Cut off item names in grid menu if its longer than cell width
|
- Cut off item names in grid menu if its longer than cell width
|
||||||
- Fix completion search menu disappearing
|
- Fix completion search menu disappearing
|
||||||
- Completion paths having duplicated characters if it's escaped
|
- Completion paths having duplicated characters if it's escaped
|
||||||
- Get custom completion command properly to call from Lua
|
|
||||||
- Put proper command on the line when using up and down arrow keys to go through command history
|
|
||||||
|
|
||||||
## [2.0.0-rc1] - 2022-09-14
|
## [2.0.0-rc1] - 2022-09-14
|
||||||
This is a pre-release version of Hilbish for testing. To see the changelog,
|
This is a pre-release version of Hilbish for testing. To see the changelog,
|
||||||
|
|
|
@ -69,7 +69,7 @@ If you're new to nix you should probably read up on how to do that [here](https:
|
||||||
## Manual Build
|
## Manual Build
|
||||||
### Prerequisites
|
### Prerequisites
|
||||||
- [Go 1.17+](https://go.dev)
|
- [Go 1.17+](https://go.dev)
|
||||||
- [Task](https://taskfile.dev/installation/) (**Go on the hyperlink here to see Task's install method for your OS.**)
|
- [Task](https://taskfile.dev/#/)
|
||||||
|
|
||||||
### Build
|
### Build
|
||||||
First, clone Hilbish. The recursive is required, as some Lua libraries
|
First, clone Hilbish. The recursive is required, as some Lua libraries
|
||||||
|
|
|
@ -3,12 +3,12 @@
|
||||||
version: '3'
|
version: '3'
|
||||||
|
|
||||||
vars:
|
vars:
|
||||||
PREFIX: '{{default "/usr/local" .PREFIX}}'
|
PREFIX: '{{default "/usr" .PREFIX}}'
|
||||||
bindir__: '{{.PREFIX}}/bin'
|
bindir__: '{{.PREFIX}}/bin'
|
||||||
BINDIR: '{{default .bindir__ .BINDIR}}'
|
BINDIR: '{{default .bindir__ .BINDIR}}'
|
||||||
libdir__: '{{.PREFIX}}/share/hilbish'
|
libdir__: '{{.PREFIX}}/share/hilbish'
|
||||||
LIBDIR: '{{default .libdir__ .LIBDIR}}'
|
LIBDIR: '{{default .libdir__ .LIBDIR}}'
|
||||||
goflags__: '-ldflags "-s -w -X main.dataDir={{.LIBDIR}}"'
|
goflags__: '-ldflags "-s -w"'
|
||||||
GOFLAGS: '{{default .goflags__ .GOFLAGS}}'
|
GOFLAGS: '{{default .goflags__ .GOFLAGS}}'
|
||||||
|
|
||||||
tasks:
|
tasks:
|
||||||
|
@ -16,7 +16,7 @@ tasks:
|
||||||
cmds:
|
cmds:
|
||||||
- CGO_ENABLED=0 go build {{.GOFLAGS}}
|
- CGO_ENABLED=0 go build {{.GOFLAGS}}
|
||||||
vars:
|
vars:
|
||||||
GOFLAGS: '-ldflags "-s -w -X main.dataDir={{.LIBDIR}} -X main.gitCommit=$(git rev-parse --short HEAD) -X main.gitBranch=$(git rev-parse --abbrev-ref HEAD)"'
|
GOFLAGS: '-ldflags "-s -w -X main.gitCommit=$(git rev-parse --short HEAD) -X main.gitBranch=$(git rev-parse --abbrev-ref HEAD)"'
|
||||||
|
|
||||||
build:
|
build:
|
||||||
cmds:
|
cmds:
|
||||||
|
|
45
aliases.go
45
aliases.go
|
@ -9,40 +9,40 @@ import (
|
||||||
rt "github.com/arnodel/golua/runtime"
|
rt "github.com/arnodel/golua/runtime"
|
||||||
)
|
)
|
||||||
|
|
||||||
var aliases *aliasModule
|
var aliases *aliasHandler
|
||||||
|
|
||||||
type aliasModule struct {
|
type aliasHandler struct {
|
||||||
aliases map[string]string
|
aliases map[string]string
|
||||||
mu *sync.RWMutex
|
mu *sync.RWMutex
|
||||||
}
|
}
|
||||||
|
|
||||||
// initialize aliases map
|
// initialize aliases map
|
||||||
func newAliases() *aliasModule {
|
func newAliases() *aliasHandler {
|
||||||
return &aliasModule{
|
return &aliasHandler{
|
||||||
aliases: make(map[string]string),
|
aliases: make(map[string]string),
|
||||||
mu: &sync.RWMutex{},
|
mu: &sync.RWMutex{},
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a *aliasModule) Add(alias, cmd string) {
|
func (a *aliasHandler) Add(alias, cmd string) {
|
||||||
a.mu.Lock()
|
a.mu.Lock()
|
||||||
defer a.mu.Unlock()
|
defer a.mu.Unlock()
|
||||||
|
|
||||||
a.aliases[alias] = cmd
|
a.aliases[alias] = cmd
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a *aliasModule) All() map[string]string {
|
func (a *aliasHandler) All() map[string]string {
|
||||||
return a.aliases
|
return a.aliases
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a *aliasModule) Delete(alias string) {
|
func (a *aliasHandler) Delete(alias string) {
|
||||||
a.mu.Lock()
|
a.mu.Lock()
|
||||||
defer a.mu.Unlock()
|
defer a.mu.Unlock()
|
||||||
|
|
||||||
delete(a.aliases, alias)
|
delete(a.aliases, alias)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a *aliasModule) Resolve(cmdstr string) string {
|
func (a *aliasHandler) Resolve(cmdstr string) string {
|
||||||
a.mu.RLock()
|
a.mu.RLock()
|
||||||
defer a.mu.RUnlock()
|
defer a.mu.RUnlock()
|
||||||
|
|
||||||
|
@ -66,10 +66,7 @@ func (a *aliasModule) Resolve(cmdstr string) string {
|
||||||
|
|
||||||
// lua section
|
// lua section
|
||||||
|
|
||||||
// #interface aliases
|
func (a *aliasHandler) Loader(rtm *rt.Runtime) *rt.Table {
|
||||||
// command aliasing
|
|
||||||
// The alias interface deals with all command aliases in Hilbish.
|
|
||||||
func (a *aliasModule) Loader(rtm *rt.Runtime) *rt.Table {
|
|
||||||
// create a lua module with our functions
|
// create a lua module with our functions
|
||||||
hshaliasesLua := map[string]util.LuaExport{
|
hshaliasesLua := map[string]util.LuaExport{
|
||||||
"add": util.LuaExport{hlalias, 2, false},
|
"add": util.LuaExport{hlalias, 2, false},
|
||||||
|
@ -84,17 +81,7 @@ func (a *aliasModule) Loader(rtm *rt.Runtime) *rt.Table {
|
||||||
return mod
|
return mod
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface aliases
|
func (a *aliasHandler) luaList(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
// add(alias, cmd)
|
|
||||||
// This is an alias (ha) for the `hilbish.alias` function.
|
|
||||||
// --- @param alias string
|
|
||||||
// --- @param cmd string
|
|
||||||
func _hlalias() {}
|
|
||||||
|
|
||||||
// #interface aliases
|
|
||||||
// list()
|
|
||||||
// Get a table of all aliases.
|
|
||||||
func (a *aliasModule) luaList(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
|
||||||
aliasesList := rt.NewTable()
|
aliasesList := rt.NewTable()
|
||||||
for k, v := range a.All() {
|
for k, v := range a.All() {
|
||||||
aliasesList.Set(rt.StringValue(k), rt.StringValue(v))
|
aliasesList.Set(rt.StringValue(k), rt.StringValue(v))
|
||||||
|
@ -103,11 +90,7 @@ func (a *aliasModule) luaList(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.PushingNext1(t.Runtime, rt.TableValue(aliasesList)), nil
|
return c.PushingNext1(t.Runtime, rt.TableValue(aliasesList)), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface aliases
|
func (a *aliasHandler) luaDelete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
// delete(name)
|
|
||||||
// Removes an alias.
|
|
||||||
// --- @param name string
|
|
||||||
func (a *aliasModule) luaDelete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
@ -120,11 +103,7 @@ func (a *aliasModule) luaDelete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.Next(), nil
|
return c.Next(), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface aliases
|
func (a *aliasHandler) luaResolve(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
// resolve(alias)
|
|
||||||
// Tries to resolve an alias to its command.
|
|
||||||
// --- @param alias string
|
|
||||||
func (a *aliasModule) luaResolve(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
44
api.go
44
api.go
|
@ -1,14 +1,6 @@
|
||||||
// the core Hilbish API
|
// Here is the core api for the hilbi shell itself
|
||||||
// The Hilbish module includes the core API, containing
|
// Basically, stuff about the shell itself and other functions
|
||||||
// interfaces and functions which directly relate to shell functionality.
|
// go here.
|
||||||
// #field ver The version of Hilbish
|
|
||||||
// #field user Username of the user
|
|
||||||
// #field host Hostname of the machine
|
|
||||||
// #field dataDir Directory for Hilbish data files, including the docs and default modules
|
|
||||||
// #field interactive Is Hilbish in an interactive shell?
|
|
||||||
// #field login Is Hilbish the login shell?
|
|
||||||
// #field vimMode Current Vim input mode of Hilbish (will be nil if not in Vim input mode)
|
|
||||||
// #field exitCode xit code of the last executed command
|
|
||||||
package main
|
package main
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
@ -27,6 +19,7 @@ import (
|
||||||
rt "github.com/arnodel/golua/runtime"
|
rt "github.com/arnodel/golua/runtime"
|
||||||
"github.com/arnodel/golua/lib/packagelib"
|
"github.com/arnodel/golua/lib/packagelib"
|
||||||
"github.com/maxlandon/readline"
|
"github.com/maxlandon/readline"
|
||||||
|
"github.com/blackfireio/osinfo"
|
||||||
"mvdan.cc/sh/v3/interp"
|
"mvdan.cc/sh/v3/interp"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -121,12 +114,20 @@ func hilbishLoad(rtm *rt.Runtime) (rt.Value, func()) {
|
||||||
util.Document(fakeMod, "Hilbish's core API, containing submodules and functions which relate to the shell itself.")
|
util.Document(fakeMod, "Hilbish's core API, containing submodules and functions which relate to the shell itself.")
|
||||||
|
|
||||||
// hilbish.userDir table
|
// hilbish.userDir table
|
||||||
hshuser := userDirLoader(rtm)
|
hshuser := rt.NewTable()
|
||||||
|
|
||||||
|
util.SetField(rtm, hshuser, "config", rt.StringValue(confDir), "User's config directory")
|
||||||
|
util.SetField(rtm, hshuser, "data", rt.StringValue(userDataDir), "XDG data directory")
|
||||||
util.Document(hshuser, "User directories to store configs and/or modules.")
|
util.Document(hshuser, "User directories to store configs and/or modules.")
|
||||||
mod.Set(rt.StringValue("userDir"), rt.TableValue(hshuser))
|
mod.Set(rt.StringValue("userDir"), rt.TableValue(hshuser))
|
||||||
|
|
||||||
// hilbish.os table
|
// hilbish.os table
|
||||||
hshos := hshosLoader(rtm)
|
hshos := rt.NewTable()
|
||||||
|
info, _ := osinfo.GetOSInfo()
|
||||||
|
|
||||||
|
util.SetField(rtm, hshos, "family", rt.StringValue(info.Family), "Family name of the current OS")
|
||||||
|
util.SetField(rtm, hshos, "name", rt.StringValue(info.Name), "Pretty name of the current OS")
|
||||||
|
util.SetField(rtm, hshos, "version", rt.StringValue(info.Version), "Version of the current OS")
|
||||||
util.Document(hshos, "OS info interface")
|
util.Document(hshos, "OS info interface")
|
||||||
mod.Set(rt.StringValue("os"), rt.TableValue(hshos))
|
mod.Set(rt.StringValue("os"), rt.TableValue(hshos))
|
||||||
|
|
||||||
|
@ -158,10 +159,10 @@ func hilbishLoad(rtm *rt.Runtime) (rt.Value, func()) {
|
||||||
mod.Set(rt.StringValue("jobs"), rt.TableValue(jobModule))
|
mod.Set(rt.StringValue("jobs"), rt.TableValue(jobModule))
|
||||||
|
|
||||||
// hilbish.timers table
|
// hilbish.timers table
|
||||||
timers = newTimersModule()
|
timers = newTimerHandler()
|
||||||
timersModule := timers.loader(rtm)
|
timerModule := timers.loader(rtm)
|
||||||
util.Document(timersModule, "Timer interface, for control of all intervals and timeouts.")
|
util.Document(timerModule, "Timer interface, for control of all intervals and timeouts.")
|
||||||
mod.Set(rt.StringValue("timers"), rt.TableValue(timersModule))
|
mod.Set(rt.StringValue("timers"), rt.TableValue(timerModule))
|
||||||
|
|
||||||
editorModule := editorLoader(rtm)
|
editorModule := editorLoader(rtm)
|
||||||
util.Document(editorModule, "")
|
util.Document(editorModule, "")
|
||||||
|
@ -249,12 +250,11 @@ func hlcwd(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// read(prompt) -> input
|
// read(prompt?) -> input?
|
||||||
// Read input from the user, using Hilbish's line editor/input reader.
|
// Read input from the user, using Hilbish's line editor/input reader.
|
||||||
// This is a separate instance from the one Hilbish actually uses.
|
// This is a separate instance from the one Hilbish actually uses.
|
||||||
// Returns `input`, will be nil if ctrl + d is pressed, or an error occurs (which shouldn't happen)
|
// Returns `input`, will be nil if ctrl + d is pressed, or an error occurs (which shouldn't happen)
|
||||||
// --- @param prompt string|nil
|
// --- @param prompt string
|
||||||
// --- @returns string|nil
|
|
||||||
func hlread(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func hlread(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
luaprompt := c.Arg(0)
|
luaprompt := c.Arg(0)
|
||||||
if typ := luaprompt.Type(); typ != rt.StringType && typ != rt.NilType {
|
if typ := luaprompt.Type(); typ != rt.StringType && typ != rt.NilType {
|
||||||
|
@ -281,7 +281,7 @@ func hlread(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
prompt(str, typ)
|
prompt(str, typ?)
|
||||||
Changes the shell prompt to `str`
|
Changes the shell prompt to `str`
|
||||||
There are a few verbs that can be used in the prompt text.
|
There are a few verbs that can be used in the prompt text.
|
||||||
These will be formatted and replaced with the appropriate values.
|
These will be formatted and replaced with the appropriate values.
|
||||||
|
@ -289,7 +289,7 @@ These will be formatted and replaced with the appropriate values.
|
||||||
`%u` - Name of current user
|
`%u` - Name of current user
|
||||||
`%h` - Hostname of device
|
`%h` - Hostname of device
|
||||||
--- @param str string
|
--- @param str string
|
||||||
--- @param typ string|nil Type of prompt, being left or right. Left by default.
|
--- @param typ string Type of prompt, being left or right. Left by default.
|
||||||
*/
|
*/
|
||||||
func hlprompt(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func hlprompt(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
err := c.Check1Arg()
|
err := c.Check1Arg()
|
||||||
|
|
|
@ -9,192 +9,27 @@ import (
|
||||||
"go/token"
|
"go/token"
|
||||||
"strings"
|
"strings"
|
||||||
"os"
|
"os"
|
||||||
"sync"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
var header = `---
|
type EmmyPiece struct {
|
||||||
title: %s %s
|
|
||||||
description: %s
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
`
|
|
||||||
|
|
||||||
type emmyPiece struct {
|
|
||||||
DocPiece *docPiece
|
|
||||||
Annotations []string
|
|
||||||
Params []string // we only need to know param name to put in function
|
|
||||||
FuncName string
|
FuncName string
|
||||||
|
Docs []string
|
||||||
|
Params []string // we only need to know param name to put in function
|
||||||
}
|
}
|
||||||
|
type DocPiece struct {
|
||||||
type module struct {
|
|
||||||
Docs []docPiece
|
|
||||||
Fields []docPiece
|
|
||||||
Properties []docPiece
|
|
||||||
ShortDescription string
|
|
||||||
Description string
|
|
||||||
ParentModule string
|
|
||||||
HasInterfaces bool
|
|
||||||
}
|
|
||||||
|
|
||||||
type docPiece struct {
|
|
||||||
Doc []string
|
Doc []string
|
||||||
FuncSig string
|
FuncSig string
|
||||||
FuncName string
|
FuncName string
|
||||||
Interfacing string
|
|
||||||
ParentModule string
|
|
||||||
GoFuncName string
|
|
||||||
IsInterface bool
|
|
||||||
IsMember bool
|
|
||||||
Fields []docPiece
|
|
||||||
Properties []docPiece
|
|
||||||
}
|
|
||||||
|
|
||||||
type tag struct {
|
|
||||||
id string
|
|
||||||
fields []string
|
|
||||||
}
|
|
||||||
|
|
||||||
var docs = make(map[string]module)
|
|
||||||
var interfaceDocs = make(map[string]module)
|
|
||||||
var emmyDocs = make(map[string][]emmyPiece)
|
|
||||||
var prefix = map[string]string{
|
|
||||||
"main": "hl",
|
|
||||||
"hilbish": "hl",
|
|
||||||
"fs": "f",
|
|
||||||
"commander": "c",
|
|
||||||
"bait": "b",
|
|
||||||
"terminal": "term",
|
|
||||||
}
|
|
||||||
|
|
||||||
func getTagsAndDocs(docs string) (map[string][]tag, []string) {
|
|
||||||
pts := strings.Split(docs, "\n")
|
|
||||||
parts := []string{}
|
|
||||||
tags := make(map[string][]tag)
|
|
||||||
|
|
||||||
for _, part := range pts {
|
|
||||||
if strings.HasPrefix(part, "#") {
|
|
||||||
tagParts := strings.Split(strings.TrimPrefix(part, "#"), " ")
|
|
||||||
if tags[tagParts[0]] == nil {
|
|
||||||
var id string
|
|
||||||
if len(tagParts) > 1 {
|
|
||||||
id = tagParts[1]
|
|
||||||
}
|
|
||||||
tags[tagParts[0]] = []tag{
|
|
||||||
{id: id},
|
|
||||||
}
|
|
||||||
if len(tagParts) >= 2 {
|
|
||||||
tags[tagParts[0]][0].fields = tagParts[2:]
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
fleds := []string{}
|
|
||||||
if len(tagParts) >= 2 {
|
|
||||||
fleds = tagParts[2:]
|
|
||||||
}
|
|
||||||
tags[tagParts[0]] = append(tags[tagParts[0]], tag{
|
|
||||||
id: tagParts[1],
|
|
||||||
fields: fleds,
|
|
||||||
})
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
parts = append(parts, part)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return tags, parts
|
|
||||||
}
|
|
||||||
|
|
||||||
func docPieceTag(tagName string, tags map[string][]tag) []docPiece {
|
|
||||||
dps := []docPiece{}
|
|
||||||
for _, tag := range tags[tagName] {
|
|
||||||
dps = append(dps, docPiece{
|
|
||||||
FuncName: tag.id,
|
|
||||||
Doc: tag.fields,
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
return dps
|
|
||||||
}
|
|
||||||
|
|
||||||
func setupDoc(mod string, fun *doc.Func) *docPiece {
|
|
||||||
docs := strings.TrimSpace(fun.Doc)
|
|
||||||
inInterface := strings.HasPrefix(docs, "#interface")
|
|
||||||
if (!strings.HasPrefix(fun.Name, prefix[mod]) && !inInterface) || (strings.ToLower(fun.Name) == "loader" && !inInterface) {
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
tags, parts := getTagsAndDocs(docs)
|
|
||||||
|
|
||||||
var interfaces string
|
|
||||||
funcsig := parts[0]
|
|
||||||
doc := parts[1:]
|
|
||||||
funcName := strings.TrimPrefix(fun.Name, prefix[mod])
|
|
||||||
funcdoc := []string{}
|
|
||||||
|
|
||||||
if inInterface {
|
|
||||||
interfaces = tags["interface"][0].id
|
|
||||||
funcName = interfaces + "." + strings.Split(funcsig, "(")[0]
|
|
||||||
}
|
|
||||||
em := emmyPiece{FuncName: funcName}
|
|
||||||
|
|
||||||
fields := docPieceTag("field", tags)
|
|
||||||
properties := docPieceTag("property", tags)
|
|
||||||
|
|
||||||
for _, d := range doc {
|
|
||||||
if strings.HasPrefix(d, "---") {
|
|
||||||
emmyLine := strings.TrimSpace(strings.TrimPrefix(d, "---"))
|
|
||||||
emmyLinePieces := strings.Split(emmyLine, " ")
|
|
||||||
emmyType := emmyLinePieces[0]
|
|
||||||
if emmyType == "@param" {
|
|
||||||
em.Params = append(em.Params, emmyLinePieces[1])
|
|
||||||
}
|
|
||||||
if emmyType == "@vararg" {
|
|
||||||
em.Params = append(em.Params, "...") // add vararg
|
|
||||||
}
|
|
||||||
em.Annotations = append(em.Annotations, d)
|
|
||||||
} else {
|
|
||||||
funcdoc = append(funcdoc, d)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
var isMember bool
|
|
||||||
if tags["member"] != nil {
|
|
||||||
isMember = true
|
|
||||||
}
|
|
||||||
var parentMod string
|
|
||||||
if inInterface {
|
|
||||||
parentMod = mod
|
|
||||||
}
|
|
||||||
dps := &docPiece{
|
|
||||||
Doc: funcdoc,
|
|
||||||
FuncSig: funcsig,
|
|
||||||
FuncName: funcName,
|
|
||||||
Interfacing: interfaces,
|
|
||||||
GoFuncName: strings.ToLower(fun.Name),
|
|
||||||
IsInterface: inInterface,
|
|
||||||
IsMember: isMember,
|
|
||||||
ParentModule: parentMod,
|
|
||||||
Fields: fields,
|
|
||||||
Properties: properties,
|
|
||||||
}
|
|
||||||
if strings.HasSuffix(dps.GoFuncName, strings.ToLower("loader")) {
|
|
||||||
dps.Doc = parts
|
|
||||||
}
|
|
||||||
em.DocPiece = dps
|
|
||||||
|
|
||||||
emmyDocs[mod] = append(emmyDocs[mod], em)
|
|
||||||
return dps
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// feel free to clean this up
|
||||||
|
// it works, dont really care about the code
|
||||||
func main() {
|
func main() {
|
||||||
fset := token.NewFileSet()
|
fset := token.NewFileSet()
|
||||||
os.Mkdir("docs", 0777)
|
os.Mkdir("docs", 0777)
|
||||||
os.Mkdir("docs/api", 0777)
|
|
||||||
os.Mkdir("emmyLuaDocs", 0777)
|
os.Mkdir("emmyLuaDocs", 0777)
|
||||||
|
|
||||||
|
|
||||||
dirs := []string{"./"}
|
dirs := []string{"./"}
|
||||||
filepath.Walk("golibs/", func (path string, info os.FileInfo, err error) error {
|
filepath.Walk("golibs/", func (path string, info os.FileInfo, err error) error {
|
||||||
if !info.IsDir() {
|
if !info.IsDir() {
|
||||||
|
@ -216,172 +51,120 @@ func main() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
interfaceModules := make(map[string]*module)
|
prefix := map[string]string{
|
||||||
|
"hilbish": "hl",
|
||||||
|
"fs": "f",
|
||||||
|
"commander": "c",
|
||||||
|
"bait": "b",
|
||||||
|
"terminal": "term",
|
||||||
|
}
|
||||||
|
docs := make(map[string][]DocPiece)
|
||||||
|
emmyDocs := make(map[string][]EmmyPiece)
|
||||||
|
|
||||||
for l, f := range pkgs {
|
for l, f := range pkgs {
|
||||||
p := doc.New(f, "./", doc.AllDecls)
|
p := doc.New(f, "./", doc.AllDecls)
|
||||||
pieces := []docPiece{}
|
|
||||||
mod := l
|
|
||||||
if mod == "main" {
|
|
||||||
mod = "hilbish"
|
|
||||||
}
|
|
||||||
var hasInterfaces bool
|
|
||||||
for _, t := range p.Funcs {
|
for _, t := range p.Funcs {
|
||||||
piece := setupDoc(mod, t)
|
mod := l
|
||||||
if piece == nil {
|
if strings.HasPrefix(t.Name, "hl") { mod = "hilbish" }
|
||||||
continue
|
if !strings.HasPrefix(t.Name, prefix[mod]) || t.Name == "Loader" { continue }
|
||||||
|
parts := strings.Split(strings.TrimSpace(t.Doc), "\n")
|
||||||
|
funcsig := parts[0]
|
||||||
|
doc := parts[1:]
|
||||||
|
funcdoc := []string{}
|
||||||
|
em := EmmyPiece{FuncName: strings.TrimPrefix(t.Name, prefix[mod])}
|
||||||
|
for _, d := range doc {
|
||||||
|
if strings.HasPrefix(d, "---") {
|
||||||
|
emmyLine := strings.TrimSpace(strings.TrimPrefix(d, "---"))
|
||||||
|
emmyLinePieces := strings.Split(emmyLine, " ")
|
||||||
|
emmyType := emmyLinePieces[0]
|
||||||
|
if emmyType == "@param" {
|
||||||
|
em.Params = append(em.Params, emmyLinePieces[1])
|
||||||
|
}
|
||||||
|
if emmyType == "@vararg" {
|
||||||
|
em.Params = append(em.Params, "...") // add vararg
|
||||||
|
}
|
||||||
|
em.Docs = append(em.Docs, d)
|
||||||
|
} else {
|
||||||
|
funcdoc = append(funcdoc, d)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pieces = append(pieces, *piece)
|
dps := DocPiece{
|
||||||
if piece.IsInterface {
|
Doc: funcdoc,
|
||||||
hasInterfaces = true
|
FuncSig: funcsig,
|
||||||
|
FuncName: strings.TrimPrefix(t.Name, prefix[mod]),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
docs[mod] = append(docs[mod], dps)
|
||||||
|
emmyDocs[mod] = append(emmyDocs[mod], em)
|
||||||
}
|
}
|
||||||
for _, t := range p.Types {
|
for _, t := range p.Types {
|
||||||
for _, m := range t.Methods {
|
for _, m := range t.Methods {
|
||||||
piece := setupDoc(mod, m)
|
if !strings.HasPrefix(m.Name, prefix[l]) || m.Name == "Loader" { continue }
|
||||||
if piece == nil {
|
parts := strings.Split(strings.TrimSpace(m.Doc), "\n")
|
||||||
continue
|
funcsig := parts[0]
|
||||||
}
|
doc := parts[1:]
|
||||||
|
funcdoc := []string{}
|
||||||
pieces = append(pieces, *piece)
|
em := EmmyPiece{FuncName: strings.TrimPrefix(m.Name, prefix[l])}
|
||||||
if piece.IsInterface {
|
for _, d := range doc {
|
||||||
hasInterfaces = true
|
if strings.HasPrefix(d, "---") {
|
||||||
}
|
emmyLine := strings.TrimSpace(strings.TrimPrefix(d, "---"))
|
||||||
}
|
emmyLinePieces := strings.Split(emmyLine, " ")
|
||||||
}
|
emmyType := emmyLinePieces[0]
|
||||||
|
if emmyType == "@param" {
|
||||||
tags, descParts := getTagsAndDocs(strings.TrimSpace(p.Doc))
|
em.Params = append(em.Params, emmyLinePieces[1])
|
||||||
shortDesc := descParts[0]
|
}
|
||||||
desc := descParts[1:]
|
if emmyType == "@vararg" {
|
||||||
filteredPieces := []docPiece{}
|
em.Params = append(em.Params, "...") // add vararg
|
||||||
for _, piece := range pieces {
|
}
|
||||||
if !piece.IsInterface {
|
em.Docs = append(em.Docs, d)
|
||||||
filteredPieces = append(filteredPieces, piece)
|
} else {
|
||||||
continue
|
funcdoc = append(funcdoc, d)
|
||||||
}
|
|
||||||
|
|
||||||
modname := piece.ParentModule + "." + piece.Interfacing
|
|
||||||
if interfaceModules[modname] == nil {
|
|
||||||
interfaceModules[modname] = &module{
|
|
||||||
ParentModule: piece.ParentModule,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if strings.HasSuffix(piece.GoFuncName, strings.ToLower("loader")) {
|
|
||||||
shortDesc := piece.Doc[0]
|
|
||||||
desc := piece.Doc[1:]
|
|
||||||
interfaceModules[modname].ShortDescription = shortDesc
|
|
||||||
interfaceModules[modname].Description = strings.Join(desc, "\n")
|
|
||||||
interfaceModules[modname].Fields = piece.Fields
|
|
||||||
interfaceModules[modname].Properties = piece.Properties
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
interfaceModules[modname].Docs = append(interfaceModules[modname].Docs, piece)
|
|
||||||
}
|
|
||||||
|
|
||||||
docs[mod] = module{
|
|
||||||
Docs: filteredPieces,
|
|
||||||
ShortDescription: shortDesc,
|
|
||||||
Description: strings.Join(desc, "\n"),
|
|
||||||
HasInterfaces: hasInterfaces,
|
|
||||||
Properties: docPieceTag("property", tags),
|
|
||||||
Fields: docPieceTag("field", tags),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
for key, mod := range interfaceModules {
|
|
||||||
docs[key] = *mod
|
|
||||||
}
|
|
||||||
|
|
||||||
var wg sync.WaitGroup
|
|
||||||
wg.Add(len(docs) * 2)
|
|
||||||
|
|
||||||
for mod, v := range docs {
|
|
||||||
docPath := "docs/api/" + mod + ".md"
|
|
||||||
if v.HasInterfaces {
|
|
||||||
os.Mkdir("docs/api/" + mod, 0777)
|
|
||||||
os.Remove(docPath) // remove old doc path if it exists
|
|
||||||
docPath = "docs/api/" + mod + "/_index.md"
|
|
||||||
}
|
|
||||||
if v.ParentModule != "" {
|
|
||||||
docPath = "docs/api/" + v.ParentModule + "/" + mod + ".md"
|
|
||||||
}
|
|
||||||
|
|
||||||
go func(modname, docPath string, modu module) {
|
|
||||||
defer wg.Done()
|
|
||||||
modOrIface := "Module"
|
|
||||||
if modu.ParentModule != "" {
|
|
||||||
modOrIface = "Interface"
|
|
||||||
}
|
|
||||||
|
|
||||||
f, _ := os.Create(docPath)
|
|
||||||
f.WriteString(fmt.Sprintf(header, modOrIface, modname, modu.ShortDescription))
|
|
||||||
f.WriteString(fmt.Sprintf("## Introduction\n%s\n\n", modu.Description))
|
|
||||||
if len(modu.Fields) != 0 {
|
|
||||||
f.WriteString("## Interface fields\n")
|
|
||||||
for _, dps := range modu.Fields {
|
|
||||||
f.WriteString(fmt.Sprintf("- `%s`: ", dps.FuncName))
|
|
||||||
f.WriteString(strings.Join(dps.Doc, " "))
|
|
||||||
f.WriteString("\n")
|
|
||||||
}
|
|
||||||
f.WriteString("\n")
|
|
||||||
}
|
|
||||||
if len(modu.Properties) != 0 {
|
|
||||||
f.WriteString("## Object properties\n")
|
|
||||||
for _, dps := range modu.Properties {
|
|
||||||
f.WriteString(fmt.Sprintf("- `%s`: ", dps.FuncName))
|
|
||||||
f.WriteString(strings.Join(dps.Doc, " "))
|
|
||||||
f.WriteString("\n")
|
|
||||||
}
|
|
||||||
f.WriteString("\n")
|
|
||||||
}
|
|
||||||
if len(modu.Docs) != 0 {
|
|
||||||
f.WriteString("## Functions\n")
|
|
||||||
}
|
|
||||||
for _, dps := range modu.Docs {
|
|
||||||
f.WriteString(fmt.Sprintf("### %s\n", dps.FuncSig))
|
|
||||||
for _, doc := range dps.Doc {
|
|
||||||
if !strings.HasPrefix(doc, "---") {
|
|
||||||
f.WriteString(doc + "\n")
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
f.WriteString("\n")
|
dps := DocPiece{
|
||||||
|
Doc: funcdoc,
|
||||||
|
FuncSig: funcsig,
|
||||||
|
FuncName: strings.TrimPrefix(m.Name, prefix[l]),
|
||||||
|
}
|
||||||
|
|
||||||
|
docs[l] = append(docs[l], dps)
|
||||||
|
emmyDocs[l] = append(emmyDocs[l], em)
|
||||||
}
|
}
|
||||||
}(mod, docPath, v)
|
}
|
||||||
|
}
|
||||||
go func(md, modname string, modu module) {
|
|
||||||
defer wg.Done()
|
for mod, v := range docs {
|
||||||
|
if mod == "main" { continue }
|
||||||
if modu.ParentModule != "" {
|
f, _ := os.Create("docs/" + mod + ".txt")
|
||||||
return
|
for _, dps := range v {
|
||||||
}
|
f.WriteString(dps.FuncSig + " > ")
|
||||||
|
for _, doc := range dps.Doc {
|
||||||
ff, _ := os.Create("emmyLuaDocs/" + modname + ".lua")
|
if !strings.HasPrefix(doc, "---") {
|
||||||
ff.WriteString("--- @meta\n\nlocal " + modname + " = {}\n\n")
|
f.WriteString(doc + "\n")
|
||||||
for _, em := range emmyDocs[modname] {
|
}
|
||||||
if strings.HasSuffix(em.DocPiece.GoFuncName, strings.ToLower("loader")) {
|
}
|
||||||
continue
|
f.WriteString("\n")
|
||||||
}
|
}
|
||||||
|
}
|
||||||
dps := em.DocPiece
|
|
||||||
funcdocs := dps.Doc
|
for mod, v := range emmyDocs {
|
||||||
ff.WriteString("--- " + strings.Join(funcdocs, "\n--- ") + "\n")
|
if mod == "main" { continue }
|
||||||
if len(em.Annotations) != 0 {
|
f, _ := os.Create("emmyLuaDocs/" + mod + ".lua")
|
||||||
ff.WriteString(strings.Join(em.Annotations, "\n") + "\n")
|
f.WriteString("--- @meta\n\nlocal " + mod + " = {}\n\n")
|
||||||
}
|
for _, em := range v {
|
||||||
accessor := "."
|
var funcdocs []string
|
||||||
if dps.IsMember {
|
for _, dps := range docs[mod] {
|
||||||
accessor = ":"
|
if dps.FuncName == em.FuncName {
|
||||||
}
|
funcdocs = dps.Doc
|
||||||
signature := strings.Split(dps.FuncSig, " ->")[0]
|
}
|
||||||
var intrface string
|
}
|
||||||
if dps.IsInterface {
|
f.WriteString("--- " + strings.Join(funcdocs, "\n--- ") + "\n")
|
||||||
intrface = "." + dps.Interfacing
|
if len(em.Docs) != 0 {
|
||||||
}
|
f.WriteString(strings.Join(em.Docs, "\n") + "\n")
|
||||||
ff.WriteString("function " + modname + intrface + accessor + signature + " end\n\n")
|
}
|
||||||
}
|
f.WriteString("function " + mod + "." + em.FuncName + "(" + strings.Join(em.Params, ", ") + ") end\n\n")
|
||||||
ff.WriteString("return " + modname + "\n")
|
}
|
||||||
}(mod, mod, v)
|
f.WriteString("return " + mod + "\n")
|
||||||
}
|
}
|
||||||
wg.Wait()
|
|
||||||
}
|
}
|
||||||
|
|
19
complete.go
19
complete.go
|
@ -172,9 +172,6 @@ func escapeFilename(fname string) string {
|
||||||
return escapeReplaer.Replace(fname)
|
return escapeReplaer.Replace(fname)
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface completions
|
|
||||||
// tab completions
|
|
||||||
// The completions interface deals with tab completions.
|
|
||||||
func completionLoader(rtm *rt.Runtime) *rt.Table {
|
func completionLoader(rtm *rt.Runtime) *rt.Table {
|
||||||
exports := map[string]util.LuaExport{
|
exports := map[string]util.LuaExport{
|
||||||
"files": {luaFileComplete, 3, false},
|
"files": {luaFileComplete, 3, false},
|
||||||
|
@ -189,19 +186,11 @@ func completionLoader(rtm *rt.Runtime) *rt.Table {
|
||||||
return mod
|
return mod
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface completions
|
// left as a shim, might doc in the same way as hilbish functions
|
||||||
// handler(line, pos)
|
|
||||||
// The handler function is the callback for tab completion in Hilbish.
|
|
||||||
// You can check the completions doc for more info.
|
|
||||||
func completionHandler(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func completionHandler(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.Next(), nil
|
return c.Next(), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface completions
|
|
||||||
// call(name, query, ctx, fields)
|
|
||||||
// Calls a completer function. This is mainly used to call
|
|
||||||
// a command completer, which will have a `name` in the form
|
|
||||||
// of `command.name`, example: `command.git`
|
|
||||||
func callLuaCompleter(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func callLuaCompleter(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.CheckNArgs(4); err != nil {
|
if err := c.CheckNArgs(4); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -241,9 +230,6 @@ func callLuaCompleter(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.PushingNext1(t.Runtime, completerReturn), nil
|
return c.PushingNext1(t.Runtime, completerReturn), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface completions
|
|
||||||
// files(query, ctx, fields)
|
|
||||||
// Returns file completion candidates based on the provided query.
|
|
||||||
func luaFileComplete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func luaFileComplete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
query, ctx, fds, err := getCompleteParams(t, c)
|
query, ctx, fds, err := getCompleteParams(t, c)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -260,9 +246,6 @@ func luaFileComplete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.PushingNext(t.Runtime, rt.TableValue(luaComps), rt.StringValue(pfx)), nil
|
return c.PushingNext(t.Runtime, rt.TableValue(luaComps), rt.StringValue(pfx)), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface completions
|
|
||||||
// bins(query, ctx, fields)
|
|
||||||
// Returns binary/executale completion candidates based on the provided query.
|
|
||||||
func luaBinaryComplete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func luaBinaryComplete(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
query, ctx, fds, err := getCompleteParams(t, c)
|
query, ctx, fds, err := getCompleteParams(t, c)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
|
@ -1,7 +0,0 @@
|
||||||
---
|
|
||||||
title: API
|
|
||||||
layout: doc
|
|
||||||
weight: -50
|
|
||||||
menu: docs
|
|
||||||
---
|
|
||||||
|
|
|
@ -1,34 +0,0 @@
|
||||||
---
|
|
||||||
title: Module bait
|
|
||||||
description: the event emitter
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
Bait is the event emitter for Hilbish. Why name it bait? Why not.
|
|
||||||
It throws hooks that you can catch. This is what you will use if
|
|
||||||
you want to listen in on hooks to know when certain things have
|
|
||||||
happened, like when you've changed directory, a command has failed,
|
|
||||||
etc. To find all available hooks thrown by Hilbish, see doc hooks.
|
|
||||||
|
|
||||||
## Functions
|
|
||||||
### catch(name, cb)
|
|
||||||
Catches a hook with `name`. Runs the `cb` when it is thrown
|
|
||||||
|
|
||||||
### catchOnce(name, cb)
|
|
||||||
Same as catch, but only runs the `cb` once and then removes the hook
|
|
||||||
|
|
||||||
### hooks(name) -> {cb, cb...}
|
|
||||||
Returns a table with hooks on the event with `name`.
|
|
||||||
|
|
||||||
### release(name, catcher)
|
|
||||||
Removes the `catcher` for the event with `name`
|
|
||||||
For this to work, `catcher` has to be the same function used to catch
|
|
||||||
an event, like one saved to a variable.
|
|
||||||
|
|
||||||
### throw(name, ...args)
|
|
||||||
Throws a hook with `name` with the provided `args`
|
|
||||||
|
|
|
@ -1,19 +0,0 @@
|
||||||
---
|
|
||||||
title: Module commander
|
|
||||||
description: library for custom commands
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
Commander is a library for writing custom commands in Lua.
|
|
||||||
|
|
||||||
## Functions
|
|
||||||
### deregister(name)
|
|
||||||
Deregisters any command registered with `name`
|
|
||||||
|
|
||||||
### register(name, cb)
|
|
||||||
Register a command with `name` that runs `cb` when ran
|
|
||||||
|
|
|
@ -1,46 +0,0 @@
|
||||||
---
|
|
||||||
title: Module fs
|
|
||||||
description: filesystem interaction and functionality library
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
The fs module provides easy and simple access to filesystem functions
|
|
||||||
and other things, and acts an addition to the Lua standard library's
|
|
||||||
I/O and filesystem functions.
|
|
||||||
|
|
||||||
## Functions
|
|
||||||
### abs(path)
|
|
||||||
Gives an absolute version of `path`.
|
|
||||||
|
|
||||||
### basename(path)
|
|
||||||
Gives the basename of `path`. For the rules,
|
|
||||||
see Go's filepath.Base
|
|
||||||
|
|
||||||
### cd(dir)
|
|
||||||
Changes directory to `dir`
|
|
||||||
|
|
||||||
### dir(path)
|
|
||||||
Returns the directory part of `path`. For the rules, see Go's
|
|
||||||
filepath.Dir
|
|
||||||
|
|
||||||
### glob(pattern)
|
|
||||||
Glob all files and directories that match the pattern.
|
|
||||||
For the rules, see Go's filepath.Glob
|
|
||||||
|
|
||||||
### join(paths...)
|
|
||||||
Takes paths and joins them together with the OS's
|
|
||||||
directory separator (forward or backward slash).
|
|
||||||
|
|
||||||
### mkdir(name, recursive)
|
|
||||||
Makes a directory called `name`. If `recursive` is true, it will create its parent directories.
|
|
||||||
|
|
||||||
### readdir(dir)
|
|
||||||
Returns a table of files in `dir`
|
|
||||||
|
|
||||||
### stat(path)
|
|
||||||
Returns info about `path`
|
|
||||||
|
|
|
@ -1,104 +0,0 @@
|
||||||
---
|
|
||||||
title: Module hilbish
|
|
||||||
description: the core Hilbish API
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
The Hilbish module includes the core API, containing
|
|
||||||
interfaces and functions which directly relate to shell functionality.
|
|
||||||
|
|
||||||
## Interface fields
|
|
||||||
- `ver`: The version of Hilbish
|
|
||||||
- `user`: Username of the user
|
|
||||||
- `host`: Hostname of the machine
|
|
||||||
- `dataDir`: Directory for Hilbish data files, including the docs and default modules
|
|
||||||
- `interactive`: Is Hilbish in an interactive shell?
|
|
||||||
- `login`: Is Hilbish the login shell?
|
|
||||||
- `vimMode`: Current Vim input mode of Hilbish (will be nil if not in Vim input mode)
|
|
||||||
- `exitCode`: xit code of the last executed command
|
|
||||||
|
|
||||||
## Functions
|
|
||||||
### alias(cmd, orig)
|
|
||||||
Sets an alias of `cmd` to `orig`
|
|
||||||
|
|
||||||
### appendPath(dir)
|
|
||||||
Appends `dir` to $PATH
|
|
||||||
|
|
||||||
### complete(scope, cb)
|
|
||||||
Registers a completion handler for `scope`.
|
|
||||||
A `scope` is currently only expected to be `command.<cmd>`,
|
|
||||||
replacing <cmd> with the name of the command (for example `command.git`).
|
|
||||||
`cb` must be a function that returns a table of "completion groups."
|
|
||||||
Check `doc completions` for more information.
|
|
||||||
|
|
||||||
### cwd()
|
|
||||||
Returns the current directory of the shell
|
|
||||||
|
|
||||||
### exec(cmd)
|
|
||||||
Replaces running hilbish with `cmd`
|
|
||||||
|
|
||||||
### goro(fn)
|
|
||||||
Puts `fn` in a goroutine
|
|
||||||
|
|
||||||
### highlighter(line)
|
|
||||||
Line highlighter handler. This is mainly for syntax highlighting, but in
|
|
||||||
reality could set the input of the prompt to *display* anything. The
|
|
||||||
callback is passed the current line and is expected to return a line that
|
|
||||||
will be used as the input display.
|
|
||||||
|
|
||||||
### hinter(line, pos)
|
|
||||||
The command line hint handler. It gets called on every key insert to
|
|
||||||
determine what text to use as an inline hint. It is passed the current
|
|
||||||
line and cursor position. It is expected to return a string which is used
|
|
||||||
as the text for the hint. This is by default a shim. To set hints,
|
|
||||||
override this function with your custom handler.
|
|
||||||
|
|
||||||
### inputMode(mode)
|
|
||||||
Sets the input mode for Hilbish's line reader. Accepts either emacs or vim
|
|
||||||
|
|
||||||
### interval(cb, time)
|
|
||||||
Runs the `cb` function every `time` milliseconds.
|
|
||||||
Returns a `timer` object (see `doc timers`).
|
|
||||||
|
|
||||||
### multiprompt(str)
|
|
||||||
Changes the continued line prompt to `str`
|
|
||||||
|
|
||||||
### prependPath(dir)
|
|
||||||
Prepends `dir` to $PATH
|
|
||||||
|
|
||||||
### prompt(str, typ)
|
|
||||||
Changes the shell prompt to `str`
|
|
||||||
There are a few verbs that can be used in the prompt text.
|
|
||||||
These will be formatted and replaced with the appropriate values.
|
|
||||||
`%d` - Current working directory
|
|
||||||
`%u` - Name of current user
|
|
||||||
`%h` - Hostname of device
|
|
||||||
|
|
||||||
### read(prompt) -> input
|
|
||||||
Read input from the user, using Hilbish's line editor/input reader.
|
|
||||||
This is a separate instance from the one Hilbish actually uses.
|
|
||||||
Returns `input`, will be nil if ctrl + d is pressed, or an error occurs (which shouldn't happen)
|
|
||||||
|
|
||||||
### run(cmd, returnOut) -> exitCode, stdout, stderr
|
|
||||||
Runs `cmd` in Hilbish's sh interpreter.
|
|
||||||
If returnOut is true, the outputs of `cmd` will be returned as the 2nd and
|
|
||||||
3rd values instead of being outputted to the terminal.
|
|
||||||
|
|
||||||
### runnerMode(mode)
|
|
||||||
Sets the execution/runner mode for interactive Hilbish. This determines whether
|
|
||||||
Hilbish wll try to run input as Lua and/or sh or only do one of either.
|
|
||||||
Accepted values for mode are hybrid (the default), hybridRev (sh first then Lua),
|
|
||||||
sh, and lua. It also accepts a function, to which if it is passed one
|
|
||||||
will call it to execute user input instead.
|
|
||||||
|
|
||||||
### timeout(cb, time)
|
|
||||||
Runs the `cb` function after `time` in milliseconds
|
|
||||||
Returns a `timer` object (see `doc timers`).
|
|
||||||
|
|
||||||
### which(name)
|
|
||||||
Checks if `name` is a valid command
|
|
||||||
|
|
|
@ -1,25 +0,0 @@
|
||||||
---
|
|
||||||
title: Interface hilbish.aliases
|
|
||||||
description: command aliasing
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
The alias interface deals with all command aliases in Hilbish.
|
|
||||||
|
|
||||||
## Functions
|
|
||||||
### add(alias, cmd)
|
|
||||||
This is an alias (ha) for the `hilbish.alias` function.
|
|
||||||
|
|
||||||
### delete(name)
|
|
||||||
Removes an alias.
|
|
||||||
|
|
||||||
### list()
|
|
||||||
Get a table of all aliases.
|
|
||||||
|
|
||||||
### resolve(alias)
|
|
||||||
Tries to resolve an alias to its command.
|
|
||||||
|
|
|
@ -1,28 +0,0 @@
|
||||||
---
|
|
||||||
title: Interface hilbish.completions
|
|
||||||
description: tab completions
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
The completions interface deals with tab completions.
|
|
||||||
|
|
||||||
## Functions
|
|
||||||
### call(name, query, ctx, fields)
|
|
||||||
Calls a completer function. This is mainly used to call
|
|
||||||
a command completer, which will have a `name` in the form
|
|
||||||
of `command.name`, example: `command.git`
|
|
||||||
|
|
||||||
### handler(line, pos)
|
|
||||||
The handler function is the callback for tab completion in Hilbish.
|
|
||||||
You can check the completions doc for more info.
|
|
||||||
|
|
||||||
### bins(query, ctx, fields)
|
|
||||||
Returns binary/executale completion candidates based on the provided query.
|
|
||||||
|
|
||||||
### files(query, ctx, fields)
|
|
||||||
Returns file completion candidates based on the provided query.
|
|
||||||
|
|
|
@ -1,26 +0,0 @@
|
||||||
---
|
|
||||||
title: Interface hilbish.editor
|
|
||||||
description: interactions for Hilbish's line reader
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
The hilbish.editor interface provides functions to
|
|
||||||
directly interact with the line editor in use.
|
|
||||||
|
|
||||||
## Functions
|
|
||||||
### getLine()
|
|
||||||
Returns the current input line.
|
|
||||||
|
|
||||||
### getVimRegister(register)
|
|
||||||
Returns the text that is at the register.
|
|
||||||
|
|
||||||
### insert(text)
|
|
||||||
Inserts text into the line.
|
|
||||||
|
|
||||||
### setVimRegister(register, text)
|
|
||||||
Sets the vim register at `register` to hold the passed text.
|
|
||||||
|
|
|
@ -1,27 +0,0 @@
|
||||||
---
|
|
||||||
title: Interface hilbish.history
|
|
||||||
description: command history
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
The history interface deals with command history.
|
|
||||||
This includes the ability to override functions to change the main
|
|
||||||
method of saving history.
|
|
||||||
|
|
||||||
## Functions
|
|
||||||
### add(cmd)
|
|
||||||
Adds a command to the history.
|
|
||||||
|
|
||||||
### clear()
|
|
||||||
Deletes all commands from the history.
|
|
||||||
|
|
||||||
### get(idx)
|
|
||||||
Retrieves a command from the history based on the `idx`.
|
|
||||||
|
|
||||||
### size()
|
|
||||||
Returns the amount of commands in the history.
|
|
||||||
|
|
|
@ -1,54 +0,0 @@
|
||||||
---
|
|
||||||
title: Interface hilbish.jobs
|
|
||||||
description: background job management
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
|
|
||||||
Manage interactive jobs in Hilbish via Lua.
|
|
||||||
|
|
||||||
Jobs are the name of background tasks/commands. A job can be started via
|
|
||||||
interactive usage or with the functions defined below for use in external runners.
|
|
||||||
|
|
||||||
## Object properties
|
|
||||||
- `cmd`: The user entered command string for the job.
|
|
||||||
- `running`: Whether the job is running or not.
|
|
||||||
- `id`: The ID of the job in the job table
|
|
||||||
- `pid`: The Process ID
|
|
||||||
- `exitCode`: The last exit code of the job.
|
|
||||||
- `stdout`: The standard output of the job. This just means the normal logs of the process.
|
|
||||||
- `stderr`: The standard error stream of the process. This (usually) includes error messages of the job.
|
|
||||||
|
|
||||||
## Functions
|
|
||||||
### background()
|
|
||||||
Puts a job in the background. This acts the same as initially running a job.
|
|
||||||
|
|
||||||
### foreground()
|
|
||||||
Puts a job in the foreground. This will cause it to run like it was
|
|
||||||
executed normally and wait for it to complete.
|
|
||||||
|
|
||||||
### start()
|
|
||||||
Starts running the job.
|
|
||||||
|
|
||||||
### stop()
|
|
||||||
Stops the job from running.
|
|
||||||
|
|
||||||
### add(cmdstr, args, execPath)
|
|
||||||
Adds a new job to the job table. Note that this does not immediately run it.
|
|
||||||
|
|
||||||
### all()
|
|
||||||
Returns a table of all job objects.
|
|
||||||
|
|
||||||
### disown(id)
|
|
||||||
Disowns a job. This deletes it from the job table.
|
|
||||||
|
|
||||||
### get(id)
|
|
||||||
Get a job object via its ID.
|
|
||||||
|
|
||||||
### last() -> Job
|
|
||||||
Returns the last added job from the table.
|
|
||||||
|
|
|
@ -1,19 +0,0 @@
|
||||||
---
|
|
||||||
title: Interface hilbish.os
|
|
||||||
description: OS Info
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
The `os` interface provides simple text information properties about
|
|
||||||
the current OS on the systen. This mainly includes the name and
|
|
||||||
version.
|
|
||||||
|
|
||||||
## Interface fields
|
|
||||||
- `family`: Family name of the current OS
|
|
||||||
- `name`: Pretty name of the current OS
|
|
||||||
- `version`: Version of the current OS
|
|
||||||
|
|
|
@ -1,31 +0,0 @@
|
||||||
---
|
|
||||||
title: Interface hilbish.runner
|
|
||||||
description: interactive command runner customization
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
The runner interface contains functions that allow the user to change
|
|
||||||
how Hilbish interprets interactive input.
|
|
||||||
Users can add and change the default runner for interactive input to any
|
|
||||||
language or script of their choosing. A good example is using it to
|
|
||||||
write command in Fennel.
|
|
||||||
|
|
||||||
## Functions
|
|
||||||
### setMode(cb)
|
|
||||||
This is the same as the `hilbish.runnerMode` function. It takes a callback,
|
|
||||||
which will be used to execute all interactive input.
|
|
||||||
In normal cases, neither callbacks should be overrided by the user,
|
|
||||||
as the higher level functions listed below this will handle it.
|
|
||||||
|
|
||||||
### lua(cmd)
|
|
||||||
Evaluates `cmd` as Lua input. This is the same as using `dofile`
|
|
||||||
or `load`, but is appropriated for the runner interface.
|
|
||||||
|
|
||||||
### sh(cmd)
|
|
||||||
Runs a command in Hilbish's shell script interpreter.
|
|
||||||
This is the equivalent of using `source`.
|
|
||||||
|
|
|
@ -1,33 +0,0 @@
|
||||||
---
|
|
||||||
title: Interface hilbish.timers
|
|
||||||
description: timeout and interval API
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
The timers interface si one to easily set timeouts and intervals
|
|
||||||
to run functions after a certain time or repeatedly without using
|
|
||||||
odd tricks.
|
|
||||||
|
|
||||||
## Object properties
|
|
||||||
- `type`: What type of timer it is
|
|
||||||
- `running`: If the timer is running
|
|
||||||
- `duration`: The duration in milliseconds that the timer will run
|
|
||||||
|
|
||||||
## Functions
|
|
||||||
### start()
|
|
||||||
Starts a timer.
|
|
||||||
|
|
||||||
### stop()
|
|
||||||
Stops a timer.
|
|
||||||
|
|
||||||
### create(type, time, callback)
|
|
||||||
Creates a timer that runs based on the specified `time` in milliseconds.
|
|
||||||
The `type` can either be interval (value of 0) or timeout (value of 1).
|
|
||||||
|
|
||||||
### get(id)
|
|
||||||
Retrieves a timer via its ID.
|
|
||||||
|
|
|
@ -1,18 +0,0 @@
|
||||||
---
|
|
||||||
title: Interface hilbish.userDir
|
|
||||||
description: user-related directories
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
This interface just contains properties to know about certain user directories.
|
|
||||||
It is equivalent to XDG on Linux and gets the user's preferred directories
|
|
||||||
for configs and data.
|
|
||||||
|
|
||||||
## Interface fields
|
|
||||||
- `config`: The user's config directory
|
|
||||||
- `data`: The user's directory for program data
|
|
||||||
|
|
|
@ -1,26 +0,0 @@
|
||||||
---
|
|
||||||
title: Module terminal
|
|
||||||
description: low level terminal library
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "API"
|
|
||||||
---
|
|
||||||
|
|
||||||
## Introduction
|
|
||||||
The terminal library is a simple and lower level library for certain terminal interactions.
|
|
||||||
|
|
||||||
## Functions
|
|
||||||
### restoreState()
|
|
||||||
Restores the last saved state of the terminal
|
|
||||||
|
|
||||||
### saveState()
|
|
||||||
Saves the current state of the terminal
|
|
||||||
|
|
||||||
### setRaw()
|
|
||||||
Puts the terminal in raw mode
|
|
||||||
|
|
||||||
### size()
|
|
||||||
Gets the dimensions of the terminal. Returns a table with `width` and `height`
|
|
||||||
Note: this is not the size in relation to the dimensions of the display
|
|
||||||
|
|
|
@ -0,0 +1,12 @@
|
||||||
|
catch(name, cb) > Catches a hook with `name`. Runs the `cb` when it is thrown
|
||||||
|
|
||||||
|
catchOnce(name, cb) > Same as catch, but only runs the `cb` once and then removes the hook
|
||||||
|
|
||||||
|
hooks(name) -> {cb, cb...} > Returns a table with hooks on the event with `name`.
|
||||||
|
|
||||||
|
release(name, catcher) > Removes the `catcher` for the event with `name`
|
||||||
|
For this to work, `catcher` has to be the same function used to catch
|
||||||
|
an event, like one saved to a variable.
|
||||||
|
|
||||||
|
throw(name, ...args) > Throws a hook with `name` with the provided `args`
|
||||||
|
|
|
@ -0,0 +1,4 @@
|
||||||
|
deregister(name) > Deregisters any command registered with `name`
|
||||||
|
|
||||||
|
register(name, cb) > Register a command with `name` that runs `cb` when ran
|
||||||
|
|
|
@ -0,0 +1,22 @@
|
||||||
|
abs(path) > Gives an absolute version of `path`.
|
||||||
|
|
||||||
|
basename(path) > Gives the basename of `path`. For the rules,
|
||||||
|
see Go's filepath.Base
|
||||||
|
|
||||||
|
cd(dir) > Changes directory to `dir`
|
||||||
|
|
||||||
|
dir(path) > Returns the directory part of `path`. For the rules, see Go's
|
||||||
|
filepath.Dir
|
||||||
|
|
||||||
|
glob(pattern) > Glob all files and directories that match the pattern.
|
||||||
|
For the rules, see Go's filepath.Glob
|
||||||
|
|
||||||
|
join(paths...) > Takes paths and joins them together with the OS's
|
||||||
|
directory separator (forward or backward slash).
|
||||||
|
|
||||||
|
mkdir(name, recursive) > Makes a directory called `name`. If `recursive` is true, it will create its parent directories.
|
||||||
|
|
||||||
|
readdir(dir) > Returns a table of files in `dir`
|
||||||
|
|
||||||
|
stat(path) > Returns info about `path`
|
||||||
|
|
|
@ -0,0 +1,62 @@
|
||||||
|
alias(cmd, orig) > Sets an alias of `cmd` to `orig`
|
||||||
|
|
||||||
|
appendPath(dir) > Appends `dir` to $PATH
|
||||||
|
|
||||||
|
complete(scope, cb) > Registers a completion handler for `scope`.
|
||||||
|
A `scope` is currently only expected to be `command.<cmd>`,
|
||||||
|
replacing <cmd> with the name of the command (for example `command.git`).
|
||||||
|
`cb` must be a function that returns a table of "completion groups."
|
||||||
|
Check `doc completions` for more information.
|
||||||
|
|
||||||
|
cwd() > Returns the current directory of the shell
|
||||||
|
|
||||||
|
exec(cmd) > Replaces running hilbish with `cmd`
|
||||||
|
|
||||||
|
goro(fn) > Puts `fn` in a goroutine
|
||||||
|
|
||||||
|
highlighter(line) > Line highlighter handler. This is mainly for syntax highlighting, but in
|
||||||
|
reality could set the input of the prompt to *display* anything. The
|
||||||
|
callback is passed the current line and is expected to return a line that
|
||||||
|
will be used as the input display.
|
||||||
|
|
||||||
|
hinter(line, pos) > The command line hint handler. It gets called on every key insert to
|
||||||
|
determine what text to use as an inline hint. It is passed the current
|
||||||
|
line and cursor position. It is expected to return a string which is used
|
||||||
|
as the text for the hint. This is by default a shim. To set hints,
|
||||||
|
override this function with your custom handler.
|
||||||
|
|
||||||
|
inputMode(mode) > Sets the input mode for Hilbish's line reader. Accepts either emacs or vim
|
||||||
|
|
||||||
|
interval(cb, time) > Runs the `cb` function every `time` milliseconds.
|
||||||
|
Returns a `timer` object (see `doc timers`).
|
||||||
|
|
||||||
|
multiprompt(str) > Changes the continued line prompt to `str`
|
||||||
|
|
||||||
|
prependPath(dir) > Prepends `dir` to $PATH
|
||||||
|
|
||||||
|
prompt(str, typ?) > Changes the shell prompt to `str`
|
||||||
|
There are a few verbs that can be used in the prompt text.
|
||||||
|
These will be formatted and replaced with the appropriate values.
|
||||||
|
`%d` - Current working directory
|
||||||
|
`%u` - Name of current user
|
||||||
|
`%h` - Hostname of device
|
||||||
|
|
||||||
|
read(prompt?) -> input? > Read input from the user, using Hilbish's line editor/input reader.
|
||||||
|
This is a separate instance from the one Hilbish actually uses.
|
||||||
|
Returns `input`, will be nil if ctrl + d is pressed, or an error occurs (which shouldn't happen)
|
||||||
|
|
||||||
|
run(cmd, returnOut) -> exitCode, stdout, stderr > Runs `cmd` in Hilbish's sh interpreter.
|
||||||
|
If returnOut is true, the outputs of `cmd` will be returned as the 2nd and
|
||||||
|
3rd values instead of being outputted to the terminal.
|
||||||
|
|
||||||
|
runnerMode(mode) > Sets the execution/runner mode for interactive Hilbish. This determines whether
|
||||||
|
Hilbish wll try to run input as Lua and/or sh or only do one of either.
|
||||||
|
Accepted values for mode are hybrid (the default), hybridRev (sh first then Lua),
|
||||||
|
sh, and lua. It also accepts a function, to which if it is passed one
|
||||||
|
will call it to execute user input instead.
|
||||||
|
|
||||||
|
timeout(cb, time) > Runs the `cb` function after `time` in milliseconds
|
||||||
|
Returns a `timer` object (see `doc timers`).
|
||||||
|
|
||||||
|
which(name) > Checks if `name` is a valid command
|
||||||
|
|
|
@ -0,0 +1,9 @@
|
||||||
|
restoreState() > Restores the last saved state of the terminal
|
||||||
|
|
||||||
|
saveState() > Saves the current state of the terminal
|
||||||
|
|
||||||
|
setRaw() > Puts the terminal in raw mode
|
||||||
|
|
||||||
|
size() > Gets the dimensions of the terminal. Returns a table with `width` and `height`
|
||||||
|
Note: this is not the size in relation to the dimensions of the display
|
||||||
|
|
16
editor.go
16
editor.go
|
@ -6,10 +6,6 @@ import (
|
||||||
rt "github.com/arnodel/golua/runtime"
|
rt "github.com/arnodel/golua/runtime"
|
||||||
)
|
)
|
||||||
|
|
||||||
// #interface editor
|
|
||||||
// interactions for Hilbish's line reader
|
|
||||||
// The hilbish.editor interface provides functions to
|
|
||||||
// directly interact with the line editor in use.
|
|
||||||
func editorLoader(rtm *rt.Runtime) *rt.Table {
|
func editorLoader(rtm *rt.Runtime) *rt.Table {
|
||||||
exports := map[string]util.LuaExport{
|
exports := map[string]util.LuaExport{
|
||||||
"insert": {editorInsert, 1, false},
|
"insert": {editorInsert, 1, false},
|
||||||
|
@ -24,9 +20,6 @@ func editorLoader(rtm *rt.Runtime) *rt.Table {
|
||||||
return mod
|
return mod
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface editor
|
|
||||||
// insert(text)
|
|
||||||
// Inserts text into the line.
|
|
||||||
func editorInsert(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func editorInsert(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -42,9 +35,6 @@ func editorInsert(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.Next(), nil
|
return c.Next(), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface editor
|
|
||||||
// setVimRegister(register, text)
|
|
||||||
// Sets the vim register at `register` to hold the passed text.
|
|
||||||
func editorSetRegister(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func editorSetRegister(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -65,9 +55,6 @@ func editorSetRegister(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.Next(), nil
|
return c.Next(), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface editor
|
|
||||||
// getVimRegister(register)
|
|
||||||
// Returns the text that is at the register.
|
|
||||||
func editorGetRegister(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func editorGetRegister(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -83,9 +70,6 @@ func editorGetRegister(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.PushingNext1(t.Runtime, rt.StringValue(string(buf))), nil
|
return c.PushingNext1(t.Runtime, rt.StringValue(string(buf))), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface editor
|
|
||||||
// getLine()
|
|
||||||
// Returns the current input line.
|
|
||||||
func editorGetLine(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func editorGetLine(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
buf := lr.rl.GetLine()
|
buf := lr.rl.GetLine()
|
||||||
|
|
||||||
|
|
|
@ -27,6 +27,6 @@ function bait.release(name, catcher) end
|
||||||
--- Throws a hook with `name` with the provided `args`
|
--- Throws a hook with `name` with the provided `args`
|
||||||
--- @param name string
|
--- @param name string
|
||||||
--- @vararg any
|
--- @vararg any
|
||||||
function bait.throw(name, ...args) end
|
function bait.throw(name, ...) end
|
||||||
|
|
||||||
return bait
|
return bait
|
||||||
|
|
|
@ -8,7 +8,7 @@ function fs.abs(path) end
|
||||||
|
|
||||||
--- Gives the basename of `path`. For the rules,
|
--- Gives the basename of `path`. For the rules,
|
||||||
--- see Go's filepath.Base
|
--- see Go's filepath.Base
|
||||||
function fs.basename(path) end
|
function fs.basename() end
|
||||||
|
|
||||||
--- Changes directory to `dir`
|
--- Changes directory to `dir`
|
||||||
--- @param dir string
|
--- @param dir string
|
||||||
|
@ -16,15 +16,15 @@ function fs.cd(dir) end
|
||||||
|
|
||||||
--- Returns the directory part of `path`. For the rules, see Go's
|
--- Returns the directory part of `path`. For the rules, see Go's
|
||||||
--- filepath.Dir
|
--- filepath.Dir
|
||||||
function fs.dir(path) end
|
function fs.dir() end
|
||||||
|
|
||||||
--- Glob all files and directories that match the pattern.
|
--- Glob all files and directories that match the pattern.
|
||||||
--- For the rules, see Go's filepath.Glob
|
--- For the rules, see Go's filepath.Glob
|
||||||
function fs.glob(pattern) end
|
function fs.glob() end
|
||||||
|
|
||||||
--- Takes paths and joins them together with the OS's
|
--- Takes paths and joins them together with the OS's
|
||||||
--- directory separator (forward or backward slash).
|
--- directory separator (forward or backward slash).
|
||||||
function fs.join(paths...) end
|
function fs.join() end
|
||||||
|
|
||||||
--- Makes a directory called `name`. If `recursive` is true, it will create its parent directories.
|
--- Makes a directory called `name`. If `recursive` is true, it will create its parent directories.
|
||||||
--- @param name string
|
--- @param name string
|
||||||
|
|
|
@ -2,38 +2,6 @@
|
||||||
|
|
||||||
local hilbish = {}
|
local hilbish = {}
|
||||||
|
|
||||||
--- This is an alias (ha) for the `hilbish.alias` function.
|
|
||||||
--- @param alias string
|
|
||||||
--- @param cmd string
|
|
||||||
function hilbish.aliases.add(alias, cmd) end
|
|
||||||
|
|
||||||
--- This is the same as the `hilbish.runnerMode` function. It takes a callback,
|
|
||||||
--- which will be used to execute all interactive input.
|
|
||||||
--- In normal cases, neither callbacks should be overrided by the user,
|
|
||||||
--- as the higher level functions listed below this will handle it.
|
|
||||||
function hilbish.runner.setMode(cb) end
|
|
||||||
|
|
||||||
--- Calls a completer function. This is mainly used to call
|
|
||||||
--- a command completer, which will have a `name` in the form
|
|
||||||
--- of `command.name`, example: `command.git`
|
|
||||||
function hilbish.completions.call(name, query, ctx, fields) end
|
|
||||||
|
|
||||||
--- The handler function is the callback for tab completion in Hilbish.
|
|
||||||
--- You can check the completions doc for more info.
|
|
||||||
function hilbish.completions.handler(line, pos) end
|
|
||||||
|
|
||||||
--- Returns the current input line.
|
|
||||||
function hilbish.editor.getLine() end
|
|
||||||
|
|
||||||
--- Returns the text that is at the register.
|
|
||||||
function hilbish.editor.getVimRegister(register) end
|
|
||||||
|
|
||||||
--- Inserts text into the line.
|
|
||||||
function hilbish.editor.insert(text) end
|
|
||||||
|
|
||||||
--- Sets the vim register at `register` to hold the passed text.
|
|
||||||
function hilbish.editor.setVimRegister(register, text) end
|
|
||||||
|
|
||||||
--- Sets an alias of `cmd` to `orig`
|
--- Sets an alias of `cmd` to `orig`
|
||||||
--- @param cmd string
|
--- @param cmd string
|
||||||
--- @param orig string
|
--- @param orig string
|
||||||
|
@ -105,21 +73,20 @@ function hilbish.prependPath(dir) end
|
||||||
--- `%u` - Name of current user
|
--- `%u` - Name of current user
|
||||||
--- `%h` - Hostname of device
|
--- `%h` - Hostname of device
|
||||||
--- @param str string
|
--- @param str string
|
||||||
--- @param typ string|nil Type of prompt, being left or right. Left by default.
|
--- @param typ string Type of prompt, being left or right. Left by default.
|
||||||
function hilbish.prompt(str, typ) end
|
function hilbish.prompt(str, typ) end
|
||||||
|
|
||||||
--- Read input from the user, using Hilbish's line editor/input reader.
|
--- Read input from the user, using Hilbish's line editor/input reader.
|
||||||
--- This is a separate instance from the one Hilbish actually uses.
|
--- This is a separate instance from the one Hilbish actually uses.
|
||||||
--- Returns `input`, will be nil if ctrl + d is pressed, or an error occurs (which shouldn't happen)
|
--- Returns `input`, will be nil if ctrl + d is pressed, or an error occurs (which shouldn't happen)
|
||||||
--- @param prompt string|nil
|
--- @param prompt string
|
||||||
--- @returns string|nil
|
|
||||||
function hilbish.read(prompt) end
|
function hilbish.read(prompt) end
|
||||||
|
|
||||||
--- Runs `cmd` in Hilbish's sh interpreter.
|
--- Runs `cmd` in Hilbish's sh interpreter.
|
||||||
--- If returnOut is true, the outputs of `cmd` will be returned as the 2nd and
|
--- If returnOut is true, the outputs of `cmd` will be returned as the 2nd and
|
||||||
--- 3rd values instead of being outputted to the terminal.
|
--- 3rd values instead of being outputted to the terminal.
|
||||||
--- @param cmd string
|
--- @param cmd string
|
||||||
function hilbish.run(cmd, returnOut) end
|
function hilbish.run(cmd) end
|
||||||
|
|
||||||
--- Sets the execution/runner mode for interactive Hilbish. This determines whether
|
--- Sets the execution/runner mode for interactive Hilbish. This determines whether
|
||||||
--- Hilbish wll try to run input as Lua and/or sh or only do one of either.
|
--- Hilbish wll try to run input as Lua and/or sh or only do one of either.
|
||||||
|
@ -138,87 +105,6 @@ function hilbish.timeout(cb, time) end
|
||||||
|
|
||||||
--- Checks if `name` is a valid command
|
--- Checks if `name` is a valid command
|
||||||
--- @param binName string
|
--- @param binName string
|
||||||
function hilbish.which(name) end
|
function hilbish.which(binName) end
|
||||||
|
|
||||||
--- Puts a job in the background. This acts the same as initially running a job.
|
|
||||||
function hilbish.jobs:background() end
|
|
||||||
|
|
||||||
--- Returns binary/executale completion candidates based on the provided query.
|
|
||||||
function hilbish.completions.bins(query, ctx, fields) end
|
|
||||||
|
|
||||||
--- Returns file completion candidates based on the provided query.
|
|
||||||
function hilbish.completions.files(query, ctx, fields) end
|
|
||||||
|
|
||||||
--- Puts a job in the foreground. This will cause it to run like it was
|
|
||||||
--- executed normally and wait for it to complete.
|
|
||||||
function hilbish.jobs:foreground() end
|
|
||||||
|
|
||||||
--- Evaluates `cmd` as Lua input. This is the same as using `dofile`
|
|
||||||
--- or `load`, but is appropriated for the runner interface.
|
|
||||||
function hilbish.runner.lua(cmd) end
|
|
||||||
|
|
||||||
--- Starts running the job.
|
|
||||||
function hilbish.jobs:start() end
|
|
||||||
|
|
||||||
--- Stops the job from running.
|
|
||||||
function hilbish.jobs.stop() end
|
|
||||||
|
|
||||||
--- Runs a command in Hilbish's shell script interpreter.
|
|
||||||
--- This is the equivalent of using `source`.
|
|
||||||
function hilbish.runner.sh(cmd) end
|
|
||||||
|
|
||||||
--- Starts a timer.
|
|
||||||
function hilbish.timers:start() end
|
|
||||||
|
|
||||||
--- Stops a timer.
|
|
||||||
function hilbish.timers:stop() end
|
|
||||||
|
|
||||||
--- Removes an alias.
|
|
||||||
--- @param name string
|
|
||||||
function hilbish.aliases.delete(name) end
|
|
||||||
|
|
||||||
--- Get a table of all aliases.
|
|
||||||
function hilbish.aliases.list() end
|
|
||||||
|
|
||||||
--- Tries to resolve an alias to its command.
|
|
||||||
--- @param alias string
|
|
||||||
function hilbish.aliases.resolve(alias) end
|
|
||||||
|
|
||||||
--- Adds a new job to the job table. Note that this does not immediately run it.
|
|
||||||
function hilbish.jobs.add(cmdstr, args, execPath) end
|
|
||||||
|
|
||||||
--- Returns a table of all job objects.
|
|
||||||
function hilbish.jobs.all() end
|
|
||||||
|
|
||||||
--- Disowns a job. This deletes it from the job table.
|
|
||||||
function hilbish.jobs.disown(id) end
|
|
||||||
|
|
||||||
--- Get a job object via its ID.
|
|
||||||
function hilbish.jobs.get(id) end
|
|
||||||
|
|
||||||
--- Returns the last added job from the table.
|
|
||||||
function hilbish.jobs.last() end
|
|
||||||
|
|
||||||
--- Adds a command to the history.
|
|
||||||
--- @param cmd string
|
|
||||||
function hilbish.history.add(cmd) end
|
|
||||||
|
|
||||||
--- Deletes all commands from the history.
|
|
||||||
function hilbish.history.clear() end
|
|
||||||
|
|
||||||
--- Retrieves a command from the history based on the `idx`.
|
|
||||||
--- @param idx number
|
|
||||||
function hilbish.history.get(idx) end
|
|
||||||
|
|
||||||
--- Returns the amount of commands in the history.
|
|
||||||
--- @returns number
|
|
||||||
function hilbish.history.size() end
|
|
||||||
|
|
||||||
--- Creates a timer that runs based on the specified `time` in milliseconds.
|
|
||||||
--- The `type` can either be interval (value of 0) or timeout (value of 1).
|
|
||||||
function hilbish.timers.create(type, time, callback) end
|
|
||||||
|
|
||||||
--- Retrieves a timer via its ID.
|
|
||||||
function hilbish.timers.get(id) end
|
|
||||||
|
|
||||||
return hilbish
|
return hilbish
|
||||||
|
|
4
exec.go
4
exec.go
|
@ -141,9 +141,9 @@ func runInput(input string, priv bool) {
|
||||||
if err != nil {
|
if err != nil {
|
||||||
if exErr, ok := isExecError(err); ok {
|
if exErr, ok := isExecError(err); ok {
|
||||||
hooks.Emit("command." + exErr.typ, exErr.cmd)
|
hooks.Emit("command." + exErr.typ, exErr.cmd)
|
||||||
} else {
|
err = exErr.sprint()
|
||||||
fmt.Fprintln(os.Stderr, err)
|
|
||||||
}
|
}
|
||||||
|
fmt.Fprintln(os.Stderr, err)
|
||||||
}
|
}
|
||||||
cmdFinish(exitCode, input, priv)
|
cmdFinish(exitCode, input, priv)
|
||||||
}
|
}
|
||||||
|
|
2
go.mod
2
go.mod
|
@ -29,4 +29,4 @@ replace github.com/maxlandon/readline => ./readline
|
||||||
|
|
||||||
replace layeh.com/gopher-luar => github.com/layeh/gopher-luar v1.0.10
|
replace layeh.com/gopher-luar => github.com/layeh/gopher-luar v1.0.10
|
||||||
|
|
||||||
replace github.com/arnodel/golua => github.com/Rosettea/golua v0.0.0-20221213193027-cbf6d4e4d345
|
replace github.com/arnodel/golua => github.com/Rosettea/golua v0.0.0-20220518005949-116371948fe3
|
||||||
|
|
4
go.sum
4
go.sum
|
@ -2,10 +2,6 @@ github.com/Rosettea/golua v0.0.0-20220419183026-6d22d6fec5ac h1:dtXrgjch8PQyf7C9
|
||||||
github.com/Rosettea/golua v0.0.0-20220419183026-6d22d6fec5ac/go.mod h1:9jzpYPiU2is0HVGCiuIOBSXdergHUW44IEjmuN1UrIE=
|
github.com/Rosettea/golua v0.0.0-20220419183026-6d22d6fec5ac/go.mod h1:9jzpYPiU2is0HVGCiuIOBSXdergHUW44IEjmuN1UrIE=
|
||||||
github.com/Rosettea/golua v0.0.0-20220518005949-116371948fe3 h1:I/wWr40FFLFF9pbT3wLb1FAEZhKb/hUWE+nJ5uHBK2g=
|
github.com/Rosettea/golua v0.0.0-20220518005949-116371948fe3 h1:I/wWr40FFLFF9pbT3wLb1FAEZhKb/hUWE+nJ5uHBK2g=
|
||||||
github.com/Rosettea/golua v0.0.0-20220518005949-116371948fe3/go.mod h1:9jzpYPiU2is0HVGCiuIOBSXdergHUW44IEjmuN1UrIE=
|
github.com/Rosettea/golua v0.0.0-20220518005949-116371948fe3/go.mod h1:9jzpYPiU2is0HVGCiuIOBSXdergHUW44IEjmuN1UrIE=
|
||||||
github.com/Rosettea/golua v0.0.0-20220621002945-b05143999437 h1:6lWu4YVLeKuZ8jR9xwHONhkHBsrIbw5dpfG1gtOVw0A=
|
|
||||||
github.com/Rosettea/golua v0.0.0-20220621002945-b05143999437/go.mod h1:9jzpYPiU2is0HVGCiuIOBSXdergHUW44IEjmuN1UrIE=
|
|
||||||
github.com/Rosettea/golua v0.0.0-20221213193027-cbf6d4e4d345 h1:QNYjYDogUSiNUkffbhFSrSCtpZhofeiVYGFN2FI4wSs=
|
|
||||||
github.com/Rosettea/golua v0.0.0-20221213193027-cbf6d4e4d345/go.mod h1:9jzpYPiU2is0HVGCiuIOBSXdergHUW44IEjmuN1UrIE=
|
|
||||||
github.com/Rosettea/sh/v3 v3.4.0-0.dev.0.20220306140409-795a84b00b4e h1:P2XupP8SaylWaudD1DqbWtZ3mIa8OsE9635LmR+Q+lg=
|
github.com/Rosettea/sh/v3 v3.4.0-0.dev.0.20220306140409-795a84b00b4e h1:P2XupP8SaylWaudD1DqbWtZ3mIa8OsE9635LmR+Q+lg=
|
||||||
github.com/Rosettea/sh/v3 v3.4.0-0.dev.0.20220306140409-795a84b00b4e/go.mod h1:R09vh/04ILvP2Gj8/Z9Jd0Dh0ZIvaucowMEs6abQpWs=
|
github.com/Rosettea/sh/v3 v3.4.0-0.dev.0.20220306140409-795a84b00b4e/go.mod h1:R09vh/04ILvP2Gj8/Z9Jd0Dh0ZIvaucowMEs6abQpWs=
|
||||||
github.com/Rosettea/sh/v3 v3.4.0-0.dev.0.20220524215627-dfd9a4fa219b h1:s5eDMhBk6H1BgipgLub/gv9qeyBaTuiHM0k3h2/9TSE=
|
github.com/Rosettea/sh/v3 v3.4.0-0.dev.0.20220524215627-dfd9a4fa219b h1:s5eDMhBk6H1BgipgLub/gv9qeyBaTuiHM0k3h2/9TSE=
|
||||||
|
|
|
@ -1,9 +1,3 @@
|
||||||
// the event emitter
|
|
||||||
// Bait is the event emitter for Hilbish. Why name it bait? Why not.
|
|
||||||
// It throws hooks that you can catch. This is what you will use if
|
|
||||||
// you want to listen in on hooks to know when certain things have
|
|
||||||
// happened, like when you've changed directory, a command has failed,
|
|
||||||
// etc. To find all available hooks thrown by Hilbish, see doc hooks.
|
|
||||||
package bait
|
package bait
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
|
|
@ -1,5 +1,3 @@
|
||||||
// library for custom commands
|
|
||||||
// Commander is a library for writing custom commands in Lua.
|
|
||||||
package commander
|
package commander
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
|
|
@ -1,7 +1,3 @@
|
||||||
// filesystem interaction and functionality library
|
|
||||||
// The fs module provides easy and simple access to filesystem functions
|
|
||||||
// and other things, and acts an addition to the Lua standard library's
|
|
||||||
// I/O and filesystem functions.
|
|
||||||
package fs
|
package fs
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
|
|
@ -1,5 +1,3 @@
|
||||||
// low level terminal library
|
|
||||||
// The terminal library is a simple and lower level library for certain terminal interactions.
|
|
||||||
package terminal
|
package terminal
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
%global debug_package %{nil}
|
%global debug_package %{nil}
|
||||||
|
|
||||||
Name: hilbish-git
|
Name: hilbish-git
|
||||||
Version: {{{ git_tag_version }}}.{{{ git_short_hash }}}
|
Version: {{{ git_dir_version }}}
|
||||||
Release: 1%{?dist}
|
Release: 1%{?dist}
|
||||||
Summary: The flower shell. A comfy and nice little shell for Lua fans!
|
Summary: The flower shell. A comfy and nice little shell for Lua fans!
|
||||||
License: MIT
|
License: MIT
|
||||||
|
|
45
job.go
45
job.go
|
@ -110,10 +110,6 @@ func (j *job) getProc() *os.Process {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface jobs
|
|
||||||
// #member
|
|
||||||
// start()
|
|
||||||
// Starts running the job.
|
|
||||||
func luaStartJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func luaStartJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -134,9 +130,6 @@ func luaStartJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.Next(), nil
|
return c.Next(), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface jobs
|
|
||||||
// stop()
|
|
||||||
// Stops the job from running.
|
|
||||||
func luaStopJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func luaStopJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -155,11 +148,6 @@ func luaStopJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.Next(), nil
|
return c.Next(), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface jobs
|
|
||||||
// #member
|
|
||||||
// foreground()
|
|
||||||
// Puts a job in the foreground. This will cause it to run like it was
|
|
||||||
// executed normally and wait for it to complete.
|
|
||||||
func luaForegroundJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func luaForegroundJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -192,10 +180,6 @@ func luaForegroundJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.Next(), nil
|
return c.Next(), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface jobs
|
|
||||||
// #member
|
|
||||||
// background()
|
|
||||||
// Puts a job in the background. This acts the same as initially running a job.
|
|
||||||
func luaBackgroundJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func luaBackgroundJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -292,20 +276,6 @@ func (j *jobHandler) stopAll() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface jobs
|
|
||||||
// #property cmd The user entered command string for the job.
|
|
||||||
// #property running Whether the job is running or not.
|
|
||||||
// #property id The ID of the job in the job table
|
|
||||||
// #property pid The Process ID
|
|
||||||
// #property exitCode The last exit code of the job.
|
|
||||||
// #property stdout The standard output of the job. This just means the normal logs of the process.
|
|
||||||
// #property stderr The standard error stream of the process. This (usually) includes error messages of the job.
|
|
||||||
// background job management
|
|
||||||
/*
|
|
||||||
Manage interactive jobs in Hilbish via Lua.
|
|
||||||
|
|
||||||
Jobs are the name of background tasks/commands. A job can be started via
|
|
||||||
interactive usage or with the functions defined below for use in external runners. */
|
|
||||||
func (j *jobHandler) loader(rtm *rt.Runtime) *rt.Table {
|
func (j *jobHandler) loader(rtm *rt.Runtime) *rt.Table {
|
||||||
jobMethods := rt.NewTable()
|
jobMethods := rt.NewTable()
|
||||||
jFuncs := map[string]util.LuaExport{
|
jFuncs := map[string]util.LuaExport{
|
||||||
|
@ -383,9 +353,6 @@ func jobUserData(j *job) *rt.UserData {
|
||||||
return rt.NewUserData(j, jobMeta.AsTable())
|
return rt.NewUserData(j, jobMeta.AsTable())
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface jobs
|
|
||||||
// get(id)
|
|
||||||
// Get a job object via its ID.
|
|
||||||
func (j *jobHandler) luaGetJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func (j *jobHandler) luaGetJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
j.mu.RLock()
|
j.mu.RLock()
|
||||||
defer j.mu.RUnlock()
|
defer j.mu.RUnlock()
|
||||||
|
@ -406,9 +373,6 @@ func (j *jobHandler) luaGetJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.PushingNext(t.Runtime, rt.UserDataValue(job.ud)), nil
|
return c.PushingNext(t.Runtime, rt.UserDataValue(job.ud)), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface jobs
|
|
||||||
// add(cmdstr, args, execPath)
|
|
||||||
// Adds a new job to the job table. Note that this does not immediately run it.
|
|
||||||
func (j *jobHandler) luaAddJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func (j *jobHandler) luaAddJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.CheckNArgs(3); err != nil {
|
if err := c.CheckNArgs(3); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -438,9 +402,6 @@ func (j *jobHandler) luaAddJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.PushingNext1(t.Runtime, rt.UserDataValue(jb.ud)), nil
|
return c.PushingNext1(t.Runtime, rt.UserDataValue(jb.ud)), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface jobs
|
|
||||||
// all()
|
|
||||||
// Returns a table of all job objects.
|
|
||||||
func (j *jobHandler) luaAllJobs(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func (j *jobHandler) luaAllJobs(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
j.mu.RLock()
|
j.mu.RLock()
|
||||||
defer j.mu.RUnlock()
|
defer j.mu.RUnlock()
|
||||||
|
@ -453,9 +414,6 @@ func (j *jobHandler) luaAllJobs(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.PushingNext1(t.Runtime, rt.TableValue(jobTbl)), nil
|
return c.PushingNext1(t.Runtime, rt.TableValue(jobTbl)), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface jobs
|
|
||||||
// disown(id)
|
|
||||||
// Disowns a job. This deletes it from the job table.
|
|
||||||
func (j *jobHandler) luaDisownJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func (j *jobHandler) luaDisownJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -473,9 +431,6 @@ func (j *jobHandler) luaDisownJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.Next(), nil
|
return c.Next(), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface jobs
|
|
||||||
// last() -> Job
|
|
||||||
// Returns the last added job from the table.
|
|
||||||
func (j *jobHandler) luaLastJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func (j *jobHandler) luaLastJob(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
j.mu.RLock()
|
j.mu.RLock()
|
||||||
defer j.mu.RUnlock()
|
defer j.mu.RUnlock()
|
||||||
|
|
|
@ -4,34 +4,34 @@ local lunacolors = require 'lunacolors'
|
||||||
|
|
||||||
commander.register('doc', function(args)
|
commander.register('doc', function(args)
|
||||||
local moddocPath = hilbish.dataDir .. '/docs/'
|
local moddocPath = hilbish.dataDir .. '/docs/'
|
||||||
local apidocHeader = [[
|
local modDocFormat = [[
|
||||||
# %s
|
%s
|
||||||
{grayBg} {white}{italic}%s {reset}
|
%s
|
||||||
|
# Functions
|
||||||
]]
|
]]
|
||||||
|
|
||||||
if #args > 0 then
|
if #args > 0 then
|
||||||
local mod = args[1]
|
local mod = args[1]
|
||||||
|
|
||||||
local f = io.open(moddocPath .. mod .. '.md', 'rb')
|
local f = io.open(moddocPath .. mod .. '.txt', 'rb')
|
||||||
local funcdocs = nil
|
local funcdocs = nil
|
||||||
if not f then
|
if not f then
|
||||||
-- assume subdir
|
-- assume subdir
|
||||||
-- dataDir/docs/<mod>/<mod>.md
|
-- dataDir/docs/<mod>/<mod>.txt
|
||||||
moddocPath = moddocPath .. mod .. '/'
|
moddocPath = moddocPath .. mod .. '/'
|
||||||
local subdocName = args[2]
|
local subdocName = args[2]
|
||||||
if not subdocName then
|
if not subdocName then
|
||||||
subdocName = 'index'
|
subdocName = 'index'
|
||||||
end
|
end
|
||||||
f = io.open(moddocPath .. subdocName .. '.md', 'rb')
|
f = io.open(moddocPath .. subdocName .. '.txt', 'rb')
|
||||||
if not f then
|
if not f then
|
||||||
print('No documentation found for ' .. mod .. '.')
|
print('No documentation found for ' .. mod .. '.')
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
funcdocs = f:read '*a'
|
funcdocs = f:read '*a'
|
||||||
local moddocs = table.filter(fs.readdir(moddocPath), function(f) return f ~= 'index.md' end)
|
local moddocs = table.filter(fs.readdir(moddocPath), function(f) return f ~= 'index.txt' end)
|
||||||
local subdocs = table.map(moddocs, function(fname)
|
local subdocs = table.map(moddocs, function(fname)
|
||||||
return lunacolors.underline(lunacolors.blue(string.gsub(fname, '.md', '')))
|
return lunacolors.underline(lunacolors.blue(string.gsub(fname, '.txt', '')))
|
||||||
end)
|
end)
|
||||||
if subdocName == 'index' then
|
if subdocName == 'index' then
|
||||||
funcdocs = funcdocs .. '\nSubdocs: ' .. table.concat(subdocs, ', ')
|
funcdocs = funcdocs .. '\nSubdocs: ' .. table.concat(subdocs, ', ')
|
||||||
|
@ -41,24 +41,8 @@ commander.register('doc', function(args)
|
||||||
if not funcdocs then
|
if not funcdocs then
|
||||||
funcdocs = f:read '*a'
|
funcdocs = f:read '*a'
|
||||||
end
|
end
|
||||||
local valsStr = funcdocs:match '%-%-%-\n([^%-%-%-]+)\n'
|
local desc = ''
|
||||||
local vals = {}
|
local ok = pcall(require, mod)
|
||||||
if valsStr then
|
|
||||||
local _, endpos = funcdocs:find('---\n' .. valsStr .. '\n---\n\n', 1, true)
|
|
||||||
funcdocs = funcdocs:sub(endpos + 1, #funcdocs)
|
|
||||||
|
|
||||||
-- parse vals
|
|
||||||
local lines = string.split(valsStr, '\n')
|
|
||||||
for _, line in ipairs(lines) do
|
|
||||||
local key = line:match '(%w+): '
|
|
||||||
local val = line:match '^%w+: (.-)$'
|
|
||||||
|
|
||||||
vals[key] = val
|
|
||||||
end
|
|
||||||
end
|
|
||||||
if mod == 'api' then
|
|
||||||
funcdocs = string.format(apidocHeader, vals.name, vals.description) .. funcdocs
|
|
||||||
end
|
|
||||||
local backtickOccurence = 0
|
local backtickOccurence = 0
|
||||||
local formattedFuncs = lunacolors.format(funcdocs:sub(1, #funcdocs - 1):gsub('`', function()
|
local formattedFuncs = lunacolors.format(funcdocs:sub(1, #funcdocs - 1):gsub('`', function()
|
||||||
backtickOccurence = backtickOccurence + 1
|
backtickOccurence = backtickOccurence + 1
|
||||||
|
@ -67,16 +51,34 @@ commander.register('doc', function(args)
|
||||||
else
|
else
|
||||||
return '{underline}{green}'
|
return '{underline}{green}'
|
||||||
end
|
end
|
||||||
end):gsub('#+.-\n', function(t)
|
|
||||||
return '{bold}{magenta}' .. t .. '{reset}'
|
|
||||||
end))
|
end))
|
||||||
print(formattedFuncs)
|
|
||||||
|
if ok then
|
||||||
|
local props = {}
|
||||||
|
local propstr = ''
|
||||||
|
local modDesc = ''
|
||||||
|
local modmt = getmetatable(require(mod))
|
||||||
|
if modmt then
|
||||||
|
modDesc = modmt.__doc
|
||||||
|
if modmt.__docProp then
|
||||||
|
-- not all modules have docs for properties
|
||||||
|
props = table.map(modmt.__docProp, function(v, k)
|
||||||
|
return lunacolors.underline(lunacolors.blue(k)) .. ' > ' .. v
|
||||||
|
end)
|
||||||
|
end
|
||||||
|
if #props > 0 then
|
||||||
|
propstr = '\n# Properties\n' .. table.concat(props, '\n') .. '\n'
|
||||||
|
end
|
||||||
|
desc = string.format(modDocFormat, modDesc, propstr)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
print(desc .. formattedFuncs)
|
||||||
f:close()
|
f:close()
|
||||||
|
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
local modules = table.map(fs.readdir(moddocPath), function(f)
|
local modules = table.map(fs.readdir(moddocPath), function(f)
|
||||||
return lunacolors.underline(lunacolors.blue(string.gsub(f, '.md', '')))
|
return lunacolors.underline(lunacolors.blue(string.gsub(f, '.txt', '')))
|
||||||
end)
|
end)
|
||||||
|
|
||||||
io.write [[
|
io.write [[
|
||||||
|
|
|
@ -24,7 +24,7 @@ function hilbish.completion.handler(line, pos)
|
||||||
return {compGroup}, pfx
|
return {compGroup}, pfx
|
||||||
else
|
else
|
||||||
local ok, compGroups, pfx = pcall(hilbish.completion.call,
|
local ok, compGroups, pfx = pcall(hilbish.completion.call,
|
||||||
'command.' .. fields[1], query, ctx, fields)
|
'command.' .. #fields[1], query, ctx, fields)
|
||||||
if ok then
|
if ok then
|
||||||
return compGroups, pfx
|
return compGroups, pfx
|
||||||
end
|
end
|
||||||
|
|
|
@ -69,11 +69,3 @@ end
|
||||||
bait.catch('error', function(event, handler, err)
|
bait.catch('error', function(event, handler, err)
|
||||||
bait.release(event, handler)
|
bait.release(event, handler)
|
||||||
end)
|
end)
|
||||||
|
|
||||||
bait.catch('command.not-found', function(cmd)
|
|
||||||
print(string.format('hilbish: %s not found', cmd))
|
|
||||||
end)
|
|
||||||
|
|
||||||
bait.catch('command.not-executable', function(cmd)
|
|
||||||
print(string.format('hilbish: %s: not executable', cmd))
|
|
||||||
end)
|
|
||||||
|
|
|
@ -1,4 +1,3 @@
|
||||||
--- hilbish.runner
|
|
||||||
local currentRunner = 'hybrid'
|
local currentRunner = 'hybrid'
|
||||||
local runners = {}
|
local runners = {}
|
||||||
|
|
||||||
|
|
27
os.go
27
os.go
|
@ -1,27 +0,0 @@
|
||||||
package main
|
|
||||||
|
|
||||||
import (
|
|
||||||
"hilbish/util"
|
|
||||||
|
|
||||||
rt "github.com/arnodel/golua/runtime"
|
|
||||||
"github.com/blackfireio/osinfo"
|
|
||||||
)
|
|
||||||
|
|
||||||
// #interface os
|
|
||||||
// OS Info
|
|
||||||
// The `os` interface provides simple text information properties about
|
|
||||||
// the current OS on the systen. This mainly includes the name and
|
|
||||||
// version.
|
|
||||||
// #field family Family name of the current OS
|
|
||||||
// #field name Pretty name of the current OS
|
|
||||||
// #field version Version of the current OS
|
|
||||||
func hshosLoader(rtm *rt.Runtime) *rt.Table {
|
|
||||||
info, _ := osinfo.GetOSInfo()
|
|
||||||
mod := rt.NewTable()
|
|
||||||
|
|
||||||
util.SetField(rtm, mod, "family", rt.StringValue(info.Family), "Family name of the current OS")
|
|
||||||
util.SetField(rtm, mod, "name", rt.StringValue(info.Name), "Pretty name of the current OS")
|
|
||||||
util.SetField(rtm, mod, "version", rt.StringValue(info.Version), "Version of the current OS")
|
|
||||||
|
|
||||||
return mod
|
|
||||||
}
|
|
|
@ -123,20 +123,23 @@ func (rl *Instance) walkHistory(i int) {
|
||||||
|
|
||||||
// When we are exiting the current line buffer to move around
|
// When we are exiting the current line buffer to move around
|
||||||
// the history, we make buffer the current line
|
// the history, we make buffer the current line
|
||||||
if rl.histOffset == 0 && rl.histOffset + i == 1 {
|
if rl.histPos == 0 && (rl.histPos+i) == 1 {
|
||||||
rl.lineBuf = string(rl.line)
|
rl.lineBuf = string(rl.line)
|
||||||
}
|
}
|
||||||
|
|
||||||
rl.histOffset += i
|
switch rl.histPos + i {
|
||||||
if rl.histOffset == 0 {
|
case 0, history.Len() + 1:
|
||||||
|
rl.histPos = 0
|
||||||
rl.line = []rune(rl.lineBuf)
|
rl.line = []rune(rl.lineBuf)
|
||||||
rl.pos = len(rl.lineBuf)
|
rl.pos = len(rl.lineBuf)
|
||||||
} else if rl.histOffset <= -1 {
|
return
|
||||||
rl.histOffset = 0
|
case -1:
|
||||||
} else {
|
rl.histPos = 0
|
||||||
|
rl.lineBuf = string(rl.line)
|
||||||
|
default:
|
||||||
dedup = true
|
dedup = true
|
||||||
old = string(rl.line)
|
old = string(rl.line)
|
||||||
new, err = history.GetLine(history.Len() - rl.histOffset)
|
new, err = history.GetLine(history.Len() - rl.histPos - 1)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
rl.resetHelpers()
|
rl.resetHelpers()
|
||||||
print("\r\n" + err.Error() + "\r\n")
|
print("\r\n" + err.Error() + "\r\n")
|
||||||
|
@ -145,6 +148,7 @@ func (rl *Instance) walkHistory(i int) {
|
||||||
}
|
}
|
||||||
|
|
||||||
rl.clearLine()
|
rl.clearLine()
|
||||||
|
rl.histPos += i
|
||||||
rl.line = []rune(new)
|
rl.line = []rune(new)
|
||||||
rl.pos = len(rl.line)
|
rl.pos = len(rl.line)
|
||||||
if rl.pos > 0 {
|
if rl.pos > 0 {
|
||||||
|
|
|
@ -134,7 +134,6 @@ type Instance struct {
|
||||||
// history operating params
|
// history operating params
|
||||||
lineBuf string
|
lineBuf string
|
||||||
histPos int
|
histPos int
|
||||||
histOffset int
|
|
||||||
histNavIdx int // Used for quick history navigation.
|
histNavIdx int // Used for quick history navigation.
|
||||||
|
|
||||||
//
|
//
|
||||||
|
|
|
@ -49,7 +49,7 @@ func (rl *Instance) Readline() (string, error) {
|
||||||
|
|
||||||
// History Init
|
// History Init
|
||||||
// We need this set to the last command, so that we can access it quickly
|
// We need this set to the last command, so that we can access it quickly
|
||||||
rl.histOffset = 0
|
rl.histPos = 0
|
||||||
rl.viUndoHistory = []undoItem{{line: "", pos: 0}}
|
rl.viUndoHistory = []undoItem{{line: "", pos: 0}}
|
||||||
|
|
||||||
// Multisplit
|
// Multisplit
|
||||||
|
@ -546,10 +546,6 @@ func (rl *Instance) Readline() (string, error) {
|
||||||
// entry readline is currently configured for and then update the line entries
|
// entry readline is currently configured for and then update the line entries
|
||||||
// accordingly.
|
// accordingly.
|
||||||
func (rl *Instance) editorInput(r []rune) {
|
func (rl *Instance) editorInput(r []rune) {
|
||||||
if len(r) == 0 {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
switch rl.modeViMode {
|
switch rl.modeViMode {
|
||||||
case VimKeys:
|
case VimKeys:
|
||||||
rl.vi(r[0])
|
rl.vi(r[0])
|
||||||
|
|
21
rl.go
21
rl.go
|
@ -225,11 +225,7 @@ func (lr *lineReader) Resize() {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface history
|
// lua module
|
||||||
// command history
|
|
||||||
// The history interface deals with command history.
|
|
||||||
// This includes the ability to override functions to change the main
|
|
||||||
// method of saving history.
|
|
||||||
func (lr *lineReader) Loader(rtm *rt.Runtime) *rt.Table {
|
func (lr *lineReader) Loader(rtm *rt.Runtime) *rt.Table {
|
||||||
lrLua := map[string]util.LuaExport{
|
lrLua := map[string]util.LuaExport{
|
||||||
"add": {lr.luaAddHistory, 1, false},
|
"add": {lr.luaAddHistory, 1, false},
|
||||||
|
@ -245,10 +241,6 @@ func (lr *lineReader) Loader(rtm *rt.Runtime) *rt.Table {
|
||||||
return mod
|
return mod
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface history
|
|
||||||
// add(cmd)
|
|
||||||
// Adds a command to the history.
|
|
||||||
// --- @param cmd string
|
|
||||||
func (lr *lineReader) luaAddHistory(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func (lr *lineReader) luaAddHistory(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -262,18 +254,10 @@ func (lr *lineReader) luaAddHistory(t *rt.Thread, c *rt.GoCont) (rt.Cont, error)
|
||||||
return c.Next(), nil
|
return c.Next(), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface history
|
|
||||||
// size()
|
|
||||||
// Returns the amount of commands in the history.
|
|
||||||
// --- @returns number
|
|
||||||
func (lr *lineReader) luaSize(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func (lr *lineReader) luaSize(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.PushingNext1(t.Runtime, rt.IntValue(int64(lr.fileHist.Len()))), nil
|
return c.PushingNext1(t.Runtime, rt.IntValue(int64(lr.fileHist.Len()))), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface history
|
|
||||||
// get(idx)
|
|
||||||
// Retrieves a command from the history based on the `idx`.
|
|
||||||
// --- @param idx number
|
|
||||||
func (lr *lineReader) luaGetHistory(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func (lr *lineReader) luaGetHistory(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -300,9 +284,6 @@ func (lr *lineReader) luaAllHistory(t *rt.Thread, c *rt.GoCont) (rt.Cont, error)
|
||||||
return c.PushingNext1(t.Runtime, rt.TableValue(tbl)), nil
|
return c.PushingNext1(t.Runtime, rt.TableValue(tbl)), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface history
|
|
||||||
// clear()
|
|
||||||
// Deletes all commands from the history.
|
|
||||||
func (lr *lineReader) luaClearHistory(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func (lr *lineReader) luaClearHistory(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
lr.fileHist.clear()
|
lr.fileHist.clear()
|
||||||
return c.Next(), nil
|
return c.Next(), nil
|
||||||
|
|
25
rpkg.macros
25
rpkg.macros
|
@ -1,25 +0,0 @@
|
||||||
function git_short_hash {
|
|
||||||
short_hash="$(cached git_short_hash)"
|
|
||||||
|
|
||||||
if [ -z "$short_hash" ]; then
|
|
||||||
short_hash="$(git rev-parse --short HEAD)"
|
|
||||||
fi
|
|
||||||
|
|
||||||
output "$short_hash"
|
|
||||||
}
|
|
||||||
|
|
||||||
function git_tag_version {
|
|
||||||
tag="$(cached git_tag_version)"
|
|
||||||
|
|
||||||
if [ -z "$tag" ]; then
|
|
||||||
tag="$(git describe --tags --abbrev=0)"
|
|
||||||
fi
|
|
||||||
|
|
||||||
# Remove the potential prefix of `v`
|
|
||||||
if [[ $tag =~ ^v[0-9].* ]]; then
|
|
||||||
tag="${tag:1}"
|
|
||||||
fi
|
|
||||||
|
|
||||||
tag="${tag/"-"/"."}"
|
|
||||||
output "$tag"
|
|
||||||
}
|
|
|
@ -6,13 +6,6 @@ import (
|
||||||
rt "github.com/arnodel/golua/runtime"
|
rt "github.com/arnodel/golua/runtime"
|
||||||
)
|
)
|
||||||
|
|
||||||
// #interface runner
|
|
||||||
// interactive command runner customization
|
|
||||||
// The runner interface contains functions that allow the user to change
|
|
||||||
// how Hilbish interprets interactive input.
|
|
||||||
// Users can add and change the default runner for interactive input to any
|
|
||||||
// language or script of their choosing. A good example is using it to
|
|
||||||
// write command in Fennel.
|
|
||||||
func runnerModeLoader(rtm *rt.Runtime) *rt.Table {
|
func runnerModeLoader(rtm *rt.Runtime) *rt.Table {
|
||||||
exports := map[string]util.LuaExport{
|
exports := map[string]util.LuaExport{
|
||||||
"sh": {shRunner, 1, false},
|
"sh": {shRunner, 1, false},
|
||||||
|
@ -26,18 +19,6 @@ func runnerModeLoader(rtm *rt.Runtime) *rt.Table {
|
||||||
return mod
|
return mod
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface runner
|
|
||||||
// setMode(cb)
|
|
||||||
// This is the same as the `hilbish.runnerMode` function. It takes a callback,
|
|
||||||
// which will be used to execute all interactive input.
|
|
||||||
// In normal cases, neither callbacks should be overrided by the user,
|
|
||||||
// as the higher level functions listed below this will handle it.
|
|
||||||
func _runnerMode() {}
|
|
||||||
|
|
||||||
// #interface runner
|
|
||||||
// sh(cmd)
|
|
||||||
// Runs a command in Hilbish's shell script interpreter.
|
|
||||||
// This is the equivalent of using `source`.
|
|
||||||
func shRunner(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func shRunner(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -61,10 +42,6 @@ func shRunner(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.PushingNext(t.Runtime, rt.TableValue(runnerRet)), nil
|
return c.PushingNext(t.Runtime, rt.TableValue(runnerRet)), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface runner
|
|
||||||
// lua(cmd)
|
|
||||||
// Evaluates `cmd` as Lua input. This is the same as using `dofile`
|
|
||||||
// or `load`, but is appropriated for the runner interface.
|
|
||||||
func luaRunner(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func luaRunner(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
|
10
timer.go
10
timer.go
|
@ -21,7 +21,7 @@ type timer struct{
|
||||||
running bool
|
running bool
|
||||||
dur time.Duration
|
dur time.Duration
|
||||||
fun *rt.Closure
|
fun *rt.Closure
|
||||||
th *timersModule
|
th *timerHandler
|
||||||
ticker *time.Ticker
|
ticker *time.Ticker
|
||||||
ud *rt.UserData
|
ud *rt.UserData
|
||||||
channel chan struct{}
|
channel chan struct{}
|
||||||
|
@ -73,10 +73,6 @@ func (t *timer) stop() error {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface timers
|
|
||||||
// #member
|
|
||||||
// start()
|
|
||||||
// Starts a timer.
|
|
||||||
func timerStart(thr *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func timerStart(thr *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
@ -95,10 +91,6 @@ func timerStart(thr *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.Next(), nil
|
return c.Next(), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface timers
|
|
||||||
// #member
|
|
||||||
// stop()
|
|
||||||
// Stops a timer.
|
|
||||||
func timerStop(thr *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
func timerStop(thr *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
|
|
@ -10,10 +10,10 @@ import (
|
||||||
rt "github.com/arnodel/golua/runtime"
|
rt "github.com/arnodel/golua/runtime"
|
||||||
)
|
)
|
||||||
|
|
||||||
var timers *timersModule
|
var timers *timerHandler
|
||||||
var timerMetaKey = rt.StringValue("hshtimer")
|
var timerMetaKey = rt.StringValue("hshtimer")
|
||||||
|
|
||||||
type timersModule struct {
|
type timerHandler struct {
|
||||||
mu *sync.RWMutex
|
mu *sync.RWMutex
|
||||||
wg *sync.WaitGroup
|
wg *sync.WaitGroup
|
||||||
timers map[int]*timer
|
timers map[int]*timer
|
||||||
|
@ -21,8 +21,8 @@ type timersModule struct {
|
||||||
running int
|
running int
|
||||||
}
|
}
|
||||||
|
|
||||||
func newTimersModule() *timersModule {
|
func newTimerHandler() *timerHandler {
|
||||||
return &timersModule{
|
return &timerHandler{
|
||||||
timers: make(map[int]*timer),
|
timers: make(map[int]*timer),
|
||||||
latestID: 0,
|
latestID: 0,
|
||||||
mu: &sync.RWMutex{},
|
mu: &sync.RWMutex{},
|
||||||
|
@ -30,11 +30,11 @@ func newTimersModule() *timersModule {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (th *timersModule) wait() {
|
func (th *timerHandler) wait() {
|
||||||
th.wg.Wait()
|
th.wg.Wait()
|
||||||
}
|
}
|
||||||
|
|
||||||
func (th *timersModule) create(typ timerType, dur time.Duration, fun *rt.Closure) *timer {
|
func (th *timerHandler) create(typ timerType, dur time.Duration, fun *rt.Closure) *timer {
|
||||||
th.mu.Lock()
|
th.mu.Lock()
|
||||||
defer th.mu.Unlock()
|
defer th.mu.Unlock()
|
||||||
|
|
||||||
|
@ -54,18 +54,14 @@ func (th *timersModule) create(typ timerType, dur time.Duration, fun *rt.Closure
|
||||||
return t
|
return t
|
||||||
}
|
}
|
||||||
|
|
||||||
func (th *timersModule) get(id int) *timer {
|
func (th *timerHandler) get(id int) *timer {
|
||||||
th.mu.RLock()
|
th.mu.RLock()
|
||||||
defer th.mu.RUnlock()
|
defer th.mu.RUnlock()
|
||||||
|
|
||||||
return th.timers[id]
|
return th.timers[id]
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface timers
|
func (th *timerHandler) luaCreate(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
// create(type, time, callback)
|
|
||||||
// Creates a timer that runs based on the specified `time` in milliseconds.
|
|
||||||
// The `type` can either be interval (value of 0) or timeout (value of 1).
|
|
||||||
func (th *timersModule) luaCreate(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
|
||||||
if err := c.CheckNArgs(3); err != nil {
|
if err := c.CheckNArgs(3); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
@ -87,10 +83,7 @@ func (th *timersModule) luaCreate(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.PushingNext1(t.Runtime, rt.UserDataValue(tmr.ud)), nil
|
return c.PushingNext1(t.Runtime, rt.UserDataValue(tmr.ud)), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface timers
|
func (th *timerHandler) luaGet(thr *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
// get(id)
|
|
||||||
// Retrieves a timer via its ID.
|
|
||||||
func (th *timersModule) luaGet(thr *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
|
||||||
if err := c.Check1Arg(); err != nil {
|
if err := c.Check1Arg(); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
@ -107,15 +100,7 @@ func (th *timersModule) luaGet(thr *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
||||||
return c.Next(), nil
|
return c.Next(), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// #interface timers
|
func (th *timerHandler) loader(rtm *rt.Runtime) *rt.Table {
|
||||||
// #property type What type of timer it is
|
|
||||||
// #property running If the timer is running
|
|
||||||
// #property duration The duration in milliseconds that the timer will run
|
|
||||||
// timeout and interval API
|
|
||||||
// The timers interface si one to easily set timeouts and intervals
|
|
||||||
// to run functions after a certain time or repeatedly without using
|
|
||||||
// odd tricks.
|
|
||||||
func (th *timersModule) loader(rtm *rt.Runtime) *rt.Table {
|
|
||||||
timerMethods := rt.NewTable()
|
timerMethods := rt.NewTable()
|
||||||
timerFuncs := map[string]util.LuaExport{
|
timerFuncs := map[string]util.LuaExport{
|
||||||
"start": {timerStart, 1, false},
|
"start": {timerStart, 1, false},
|
||||||
|
|
23
userdir.go
23
userdir.go
|
@ -1,23 +0,0 @@
|
||||||
package main
|
|
||||||
|
|
||||||
import (
|
|
||||||
"hilbish/util"
|
|
||||||
|
|
||||||
rt "github.com/arnodel/golua/runtime"
|
|
||||||
)
|
|
||||||
|
|
||||||
// #interface userDir
|
|
||||||
// user-related directories
|
|
||||||
// This interface just contains properties to know about certain user directories.
|
|
||||||
// It is equivalent to XDG on Linux and gets the user's preferred directories
|
|
||||||
// for configs and data.
|
|
||||||
// #field config The user's config directory
|
|
||||||
// #field data The user's directory for program data
|
|
||||||
func userDirLoader(rtm *rt.Runtime) *rt.Table {
|
|
||||||
mod := rt.NewTable()
|
|
||||||
|
|
||||||
util.SetField(rtm, mod, "config", rt.StringValue(confDir), "User's config directory")
|
|
||||||
util.SetField(rtm, mod, "data", rt.StringValue(userDataDir), "XDG data directory")
|
|
||||||
|
|
||||||
return mod
|
|
||||||
}
|
|
|
@ -14,7 +14,7 @@ var (
|
||||||
.. hilbish.userDir.config .. '/hilbish/?/init.lua;'
|
.. hilbish.userDir.config .. '/hilbish/?/init.lua;'
|
||||||
.. hilbish.userDir.config .. '/hilbish/?/?.lua;'
|
.. hilbish.userDir.config .. '/hilbish/?/?.lua;'
|
||||||
.. hilbish.userDir.config .. '/hilbish/?.lua'`
|
.. hilbish.userDir.config .. '/hilbish/?.lua'`
|
||||||
dataDir = "/usr/local/share/hilbish"
|
dataDir = "/usr/share/hilbish"
|
||||||
preloadPath = dataDir + "/nature/init.lua"
|
preloadPath = dataDir + "/nature/init.lua"
|
||||||
sampleConfPath = dataDir + "/.hilbishrc.lua" // Path to default/sample config
|
sampleConfPath = dataDir + "/.hilbishrc.lua" // Path to default/sample config
|
||||||
defaultConfDir = ""
|
defaultConfDir = ""
|
||||||
|
|
|
@ -1,6 +0,0 @@
|
||||||
---
|
|
||||||
title: "{{ replace .Name "-" " " | title }}"
|
|
||||||
date: {{ .Date }}
|
|
||||||
draft: true
|
|
||||||
---
|
|
||||||
|
|
|
@ -1,25 +0,0 @@
|
||||||
baseURL = 'https://rosettea.github.io/Hilbish/'
|
|
||||||
languageCode = 'en-us'
|
|
||||||
title = 'Hilbish'
|
|
||||||
theme = 'hsh'
|
|
||||||
enableGitInfo = true
|
|
||||||
|
|
||||||
[menu]
|
|
||||||
[[menu.nav]]
|
|
||||||
identifier = 'home'
|
|
||||||
name = 'Home'
|
|
||||||
pageref = '/'
|
|
||||||
weight = 1
|
|
||||||
[[menu.nav]]
|
|
||||||
identifier = 'install'
|
|
||||||
name = 'Install'
|
|
||||||
pageref = '/install'
|
|
||||||
weight = 2
|
|
||||||
[[menu.nav]]
|
|
||||||
identifier = 'docs'
|
|
||||||
name = 'Docs'
|
|
||||||
pageref = '/docs'
|
|
||||||
weight = 3
|
|
||||||
|
|
||||||
[markup.goldmark.renderer]
|
|
||||||
unsafe = true
|
|
|
@ -1,134 +0,0 @@
|
||||||
---
|
|
||||||
description: 'Something Unique. Hilbish is the new interactive shell for Lua fans. Extensible, scriptable, configurable: All in Lua.'
|
|
||||||
---
|
|
||||||
|
|
||||||
[//]: <>
|
|
||||||
|
|
||||||
<!-- hugo (prob goldmark) is funny; the html wont work if its the first thing -->
|
|
||||||
<div class="text-center">
|
|
||||||
<h1 class="fw-light">Something Unique.</h1>
|
|
||||||
<p>
|
|
||||||
<strong>Hilbish</strong> is the new interactive shell for Lua fans.<br>
|
|
||||||
Extensible, scriptable, configurable: All in Lua.
|
|
||||||
</p>
|
|
||||||
<a href="install" class="btn btn-primary">Install</a>
|
|
||||||
<a href="https://github.com/Rosettea/Hilbish" class="btn btn-secondary" target="_blank">Github</a>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<hr>
|
|
||||||
|
|
||||||
<div class="row row-cols-1 row-cols-md-2 g-4">
|
|
||||||
<div class="col">
|
|
||||||
<div class="card border-light mb-3">
|
|
||||||
<div class="row g-0">
|
|
||||||
<div class="col-md-4">
|
|
||||||
<a href="https://safe.kashima.moe/6njmopm47u1x.png">
|
|
||||||
<img src="https://safe.kashima.moe/6njmopm47u1x.png" class="img-fluid rounded-start">
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
<div class="col-md-8">
|
|
||||||
<h5 class="card-header">Simple and Easy Scripting</h5>
|
|
||||||
<div class="card-body">
|
|
||||||
<p class="card-text">
|
|
||||||
Hilbish is configured and scripted in the Lua programming language.
|
|
||||||
This removes all the old, ugly things about Shell script and introduces
|
|
||||||
everything good about Lua, including other languages (Moonscript & Fennel).
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div class="col">
|
|
||||||
<div class="card border-light mb-3">
|
|
||||||
<div class="row g-0">
|
|
||||||
<div class="col-md-4">
|
|
||||||
<a href="https://safe.kashima.moe/jkndbi636lzj.png">
|
|
||||||
<img src="https://safe.kashima.moe/jkndbi636lzj.png" class="img-fluid rounded-start">
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
<div class="col-md-8">
|
|
||||||
<h5 class="card-header">History and Completion Menus</h5>
|
|
||||||
<div class="card-body">
|
|
||||||
<p class="card-text">
|
|
||||||
Hilbish provides the user with proper menus for completions,
|
|
||||||
history searching. Want to see your previous commands? Hit Ctrl-R.
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div class="col">
|
|
||||||
<div class="card border-light mb-3">
|
|
||||||
<div class="row g-0">
|
|
||||||
<div class="col-md-4">
|
|
||||||
<a href="https://safe.kashima.moe/6yfeooamzro4.png">
|
|
||||||
<img src="https://safe.kashima.moe/6yfeooamzro4.png" class="img-fluid rounded-start">
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
<div class="col-md-8">
|
|
||||||
<h5 class="card-header">Tons of Features, and More to Come</h5>
|
|
||||||
<div class="card-body">
|
|
||||||
<p class="card-text">
|
|
||||||
Hilbish offers a bunch of features to make your interactive
|
|
||||||
shell experience rich. Things like syntax highlighting and hinting
|
|
||||||
available via the Lua API.
|
|
||||||
</p>
|
|
||||||
<p class="card-small text-muted">* Command hints shown in photo are not default.</p>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<!-- uncomment, replace top when editor interface can be replaced (and replace the images) -->
|
|
||||||
<!--
|
|
||||||
<div class="col">
|
|
||||||
<div class="card border-light mb-3">
|
|
||||||
<div class="row g-0">
|
|
||||||
<div class="col-md-4">
|
|
||||||
<a href="https://safe.kashima.moe/6yfeooamzro4.png">
|
|
||||||
<img src="https://safe.kashima.moe/6yfeooamzro4.png" class="img-fluid rounded-start">
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
<div class="col-md-8">
|
|
||||||
<h5 class="card-header">Highly Extensible</h5>
|
|
||||||
<div class="card-body">
|
|
||||||
<p class="card-text">
|
|
||||||
Hilbish can be turned into an all new shell if wanted. One of our
|
|
||||||
main goals is that most (if not all) interfaces can be replaced.
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
-->
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<hr>
|
|
||||||
|
|
||||||
<h1 class="fw-light">Why not just Lua?</h1>
|
|
||||||
<p>
|
|
||||||
Hilbish is your interactive shell as well as a just a Lua interpreter
|
|
||||||
and enhanced REPL.<br>
|
|
||||||
</p>
|
|
||||||
<ul class="list-group" style="max-width: 64em;">
|
|
||||||
<li class="list-group-item"><i class="fa-solid fa-battery-full"></i> Batteries included Lua runtime that's also your user shell!</li>
|
|
||||||
<li class="list-group-item"><i class="fa-solid fa-network-wired"></i> Hilbish is easily cross platform. It has OS agnostic interfaces for easy cross platform Lua code.</li>
|
|
||||||
</ul>
|
|
||||||
|
|
||||||
<hr>
|
|
||||||
|
|
||||||
<h1 class="fw-light">Try It Today!</h1>
|
|
||||||
<p>
|
|
||||||
Hilbish is known to run on the 3 major platforms (Windows, MacOS, Linux)
|
|
||||||
but likely builds on other Unixes!
|
|
||||||
<br>
|
|
||||||
Windows doesn't work as well as it should, so if you're a Windows user,
|
|
||||||
<a href="https://github.com/Rosettea/Hilbish/discussions/165">say something</a>!
|
|
||||||
<ul class="list-group" style="max-width: 64em;">
|
|
||||||
<li class="list-group-item"><i class="fa-solid fa-cloud-arrow-down"></i> <a href="/Hilbish/install" style="text-decoration: none;"><strong>Download</strong></a> the binary</li>
|
|
||||||
<li class="list-group-item"><i class="fa-solid fa-screwdriver-wrench"></i> <a href="https://github.com/Rosettea/Hilbish#manual-build" style="text-decoration: none;"><strong>Build</strong></a> from source</li>
|
|
||||||
</ul>
|
|
||||||
</p>
|
|
|
@ -1,19 +0,0 @@
|
||||||
---
|
|
||||||
title: Introduction
|
|
||||||
layout: doc
|
|
||||||
weight: -1
|
|
||||||
menu: docs
|
|
||||||
---
|
|
||||||
|
|
||||||
Here lies the documentation for Hilbish, the hyper extensible Lua shell.
|
|
||||||
Hilbish provides you with a few quality of life features and useful
|
|
||||||
functions to ensure you can make the shell fully yours.
|
|
||||||
|
|
||||||
These features include:
|
|
||||||
- Completion and history search menus
|
|
||||||
- Hinting and syntax highlighting (scripted by user)
|
|
||||||
|
|
||||||
# Installation
|
|
||||||
Steps on installing Hilbish will be at the Install page in the navigation bar
|
|
||||||
at the top. This also included getting development builds from the GitHub
|
|
||||||
repository.
|
|
|
@ -1 +0,0 @@
|
||||||
../../../docs/api/
|
|
|
@ -1,25 +0,0 @@
|
||||||
---
|
|
||||||
title: Frequently Asked Questions
|
|
||||||
layout: doc
|
|
||||||
weight: -20
|
|
||||||
menu: docs
|
|
||||||
---
|
|
||||||
|
|
||||||
# Is Hilbish POSIX compliant?
|
|
||||||
No, it is not. POSIX compliance is a non-goal. Perhaps in the future,
|
|
||||||
someone would be able to write a native plugin to support shell scripting
|
|
||||||
(which would be against it's main goal, but ....)
|
|
||||||
|
|
||||||
# Windows Support?
|
|
||||||
It compiles for Windows (CI ensures it does), but otherwise it is not
|
|
||||||
directly supported. If you'd like to improve this situation,
|
|
||||||
checkout [the discussion](https://github.com/Rosettea/Hilbish/discussions/165).
|
|
||||||
|
|
||||||
# Where is the API documentation?
|
|
||||||
The builtin `doc` command supplies all documentation of Hilbish provided
|
|
||||||
APIs. This will be on the website in the near future.
|
|
||||||
|
|
||||||
# Why?
|
|
||||||
Hilbish emerged from the desire of a Lua configured shell.
|
|
||||||
It was the initial reason that it was created, but now it's more:
|
|
||||||
to be hyper extensible, simpler and more user friendly.
|
|
|
@ -1,11 +0,0 @@
|
||||||
---
|
|
||||||
title: Features
|
|
||||||
layout: doc
|
|
||||||
weight: -40
|
|
||||||
menu: docs
|
|
||||||
---
|
|
||||||
|
|
||||||
Hilbish has a wide range of features to enhance the user's experience and
|
|
||||||
is always adding new ones. If there is something missing here or something
|
|
||||||
you would like to see, please [start a discussion](https://github.com/Rosettea/Hilbish/discussions)
|
|
||||||
or comment on any existing ones which match your request.
|
|
|
@ -1,17 +0,0 @@
|
||||||
---
|
|
||||||
title: Runner Mode
|
|
||||||
description: Customize the interactive script/command runner.
|
|
||||||
layout: doc
|
|
||||||
menu:
|
|
||||||
docs:
|
|
||||||
parent: "Features"
|
|
||||||
---
|
|
||||||
|
|
||||||
Hilbish allows you to change how interactive text can be interpreted.
|
|
||||||
This is mainly due to the fact that the default method Hilbish uses
|
|
||||||
is that it runs Lua first and then falls back to shell script.
|
|
||||||
|
|
||||||
In some cases, someone might want to switch to just shell script to avoid
|
|
||||||
it while interactive but still have a Lua config, or go full Lua to use
|
|
||||||
Hilbish as a REPL. This also allows users to add alternative languages,
|
|
||||||
instead of either like Fennel.
|
|
|
@ -1,59 +0,0 @@
|
||||||
---
|
|
||||||
title: Getting Started
|
|
||||||
layout: doc
|
|
||||||
weight: -10
|
|
||||||
menu: docs
|
|
||||||
---
|
|
||||||
|
|
||||||
To start Hilbish, open a terminal. If Hilbish has been installed and is not the
|
|
||||||
default shell, you can simply run `hilbish` to start it. This will launch
|
|
||||||
a normal interactive session.
|
|
||||||
To exit, you can either run the `exit` command or hit Ctrl+D.
|
|
||||||
|
|
||||||
# Setting as Default
|
|
||||||
## Login shell
|
|
||||||
There are a few ways to make Hilbish your default shell. A simple way is
|
|
||||||
to make it your user/login shell.
|
|
||||||
|
|
||||||
{{< warning `It is not recommended to set Hilbish as your login shell. That is expected to be a
|
|
||||||
POSIX compliant shell, which Hilbish is not. At most, there will just be a
|
|
||||||
few variables missing in your environment` >}}
|
|
||||||
|
|
||||||
To do that, simply run `chsh -s /usr/bin/hilbish`.
|
|
||||||
Some distros (namely Fedora) might have `lchsh` instead, which is used like `lchsh <user>`.
|
|
||||||
When prompted, you can put the path for Hilbish.
|
|
||||||
|
|
||||||
## Default with terminal
|
|
||||||
The simpler way is to set the default shell for your terminal. The way of
|
|
||||||
doing this depends on how your terminal settings are configured.
|
|
||||||
|
|
||||||
## Run after login shell
|
|
||||||
Some shells (like zsh) have an rc file, like `.zlogin`, which is ran when the shell session
|
|
||||||
is a login shell. In that file, you can run Hilbish. Example:
|
|
||||||
|
|
||||||
```
|
|
||||||
exec hilbish -S -l
|
|
||||||
```
|
|
||||||
|
|
||||||
This will replace the shell with Hilbish, set $SHELL to Hilbish and launch it as a login shell.
|
|
||||||
|
|
||||||
# Configuration
|
|
||||||
Once installation and setup has been done, you can then configure Hilbish.
|
|
||||||
It is configured and scripted via Lua, so the config file is a Lua file.
|
|
||||||
You can use any pure Lua library to do whatever you want.
|
|
||||||
|
|
||||||
Hilbish's sample configuration is usually located in `hilbish.dataDir .. '/.hilbishrc.lua'`.
|
|
||||||
You can print that path via Lua to see what it is: `print(hilbish.dataDir .. '/.hilbishrc.lua')`.
|
|
||||||
As an example, it will usually will result in `/usr/share/hilbish/.hilbishrc.lua` on Linux.
|
|
||||||
|
|
||||||
To edit your user configuration, you can copy that file to `hilbish.userDir.config .. '/hilbish/init.lua'`,
|
|
||||||
which follows XDG on Linux and MacOS, and is located in %APPDATA% on Windows.
|
|
||||||
|
|
||||||
As the directory is usually `~/.config` on Linux, you can run this command to copy it:
|
|
||||||
`cp /usr/share/hilbish/.hilbishrc.lua ~/.config/hilbish/init.lua`
|
|
||||||
|
|
||||||
Now you can get to editing it. Since it's just a Lua file, having basic
|
|
||||||
knowledge of Lua would help. All of Lua's standard libraries and functions
|
|
||||||
from Lua 5.4 are available. Hilbish has some custom and modules that are
|
|
||||||
available. To see them, you can run the `doc` command. This also works as
|
|
||||||
general documentation for other things.
|
|
|
@ -1,55 +0,0 @@
|
||||||
---
|
|
||||||
title: Install
|
|
||||||
description: Steps on how to install Hilbish on all the OSes and distros supported.
|
|
||||||
layout: page
|
|
||||||
---
|
|
||||||
|
|
||||||
## Official Binaries
|
|
||||||
The best way to get Hilbish is to get a build directly from GitHub.
|
|
||||||
At any time, there are 2 versions of Hilbish recommended for download:
|
|
||||||
the latest stable release, and development builds from the master branch.
|
|
||||||
|
|
||||||
You can download both at any time, but note that the development builds may
|
|
||||||
have breaking changes.
|
|
||||||
|
|
||||||
For the latest **stable release**, check here: https://github.com/Rosettea/Hilbish/releases/latest
|
|
||||||
For a **development build**: https://nightly.link/Rosettea/Hilbish/workflows/build/master
|
|
||||||
|
|
||||||
## Package Repositories
|
|
||||||
### Fedora (COPR)
|
|
||||||
An official COPR is offered to install Hilbish easily on Fedora.
|
|
||||||
Enable the repo:
|
|
||||||
```
|
|
||||||
sudo dnf copr enable sammyette/Hilbish
|
|
||||||
```
|
|
||||||
|
|
||||||
And install Hilbish:
|
|
||||||
```
|
|
||||||
sudo dnf install hilbish
|
|
||||||
```
|
|
||||||
|
|
||||||
Or for the latest development build from master:
|
|
||||||
```
|
|
||||||
sudo dnf install hilbish-git
|
|
||||||
```
|
|
||||||
|
|
||||||
### Arch Linux (AUR)
|
|
||||||
Hilbish is on the AUR. Setup an AUR helper, and install.
|
|
||||||
Example with yay:
|
|
||||||
|
|
||||||
```
|
|
||||||
yay -S hilbish
|
|
||||||
```
|
|
||||||
|
|
||||||
Or, from master branch:
|
|
||||||
```
|
|
||||||
yay -S hilbish-git
|
|
||||||
```
|
|
||||||
|
|
||||||
### Alpine Linux
|
|
||||||
Hilbish is currentlty in the testing/edge repository for Alpine.
|
|
||||||
Follow the steps [here](https://wiki.alpinelinux.org/wiki/Enable_Community_Repository)
|
|
||||||
(Using testing repositories) and install:
|
|
||||||
```
|
|
||||||
apk add hilbish
|
|
||||||
```
|
|
Binary file not shown.
Before Width: | Height: | Size: 16 KiB |
|
@ -1,21 +0,0 @@
|
||||||
MIT License
|
|
||||||
|
|
||||||
Copyright (c) 2022 Rosettea
|
|
||||||
|
|
||||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
||||||
of this software and associated documentation files (the "Software"), to deal
|
|
||||||
in the Software without restriction, including without limitation the rights
|
|
||||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
||||||
copies of the Software, and to permit persons to whom the Software is
|
|
||||||
furnished to do so, subject to the following conditions:
|
|
||||||
|
|
||||||
The above copyright notice and this permission notice shall be included in all
|
|
||||||
copies or substantial portions of the Software.
|
|
||||||
|
|
||||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
||||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
||||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
||||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
||||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
||||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
||||||
SOFTWARE.
|
|
|
@ -1,2 +0,0 @@
|
||||||
+++
|
|
||||||
+++
|
|
|
@ -1,7 +0,0 @@
|
||||||
{{ define "main"}}
|
|
||||||
<main id="main">
|
|
||||||
<div>
|
|
||||||
<h1><a href="{{ "/" | relURL }}">Go Home</a></h1>
|
|
||||||
</div>
|
|
||||||
</main>
|
|
||||||
{{ end }}
|
|
|
@ -1,6 +0,0 @@
|
||||||
<h{{ (add .Level 1) }} id="{{ .Anchor | safeURL }}">
|
|
||||||
{{ .Text | safeHTML }}
|
|
||||||
</h{{ (add .Level 1) }}>
|
|
||||||
{{ if eq .Text ""}}
|
|
||||||
<hr>
|
|
||||||
{{ end }}
|
|
|
@ -1,4 +0,0 @@
|
||||||
<a href="{{ .Destination | safeURL }}"{{ with .Title}} title="{{ . }}"{{ end }}{{ if eq (substr .Destination 0 4) "http" }} target="_blank" rel="noopener"{{ end }}>
|
|
||||||
{{ .Text | safeHTML }}
|
|
||||||
</a>
|
|
||||||
|
|
|
@ -1,21 +0,0 @@
|
||||||
<!DOCTYPE html>
|
|
||||||
<html>
|
|
||||||
{{- partial "head.html" . -}}
|
|
||||||
<body class="d-flex flex-column min-vh-100" style="overflow-x: hidden;">
|
|
||||||
<svg xmlns="http://www.w3.org/2000/svg" style="display: none;">
|
|
||||||
<symbol id="check-circle-fill" fill="currentColor" viewBox="0 0 16 16">
|
|
||||||
<path d="M16 8A8 8 0 1 1 0 8a8 8 0 0 1 16 0zm-3.97-3.03a.75.75 0 0 0-1.08.022L7.477 9.417 5.384 7.323a.75.75 0 0 0-1.06 1.06L6.97 11.03a.75.75 0 0 0 1.079-.02l3.992-4.99a.75.75 0 0 0-.01-1.05z"/>
|
|
||||||
</symbol>
|
|
||||||
<symbol id="info-fill" fill="currentColor" viewBox="0 0 16 16">
|
|
||||||
<path d="M8 16A8 8 0 1 0 8 0a8 8 0 0 0 0 16zm.93-9.412-1 4.705c-.07.34.029.533.304.533.194 0 .487-.07.686-.246l-.088.416c-.287.346-.92.598-1.465.598-.703 0-1.002-.422-.808-1.319l.738-3.468c.064-.293.006-.399-.287-.47l-.451-.081.082-.381 2.29-.287zM8 5.5a1 1 0 1 1 0-2 1 1 0 0 1 0 2z"/>
|
|
||||||
</symbol>
|
|
||||||
<symbol id="exclamation-triangle-fill" fill="currentColor" viewBox="0 0 16 16">
|
|
||||||
<path d="M8.982 1.566a1.13 1.13 0 0 0-1.96 0L.165 13.233c-.457.778.091 1.767.98 1.767h13.713c.889 0 1.438-.99.98-1.767L8.982 1.566zM8 5c.535 0 .954.462.9.995l-.35 3.507a.552.552 0 0 1-1.1 0L7.1 5.995A.905.905 0 0 1 8 5zm.002 6a1 1 0 1 1 0 2 1 1 0 0 1 0-2z"/>
|
|
||||||
</symbol>
|
|
||||||
</svg>
|
|
||||||
|
|
||||||
{{- partial "header.html" . -}}
|
|
||||||
{{- block "main" . }}{{- end }}
|
|
||||||
{{- partial "footer.html" . -}}
|
|
||||||
</body>
|
|
||||||
</html>
|
|
|
@ -1,53 +0,0 @@
|
||||||
{{ define "main" }}
|
|
||||||
<div class="container py-3 row">
|
|
||||||
<div class="container" style="width: 240px;">
|
|
||||||
<div class="p-3 col">
|
|
||||||
<ul class="nav nav-pills mb-auto collapse navbar-collapse" id="navbarSupportedContent">
|
|
||||||
{{ $currentPage := . }}
|
|
||||||
{{ range .Site.Menus.docs.ByWeight.Reverse }}
|
|
||||||
<li class="nav-item">
|
|
||||||
<a href="{{ .URL }}" class="nav-link">
|
|
||||||
<strong>{{ .Title }}</strong>
|
|
||||||
</a>
|
|
||||||
</li>
|
|
||||||
{{ if .Children }}
|
|
||||||
<ul style="list-style: none;">
|
|
||||||
{{ range .Children }}
|
|
||||||
<li class="nav-item">
|
|
||||||
<a href="{{ .URL }}" class="nav-link">
|
|
||||||
{{ .Title }}
|
|
||||||
</a>
|
|
||||||
</li>
|
|
||||||
{{ end }}
|
|
||||||
</ul>
|
|
||||||
{{ end }}
|
|
||||||
{{ end }}
|
|
||||||
</ul>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div class="p-3 col">
|
|
||||||
<div>
|
|
||||||
<h1>{{ .Title }}</h1>
|
|
||||||
<p><em>
|
|
||||||
{{ $date := .Date.UTC.Format "Jan 2, 2006" }}
|
|
||||||
{{ $lastmod := .Lastmod.UTC.Format "Jan 2, 2006" }}
|
|
||||||
{{ if and (ne $lastmod $date) (gt .Lastmod .Date) }}
|
|
||||||
Last updated {{ $lastmod }}<br>
|
|
||||||
{{ end }}
|
|
||||||
|
|
||||||
{{ if .Description }}
|
|
||||||
{{ .Description }}<br>
|
|
||||||
{{ end}}
|
|
||||||
</em></p>
|
|
||||||
{{.Content}}
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="footer mt-auto">
|
|
||||||
<p class="card-small text-muted">
|
|
||||||
Want to help improve this page? <a href="https://github.com/Rosettea/Hilbish/issues/new/choose">Create an issue.</a>
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
{{ end }}
|
|
||||||
|
|
|
@ -1,7 +0,0 @@
|
||||||
{{ define "main" }}
|
|
||||||
<main>
|
|
||||||
<div class="container mt-2">
|
|
||||||
{{.Content}}
|
|
||||||
</div>
|
|
||||||
</main>
|
|
||||||
{{ end }}
|
|
|
@ -1,8 +0,0 @@
|
||||||
{{ define "main" }}
|
|
||||||
<main>
|
|
||||||
<div class="container mt-2">
|
|
||||||
<h1>{{ .Title }}</h1>
|
|
||||||
{{.Content}}
|
|
||||||
</div>
|
|
||||||
</main>
|
|
||||||
{{ end }}
|
|
|
@ -1,6 +0,0 @@
|
||||||
{{ define "main" }}
|
|
||||||
<main style="max-width: 80em; margin: auto;">
|
|
||||||
{{.Content}}
|
|
||||||
</main>
|
|
||||||
{{ end }}
|
|
||||||
|
|
|
@ -1,32 +0,0 @@
|
||||||
<footer class="footer mt-auto mt-auto py-3 bg-light row">
|
|
||||||
<div class="col mb-3">
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="col mb-3">
|
|
||||||
<a href="/Hilbish" class="d-flex align-items-center mb-3 link-dark text-decoration-none">
|
|
||||||
<img src="/Hilbish/hilbish-flower.png" alt="" height="48" class="d-inline-block align-text-top">
|
|
||||||
</a>
|
|
||||||
<p class="text-muted">
|
|
||||||
Rosettea © 2022
|
|
||||||
<br>
|
|
||||||
Made with <i class="fa-solid fa-heart" style="color: #f6345b;"></i>
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="col mb-3"></div>
|
|
||||||
<div class="col mb-3"></div>
|
|
||||||
<div class="col mb-3"></div>
|
|
||||||
|
|
||||||
<div class="col mb-3">
|
|
||||||
<h5>Hilbish</h5>
|
|
||||||
<ul class="nav flex-column">
|
|
||||||
<li class="nav-item mb-2"><a href="/Hilbish" class="nav-link p-0 text-muted">Home</a></li>
|
|
||||||
<li class="nav-item mb-2"><a href="/Hilbish/docs/faq" class="nav-link p-0 text-muted">FAQ</a></li>
|
|
||||||
<li class="nav-item mb-2"><a href="https://github.com/Rosettea/Hilbish" class="nav-link p-0 text-muted">Source</a></li>
|
|
||||||
<li class="nav-item mb-2"><a href="https://github.com/Rosettea/Hilbish/releases" class="nav-link p-0 text-muted">Releases</a></li>
|
|
||||||
<li class="nav-item mb-2"><a href="/Hilbish/docs" class="nav-link p-0 text-muted">Documentation</a></li>
|
|
||||||
</ul>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="col mb-3"></div>
|
|
||||||
</footer>
|
|
|
@ -1,26 +0,0 @@
|
||||||
<head>
|
|
||||||
{{ $title := print .Title " — " .Site.Title }}
|
|
||||||
{{ if .IsHome }}{{ $title = .Site.Title }}{{ end }}
|
|
||||||
<title>{{ $title }}</title>
|
|
||||||
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8"/>
|
|
||||||
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1.0, user-scalable=no"/>
|
|
||||||
|
|
||||||
<meta name="theme-color" content="#ff89dd">
|
|
||||||
<meta content="/Hilbish/hilbish-flower.png" property="og:image" />
|
|
||||||
|
|
||||||
<meta property="og:site_name" content="Hilbish" />
|
|
||||||
<meta content="{{ $title }}" property="og:title" />
|
|
||||||
<meta content="{{if .Description}}{{ .Description }}{{ else }}{{ .Summary }}{{ end }}" property="og:description" />
|
|
||||||
<meta content="{{if .Description}}{{ .Description }}{{ else }}{{ .Summary }}{{ end }}" name="description" />
|
|
||||||
|
|
||||||
<meta name="revisit-after" content="2 days">
|
|
||||||
<meta name="keywords" content="Lua, Hilbish, Linux, Shell">
|
|
||||||
|
|
||||||
<meta property="og:locale" content="en_GB" />
|
|
||||||
<link rel="canonical" href="https://rosettea.github.io/Hilbish/" />
|
|
||||||
<meta property="og:url" content="https://rosettea.github.io/Hilbish/" />
|
|
||||||
|
|
||||||
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.2.0-beta1/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-0evHe/X+R7YkIZDRvuzKMRqM+OrBnVFBL6DOitfPri4tjfHxaWutUpFmBp4vmVor" crossorigin="anonymous">
|
|
||||||
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.2.0-beta1/dist/js/bootstrap.bundle.min.js" integrity="sha384-pprn3073KE6tl6bjs2QrFaJGz5/SUsLqktiwsUTF55Jfv3qYSDhgCecCxMW52nD2" crossorigin="anonymous"></script>
|
|
||||||
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.1.1/css/all.min.css" integrity="sha512-KfkfwYDsLkIlwQp6LFnl8zNdLGxu9YAA1QvwINks4PhcElQSvqcyVLLD9aMhXd13uQjoXtEKNosOWaZqXgel0g==" crossorigin="anonymous" referrerpolicy="no-referrer" />
|
|
||||||
</head>
|
|
|
@ -1,25 +0,0 @@
|
||||||
<header>
|
|
||||||
<nav class="navbar navbar-expand-md sticky-top bg-light">
|
|
||||||
<div class="container-fluid">
|
|
||||||
<a class="navbar-brand" href="/Hilbish">
|
|
||||||
<img src="/Hilbish/hilbish-flower.png" alt="" height="24" class="d-inline-block align-text-top">
|
|
||||||
Hilbish
|
|
||||||
</a>
|
|
||||||
<button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation">
|
|
||||||
<span class="navbar-toggler-icon"></span>
|
|
||||||
</button>
|
|
||||||
<div class="collapse navbar-collapse" id="navbarSupportedContent">
|
|
||||||
<ul class="navbar-nav me-auto mb-2 mb-lg-0">
|
|
||||||
{{ $currentPage := . }}
|
|
||||||
{{ range .Site.Menus.nav }}
|
|
||||||
<li class="nav-item">
|
|
||||||
<a href="{{ .URL }}" class="nav-link {{ if $currentPage.IsMenuCurrent "nav" . }}active{{ end }}">
|
|
||||||
{{ .Name }}
|
|
||||||
</a>
|
|
||||||
</li>
|
|
||||||
{{ end }}
|
|
||||||
</ul>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</nav>
|
|
||||||
</header>
|
|
|
@ -1,6 +0,0 @@
|
||||||
<div class="alert alert-warning d-flex align-items-center" role="alert">
|
|
||||||
<svg class="bi flex-shrink-0 me-2" width="24" height="24" role="img" aria-label="Warning:"><use xlink:href="#exclamation-triangle-fill"/></svg>
|
|
||||||
<div>
|
|
||||||
{{ .Get 0 }}
|
|
||||||
</div>
|
|
||||||
</div>
|
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue