• Stars
    star
    184
  • Rank 202,306 (Top 5 %)
  • Language
    Nim
  • License
    MIT License
  • Created over 5 years ago
  • Updated about 1 year ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

❄️ a nice and icy zsh and bash prompt in Nim

A nice and icy zsh and bash prompt in Nim

Build Status

scrot

Why?

I’ve always wanted to minimize my reliance on frameworks like oh-my-zsh, so I figured, why not write my own ZSH prompt in my new favourite language? Turned out to be a really fun exercise.

Highlights

  • Written in Nim 👑
  • Fast (in theory, since Nim compiles to C)
  • Pretty defaults.
  • Plugin-like system for prompt customization, in case you didn’t like the pretty defaults.
  • Support both zsh and bash.
  • Fun, I guess.

Installation

Note: It’s probably a good idea to uninstall oh-my-zsh, or any other plugin framework you’re using altogether. It may cause conflicts.

$ nimble install nicy

Don’t know what that is? New to Nim? Check out the Nim docs. nimble is packaged with Nim by default.

Quick start

Add this to your ~/.zshrc. If you installed via nimble, set PROMPT to $(~/.nimble/bin/nicy).

autoload -Uz add-zsh-hook
_nicy_prompt() {
	PROMPT=$("/path/to/nicy")
}
add-zsh-hook precmd _nicy_prompt

Make sure you disable all other themes.

Nicy supports BASH also, and you could simply add it to your ~/.bashrc or ~/.bash_profile:

function nicy_prompt_command {
    PS1=$(/path/to/nicy)
}
PROMPT_COMMAND="nicy_prompt_command"

Configuration

If you want to configure nicy as it is, you’ll have to edit the src/nicy.nim file and recompile. Messy, I know.

Build your own prompt

Alternatively, you can just as easily write your own prompt in Nim using nicy’s built-in API. Refer to the Examples section for some insight.

Once you’re done, compile it and add a similar function to your .zshrc as above, replacing PROMPT with the path to your own binary.

Examples

# ‘user@host $’ prompt

import nicy, strformat

let
  user = color(user(), green)
  host = color(host(), red)
  prompt = color("$ ", cyan)
  at = color("@", yellow)

echo fmt"{user}{at}{host} {prompt}"
# fish’s default prompt '~>'

import nicy, strformat

let
  prompt = color("> ", green)
  tilde = tilde(getCwd())

echo fmt"{tilde}{prompt}"
# pure by @sindresorhus (kinda)

import nicy, strformat

let
  prompt = color("", magenta)
  tilde = color(tilde(getCwd()), cyan)
  git = color(gitBranch() & gitStatus("*", ""), red)
  nl = "\n"

echo fmt"{tilde}{git}{nl}{prompt}"
# switching by return code

import nicy, strformat

let
  prompt = returnCondition(ok = "👍", ng = "👎") & " "
  tilde = color(tilde(getCwd()), cyan)
  git = color(gitBranch() & gitStatus("*", ""), red)
  nl = "\n"

echo fmt"{tilde}{git}{nl}{prompt}"
# ~ master
# 👍 

If you like to know more details about git status, you may want to try the following powerful example which is including the number of untracked, modified, staged, conflicted and the number of commits your local branch is ahead, behind, etc:

nim c -d:release examples/power.nim

API

zeroWidth(s: string): string
Returns the given string wrapped in zsh zero-width codes. Useful for prompt alignment and cursor positioning.
All procs below return strings wrapped by this.

foreground(s: string, color: Color): string
Returns the given string, colorized.
Possible colors are black, red, green, blue, cyan, yellow, magenta, white.

background(s, color: string): string
Returns the given string with its background colorized.
Same possible colors as above.

bold(s: string): string
Makes the given string bold.

underline(s: string): string
Adds an underline to the given string.

italics(s: string): string
Italicizes the given text. May not work in some terminal emulators!

reverse(s: string): string
Swaps the foreground/background colors for the given string.

reset(s: string): string
Resets all attributes. Useful for disabling all styling.

color*(s: string, fg, bg = Color.none, b, u, r = false): string
Convenience proc that sets all attributes to a given string.
fg: foreground, bg: background, b: bold, u: underline, r: reverse

horizontalRule(c: char): string
Returns a string of characters c, having the length of the current terminal width. Useful for positioning right-side prompts.

tilde(path: string): string
If path starts with /home/user, it is replaced by a ~/.

getCwd(): string
Returns the full path of the current working directory, or returns the string [not found] if current path doesn’t exist. (eg: rm -rf ../curpath)

virtualenv(): string
Returns the current virtualenv name if in one.

gitBranch(): string
Returns the current git branch, if in a git directory.

gitStatus(dirty, clean: string): string
Returns either dirty or clean if in a git repository. For example, return if clean and × if dirty.

user(): string
Returns the current username.

host(): string
Returns the current hostname.

returnCondition*(ok: string, ng: string, delimiter = "."): string
If the return code is 0 then returns ok string, otherwise ng.

returnCondition*(ok: proc(): string, ng: proc(): string, delimiter = "."): string
Returns result of ok proc or ng proc. If the return code is 0 then this proc calls ok proc, otherwise calls ng proc.

shellName*: string Contains the name of shell in which your prompt progoram is running. Currently it may be zsh or bash. You can specify it during compilation using the switch -d:zsh or -d:bash, or you can let the program detect it automatically, which may slow it down by a few milliseconds.

GitStats API

newGitStats*(): GitStats
Returns a GitStats object which contains the name of the local branch, the name of remote reference, number of commits your local branch is ahead or behind remote ref, number of untracked, modified, staged, conflicted, and the number of stashed changes.

branch*(gs: GitStats, detachedPrefix = "", postfix = " "): string
Returns the current git branch name.

status*(gs: GitStats, ahead, behind, untracked, changed, staged, conflicted, stash: string, separator, postfix = " "): string
Returns the git status string.

dirty*(gs: GitStats): bool
Returns whether the current directory has been changed.

Contributing

Bad code? New feature in mind? Open an issue. Better still, learn Nim and shoot a PR

License

MIT © Anirudh Oppiliappan

More Repositories

1

shlide

🖼️ a slide deck presentation tool written in pure bash
Shell
458
star
2

legit

web frontend for git, written in go
Go
187
star
3

dotfiles

system configurations using nix
Nix
165
star
4

repl

🐚 an instant REPL for any command
Shell
76
star
5

vite

🌀 a static site generator that Just Works™; powers https://icyphox.sh
HTML
59
star
6

icyrc

#️⃣ a no bs irc client
C
54
star
7

fab

🌟 print fabulously in your terminal
Nim
49
star
8

ferricy

a 34-key split keyboard based on the Ferris Sweep
48
star
9

mdium

📄 publish your markdown to Medium, from the CLI
Python
48
star
10

crap

🗑️ `rm` files without fear
Nim
33
star
11

site

my digital home
CSS
24
star
12

nanoid.nim

🆔 the Nim implementation of NanoID
Nim
24
star
13

go-vite

vite, but in Go; powers https://icyphox.sh
Go
22
star
14

pw

🔐 a mnml password manager
Shell
20
star
15

twsh

🐦 a twtxt client written in bash
Shell
12
star
16

asdf

💩 scrapped ideas and garbage code
JavaScript
12
star
17

kanbash

an opinionated kanban board written in bash
Shell
11
star
18

fsrv

filehost server for x.icyphox.sh
Go
10
star
19

openring.py

generate a webring from rss feeds
Python
10
star
20

mael

[WIP] an experimental mail client written in bash (and a bit of python)
Shell
9
star
21

mawkdown

a subset of markdown, written in awk
Awk
8
star
22

detotated

how much detotated wam do you need for a server? (it's an IRC bot, move on)
Python
6
star
23

clef

🔑 in-memory key-value store, written in Nim
Nim
5
star
24

base16-icy-scheme

🎨 a 16-bit colorscheme
5
star
25

janny

clean up Kubernetes resources after a set TTL
Python
5
star
26

nit

:octocat: a Git implementation in Nim
Nim
4
star
27

bin

oralé all my scripts an' shi
Shell
4
star
28

gitsocial-instance

👥 a federated and versioned social network
HTML
4
star
29

sup

⬆️ an scp based file upload tool
Nim
3
star
30

hugo-icydark-theme

✨ my version of the Hugo After-Dark theme
HTML
2
star
31

paprika

Go rewrite of Taigabot
Go
2
star
32

ferricy-zmk

zmk config for the ferricy split keyboard
2
star
33

python-tcp-flooder

This flooder is designed specifically to flood routers.
Python
2
star
34

r2wars-bots

r2wars bot attempts
Assembly
1
star
35

marko

🤖 a Twitter bot that tries to sound smart
Python
1
star
36

cyware19

Intro to RE — talk slides and other materials
C
1
star
37

goget

go-import meta tag server
Go
1
star
38

privychka

habit tracking service
Go
1
star
39

riskmanagement

📝 lecture notes from RITx Cybersecurity Risk Management (CYBER503x)
1
star
40

resume

📄 my résumé
TeX
1
star
41

filechat

Semester II Computer Science Project for CBSE Grade 12 (LOL, sounds like something a school would call it)
C++
1
star