színes bash kimenet

Fórumok

Sziasztok !

Egy Arch linux oldalon találtam egy egyszerű megoldást arra, hogy terminalon, színben el lehessen választani a különböző jogokkal felhasználókat. ( így ha az ember ránézz a képernyőre rögtön látja, hogy milyen jogosultsági szinten dolgozik )

Lehet hogy sokak számára nem jelent újdonságot, de talán lesznek olyanok akik jó hasznát veszik majd.

A példa kedvérét egy alap jogokkal rendelkező felhasználó home könyvtárában lévő .bashrc fájl végére felvettem az alábbi sorokat, ennek hatására a felhasználó nevét zöld színnel jelezi a rendszer, illetve kis eltéréssel a /root/.bashrc fájl végére is felvettem ugyanezeket a sorokat, aminek hatására (át "su"-zás után) a root felhasználó neve piros színben látszik a terminálon.

/home/'username'/.bashrc

txtblk='\e[0;30m' # Black - Regular
txtred='\e[0;31m' # Red
txtgrn='\e[0;32m' # Green
txtylw='\e[0;33m' # Yellow
txtblu='\e[0;34m' # Blue
txtpur='\e[0;35m' # Purple
txtcyn='\e[0;36m' # Cyan
txtwht='\e[0;37m' # White
bldblk='\e[1;30m' # Black - Bold
bldred='\e[1;31m' # Red
bldgrn='\e[1;32m' # Green
bldylw='\e[1;33m' # Yellow
bldblu='\e[1;34m' # Blue
bldpur='\e[1;35m' # Purple
bldcyn='\e[1;36m' # Cyan
bldwht='\e[1;37m' # White
unkblk='\e[4;30m' # Black - Underline
undred='\e[4;31m' # Red
undgrn='\e[4;32m' # Green
undylw='\e[4;33m' # Yellow
undblu='\e[4;34m' # Blue
undpur='\e[4;35m' # Purple
undcyn='\e[4;36m' # Cyan
undwht='\e[4;37m' # White
bakblk='\e[40m' # Black - Background
bakred='\e[41m' # Red
badgrn='\e[42m' # Green
bakylw='\e[43m' # Yellow
bakblu='\e[44m' # Blue
bakpur='\e[45m' # Purple
bakcyn='\e[46m' # Cyan
bakwht='\e[47m' # White
txtrst='\e[0m' # Text Reset

PS1='\[\e[0;32m\]\u\[\e[m\] \[\e[1;34m\]\w\[\e[m\] \[\e[1;32m\]\$\[\e[m\] \[\e[1;37m\]'

/root/.bashrc

txtblk='\e[0;30m' # Black - Regular
txtred='\e[0;31m' # Red
txtgrn='\e[0;32m' # Green
txtylw='\e[0;33m' # Yellow
txtblu='\e[0;34m' # Blue
txtpur='\e[0;35m' # Purple
txtcyn='\e[0;36m' # Cyan
txtwht='\e[0;37m' # White
bldblk='\e[1;30m' # Black - Bold
bldred='\e[1;31m' # Red
bldgrn='\e[1;32m' # Green
bldylw='\e[1;33m' # Yellow
bldblu='\e[1;34m' # Blue
bldpur='\e[1;35m' # Purple
bldcyn='\e[1;36m' # Cyan
bldwht='\e[1;37m' # White
unkblk='\e[4;30m' # Black - Underline
undred='\e[4;31m' # Red
undgrn='\e[4;32m' # Green
undylw='\e[4;33m' # Yellow
undblu='\e[4;34m' # Blue
undpur='\e[4;35m' # Purple
undcyn='\e[4;36m' # Cyan
undwht='\e[4;37m' # White
bakblk='\e[40m' # Black - Background
bakred='\e[41m' # Red
badgrn='\e[42m' # Green
bakylw='\e[43m' # Yellow
bakblu='\e[44m' # Blue
bakpur='\e[45m' # Purple
bakcyn='\e[46m' # Cyan
bakwht='\e[47m' # White
txtrst='\e[0m' # Text Reset

PS1='\[\e[0;31m\]\u\[\e[m\] \[\e[1;34m\]\w\[\e[m\] \[\e[0;31m\]\$ \[\e[m\]\[\e[0;37m\]'

Hozzászólások

if [ $(id -u) -eq 0 ]; then export PS1='rootvagybazeg# ' ; fi

Azt az egyet nem ertem, hogy ha mar definialsz mindenfele szines valtozot, akkor miert nem azokat hasznalod PS1-ben, hogy esetleg ertheto is legyen mi a fenet csinal?

Egyebkent alapbol legtobb helyen ugy nez ki a prompt, hogy usernek $ a vege, root-nak meg # - igy relative konnyen meg lehet kulonboztetni, hogy az ember most akkor root-e vagy se.

--
|8]

Sziasztok, az alábbi kódot találtam, de ez így elég olvashatatlan számomra, nagyjából értem, hogy hogyan működik. Annyival szeretném kiegészíteni, hogyha root ra váltok, akkor piros legyen az user\host
Szerintem be kellene tenni mégegy if ágat, if UUID == root, akkor színezzen, és ugyanígy írja ki a visszatérési értéket a kis ;-) \ ;-( jelekkel. Esetleg abban tudnátok segíteni, hogy hogyan nézne ki ez a kód szépen olvashatóan betördelve és hova tegyem és hogyan a root ra váltásra vonatkozó részt?

PS1="\[\033[01;37m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\];)\"; else echo \"\[\033[01;31m\];(\"; fi) $(if [[ ${EUID} == 0 ]]; then echo '\[\033[01;31m\]\h'; else echo '\[\033[01;32m\]\u@\h'; fi)\[\033[01;34m\] \w \$\[\033[00m\] "

-- Zoli

Kicsit játszottam a prompttal, s ebből nekem úgy tűnik, célszerűbb a PS1 értékét aposztrofok között megadni, mert egy kiértékelést mindenképpen ráereszt még a PS1 stringre. Szóval olyasmit csinál, mintha egy eval "$PS1" lenne.

Aposztrofok között például nem kell escape-elni a $ karaktert, s kicsit olvashatóbb az egész így.

Gondolom, vagy EUID-ot, vagy UID-ot akartál írni, az UUID más. Viszont amit kérdezel, már a kód része. Szerintem csak azért nem működik, mert amikor root leszel, akkor a /root/.bashrc-ből olvasott PS1 jut érvényre, s nem az, amit a felhasználód .bashrc-jében definiáltál.

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

Nálam így néz ki a root prompt:


PS1='\[\e[1;31m\][\u@\h \w]\$ \[\e[m\]'

Mivel áttetsző fekete terminált használok, a bold/világos piros jobban látszik.

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

Nekem így néznek ki a root shellek:

\[\033[01;31m\][\t] \u@\h:\w#\[\033[00m\]

A userek általában:

\[\033[01;36m\][\t]\[\033[00m\] \[\033[01;32m\]\u@\h\[\033[00m\]:\[\033[01;34m\]\w\[\033[00m\]>

A zöld szín pedig hostonként, vagy ügyfelenként változik, így szín és/vagy hostnév alapján azonnal látom, hogy hol vagyok.
--
The Community ENTerprise Operating System

Jól néznek ki, pl tetszik, hogy az egyik időt is mutat, ezt majd beépítem a sajátomba:-)
De a legjobban az tetszik, hogyha a mutatja, hogy sikeresen lefutott -e a parancs és zöldre vált vagy pirosra, ha sikertelen valamint még a visszatérési érték is megjelenik a legelején

-- Zoli

Szia Zoli!

Dobd ezt be a .bashrc-d végére:


####################################################
rcPrompt() {
   rc=$?
   if [ $rc -eq 0 ]
   then
	PS1="\e[0;33m\d \t \033[1;32m${rc} \e[0;31m\u\e[1;37m@\h:\e[0;32m\w\e[0;33m \e[0;37m\n"
   else
	PS1="\e[1;33;41m\d \t \033[1;37;40m ${rc} \e[1;31;41m \u\e[1;37;41m@\h:\e[1;32;41m\w\e[0;33m \e[0;37m\n"
   fi
}
PROMPT_COMMAND=rcPrompt
####################################################

Üdv,
vf

User: PS1='\[\e]0;\u@\h: \w\a\]\[\033[1;32m\][\t]\[\033[m\] \[\033[1;37m\]@\H \w\n\u \$ \[\033[m\] '
root: PS1='\[\e]0;\u@\h: \w\a\]\[\033[1;31m\][\t]\[\033[m\] \[\033[1;37m\] Host:\H \w\n\u\$ \[\033[m\] '

Ezek még nem túl vadak de lehet olyan bash prompt howtokat találni hogy a hajad égnek áll :)

===============================================================================
// Hocus Pocus, grab the focus
winSetFocus(...)

http://c2.com/cgi/wiki?FunnyThingsSeenInSourceCodeAndDocumentation

Adj ennek futás jogot egy xterm-be: ;)


#!/usr/bin/gawk -f
BEGIN	{
	for(i=0; i<=6; i++)
		{
		for(j=30; j<=37; j++)
			{
			for(k=40; k<=47; k++)
				{
				text	= sprintf(" %s;%s;%s ",i,j,k)
				BFormat = sprintf("\033[%s;%s;%sm",i,j,k)
				EFormat = sprintf("\033[0m")
				
				printf("%s%s%s",BFormat,text,EFormat)
				
				# print "Name: \033[1;31m" $2 "\033[0m" }
				}
			print
			}
		}
	printRED("\nVFeró!")
	printGREEN("\t\t\t\t\t\t\tdone\n\n")
	}

function printRED	(input) { printf "\033[1;31;40m" input "\033[0m" }
function printGREEN	(input) { printf "\033[1;32;40m" input "\033[0m" }

Üdv,
vf

Kedvet kaptam, most ezt csináltam:

PS1='\[\e[m\][`RET=$?; [ $RET -ne 0 ] && echo "\[\e[33;1m\]$RET\[\e[m\] "`\u@\h \w]\$ '

Alapból sima prompt, viszont ha az exit kód nem nulla, akkor sárgával beleírja az exit kódot. Fekete a terminálom, ezért sárga a szín.

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

Úgy látom, mindenki leragadt a hagyományos szűk színpalettánál, miközben már gyakorlatilag minden grafikus terminál 256 színt támogat (6x6x6-os RGB kocka, és 24 szürkeárnyalat a hagyományos színeken felül).

Példa:

if [ "$TERM" = "xterm-256color" ]; then
PS1=$'\[\e[38;5;166m\]#\[\e[38;5;167m\]#\[\e[38;5;168m\]#\[\e[38;5;169m\]#\[\e[38;5;170m\]#\[\e[38;5;171m\]#\[\e[0m\] '
fi

Eddig nem tudtam, miért van az, hogy az mc hol ismeri, hol meg nem a bold karaktereket. Most sem tudom, de már látom, hogy a 256 színhez van talán köze. :)

Ha így indítom:

xfce4-terminal -e mc

akkor bolddal írja a directory-kat, ha indítok egy xfce4-terminal-t, s abban induló shellnek mondom, hogy mc, akkor vékony betűkkel mutatja a könyvtárneveket.

Mindkét esetben a már futó mc-ből az alábbi választ kapom:

echo "$TERM"
xterm-256color

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

Amelyik vastag betűket is írt:

COLORTERM=xfce4-terminal
TERM=xterm

És amelyik nem:

TERM=xterm-256color
COLORTERM=xfce4-terminal

Miért indul más környezetben az mc, ha interaktív módon indítom, s miért másban, ha xfce4-terminal -e mc paranccsal?

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

Mert az előbbi esetben a terminál és az mc között még ott van egy shell amelyik végignyálazza a .bashrc-t, talán a .profile-t is. A második esetben ez nincs ott, a terminál közvetlenül az mc-t indítja.

Egyfelől a rendszer ahogy globálisan össze van rakva is hibás szerintem, mert a TERM értéket a terminálnak kell szolgáltatnia, nem a .bashrc-nek vagy hasonlónak kellene beállítani.

Másfelől az mc is valamelyest ludas abban hogy a kétféle term esetén másképpen néz ki.

Welcome to the beautiful world of Unix :)

Viszont, ha jól gondolom, a TERM változó értékének túl nagy jelentősége nincs, hiszen a terminál a változó értékétől függetlenül 256 színt tud. Az más kérdés, hogy a terminált használó alkalmazás éppen a TERM változó értéke alapján hiszi azt, hogy 16, vagy 256 színt tudó terminált kapott maga alá.

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

Így van. Viszont az mc történetesen más-más módon próbál fehér színt rajzolni a két esetben, és az xterm (16 szín) esetben ez a boldot is bekapcsolja, míg az xterm-256color esetben nem.

Úgy látom, az xfce4-terminálnak van opciója hogy mi legyen a TERM értéke, azt átírhatod 256 színűre, onnan kezdve egységes lesz a kétféle mc indítás, egyik sem lesz bold. Ha bold-ot akarsz, akkor az mc skin-t átdefiniálhatod (lásd a hivatkozott mc hibajegy), vagy a .bashrc-t hegesztheted ellenkező irányba hogy mindig TERM=xterm legyen (bár ezzel elesel annak a lehetőségétől hogy pár progiban, köztük az mc-be is rendes 256 színnel kezdj el játszadozni).

A régi 16 szín módban a fehér (és mind a 8 világos szín) "mellékhatása" a félkövérség. A 256 színes módban a félkövérség egy külön attribútum, melyet be tud billenteni az mc, csak a default skin esetén nem akarja. Ha berakod a bold szót a megfelelő helyekre a skinben akkor azok a dolgok félkövérek lesznek.

A linkelt hiba arról (is) szól, hogy mit lehetne-kellene tennie az mc-nek (ha egyáltalán bármit) annak érdekében, hogy ha 16 színű skin-t használ 256 színű módban, akkor esetleg magától találja ki hogy mely színeket kell félkövérítenie. Ott megtalálod a default skin átírt változatát ami direkt félkövéret kér a világos színekhez.

Pillanatnyilag úgy látom, hogy a mc-nek nincs opciója, amivel erőltetni lehetne a 256 színű módot; csak az számít, hogy a $TERM végén ott van-e a -256color (pl rxvt-256color, konsole-256color)

Nem a TERM értékének vége számít, hanem az hogy a TERM-hez tartozó terminál leíró fájl mit mond a színek számáról. Erőltetni azért nem lehet, mert ha nem lát ilyen leíró fájlt, akkor nem tudja hogy hogyan kell ezeket a színeket használni. Úgy tudod "erőltetni", hogy egy wrapperen át beállítod ilyenre a TERM-et.

Nekem picit bovebb a lista:

/usr/share/terminfo/E/Eterm-256color
/usr/share/terminfo/g/gnome-256color
/usr/share/terminfo/m/mrxvt-256color
/usr/share/terminfo/m/mlterm-256color
/usr/share/terminfo/p/putty-256color
/usr/share/terminfo/r/rxvt-unicode-256color
/usr/share/terminfo/r/rxvt-256color
/usr/share/terminfo/x/xterm-256color
/usr/share/terminfo/v/vte-256color
/usr/share/terminfo/s/screen-256color
/usr/share/terminfo/k/konsole-256color

--

Ki oda vagyik, hol szall a galamb, elszalasztja a kincset itt alant. 

Sziasztok,

Tudnátok egy kicsit segíteni, abban, hogy beállítottam az alábbi promptot, de valamilyen oknál fogva, root ként nem teszi elé a sárga hibakódot és a smile-t

#return value visualisation
PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\];)\"; else echo \"\[\033[01;31m\];(\"; fi) $(if [[ ${EUID} == 0 ]]; then echo '\[\033[01;31m\]\h'; else echo '\[\033[01;32m\]\u@\h'; fi)\[\033[01;34m\] \w \$\[\033[00m\] "

-- Zoli

A root egy másik felhasználó, így az nem fog arról tudni, ha valamelyik user .bashrc-jében megadtad ezt a PS1-et. Root-ként akkor lesz jó, ha a root .bashrc-jében definiálod. És persze az éppen futó shell már nem kapja meg az értéket, csak az újonnan indított.

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

Értem, köszi.

Tudnál segíteni abban, hogyan tudnám ezt a stringet teljesen levédeni? Nem lehet '' közé tenni, mert tartalmaz ilyen jeleket, nem tudom `` közé tenni, mert nem parancs végrehajtást szeretnék. A héjprogramozás könyvben azt írja a szerző, hogy teljes levédésnek minősül a '' jelek használata, de itt most tartalmaz maga a string ' jelet és még sok más, a bash számára értelmezhető jeleket.

http://pastebin.com/uRYzZmmi

-- Zoli

Eltűnt hogy milyen stringet akarsz megadni.

Az egyik általánosan használható módszer, hogy aposztrófok között bármilyen karakter megadható simán, az egyetlen kivétel maga az aposztróf. Ha olyat akarsz megadni, akkor becsukod a régit, backslashhel escape-elsz egyet, majd újat nyitsz. Például:

echo '!@#$%^&*()_[];\,./ it'\''s working'

Ez lenne a string:

# return value visalisation
PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\];)\"; else echo \"\[\033[01;31m\];(\"; fi) $(if [[ ${EUID} == 0 ]]; then echo '\[\033[01;31m\]\h'; else echo '\[\033[1;32m\]\u@\h'; fi)\[\033[01;34m\] \w \$\[\033[00m\] "

Próbáltam úgy, hogy minden egyes ' jel elé betettem a \ jelet, de nem működik:

echo '# return value visalisation
PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\];)\"; else echo \"\[\033[01;31m\];(\"; fi) $(if [[ ${EUID} == 0 ]]; then echo \'\[\033[01;31m\]\h\'; else echo \'\[\033[1;32m\]\u@\h\'; fi)\[\033[01;34m\] \w \$\[\033[00m\] "'

-- Zoli

Kezdjuk elolrol: mindent aposztrofok koze tegyel, kiveve, ha ott van egy $-jel. Amit vagy tenyleg $-jelkent akarsz kiirni, ekkor maradjon aposztrofok kozott, vagy ki akarod hasznalni a shell helyettesito lehetosegei valamelyiket:

- valtozo: $valtozo vagy ${valtozo}
- parancs: vagy $( parancs ) vagy regi formajaban ` parancs `
- kifejezes: $(( aritmetikai kifejezes )) (bash specifikus, nem-kompatibilis formaja: $[ aritmetikai kifejezes ] ).

Ezeket a vackokat pedig idezojelek koze tegyed.

Ennyi lenne csak:

#!/bin/bash

color_prompt=# return value visalisation
PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\];)\"; else echo \"\[\033[01;31m\];(\"; fi) $(if [[ ${EUID} == 0 ]]; then echo '\[\033[01;31m\]\h'; else echo '\[\033[1;32m\]\u@\h'; fi)\[\033[01;34m\] \w \$\[\033[00m\] "

sudo echo $color_prompt >>/root/.bashrc
echo $color_prompt >>/root/.bashrc

Ha beteszem minden ' elé a \ karaktert, akkor sem működik, pedig minden fórum, a Büki András könyv azt írja, hogyha ' ' karakterek közé teszünk egy sztringet, akkor az teljesen levédi a közötte lévő sztringeket. Nos ez nem így van, hiszen nem műkődik így, még mindig marad a bash számára értelmezhető karakter. Próbáld ki:

echo '# return value visalisation
PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\];)\"; else echo \"\[\033[01;31m\];(\"; fi) $(if [[ ${EUID} == 0 ]]; then echo \'\[\033[01;31m\]\h\'; else echo \'\[\033[1;32m\]\u@\h\'; fi)\[\033[01;34m\] \w \$\[\033[00m\] "'

És ha elkezdem betenni a többi karakter elé is, amire panaszkodik, akkor mindig jön egy újabb karakter, amit értelmez a bash. Először panaszkodott a fi-k re, betettem elé a \ karaktert, utána panaszkodott a ( jelekre, utána a ; -ra stb.

- Zoli

Nem érzek benne hibát. Egyszerűen hozzá szeretnék fűzni egy szöveget ahhoz a 2 fájlhoz, hogy nem kelljen kézzel szerkesztgetni, csak lefuttatnám ezt a scriptet és automatikusan hozzászúrná a végéhez. De úgy látszik, hogy nem lehet megoldani.

Itt van:

echo '# return value visalisation
PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\];)\"; else echo \"\[\033[01;31m\];(\"; fi) $(if [[ ${EUID} == 0 ]]; then echo \'\[\033[01;31m\]\h\'; else echo \'\[\033[1;32m\]\u@\h\'; fi)\[\033[01;34m\] \w \$\[\033[00m\] "'

Próbáld ki, nem fogja visszaadni ezt, amit szeretnék:

# return value visalisation
PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\];)\"; else echo \"\[\033[01;31m\];(\"; fi) $(if [[ ${EUID} == 0 ]]; then echo \'\[\033[01;31m\]\h\'; else echo \'\[\033[1;32m\]\u@\h\'; fi)\[\033[01;34m\] \w \$\[\033[00m\] "

Pedig át van léptetve minden egyes ' karakter, ami közben előfordul.

Egyszerű kérdés: miért nem működik ez kis script:

#!/bin/bash

color_prompt='# return value visalisation
PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\];)\"; else echo \"\[\033[01;31m\];(\"; fi) $(if [[ ${EUID} == 0 ]]; then echo \'\[\033[01\;31m\]\h\'\; \else \echo \'\[\033[1\;32m\]\u@\h\'\; \fi)\[\033[01\;34m\] \w \$\[\033[00m\] "'

sudo echo $color_prompt >>/root/.bashrc
echo $color_prompt >>/home/zoli/.bashrc

-- Zoli

Az mennyiben a mi hibánk, hogy nem olvasol dokumentációt?

#!/bin/bash

cat <<'EOF' >>.bashrc
# megjegyzés
PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\];)\"; else echo \"\[\033[01;31m\];(\"; fi) $(if [[ ${EUID} == 0 ]]; then echo '\[\033[01;31m\]\h'; else echo '\[\033[1;32m\]\u@\h'; fi)\[\033[01;34m\] \w \$\[\033[00m\] "
EOF
exit 0

Ilyeneket látok:

   Here Documents
       This type of redirection instructs the shell to  read  input  from  the
       current source until a line containing only delimiter (with no trailing
       blanks) is seen.  All of the lines read up to that point are then  used
       as the standard input for a command.

       The format of here-documents is:

              <<[-]word
                      here-document
              delimiter

       No  parameter expansion, command substitution, arithmetic expansion, or
       pathname expansion is performed on word.  If any characters in word are
       quoted,  the  delimiter is the result of quote removal on word, and the
       lines in the here-document are not expanded.  If word is unquoted,  all
       lines  of  the here-document are subjected to parameter expansion, com‐
       mand substitution, and arithmetic expansion.  In the latter  case,  the
       character  sequence  \<newline> is ignored, and \ must be used to quote
       the characters \, $, and `.

       If the redirection operator is <<-, then all leading tab characters are
       stripped  from  input  lines  and  the line containing delimiter.  This
       allows here-documents within shell scripts to be indented in a  natural
       fashion.

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

Tudod, mi a legviccesebb? Anélkül, hogy átnéztem volna a kódot, egy szövegfile-ba másoltam azt a hozzászólásodból, utána include-oltam a pont paranccsal, majd azonnal működött. Valamiért azt érzem, hogy keresed a hibát olyan valamiben, amiben nincs. Nekem az nem világos, hogy van az a hülyeség azzal a color_prompt-tal, utána van a PS1 definíciója, ez utóbbi jó, majd a hibás color_promt-ot hozzáfűzöd a .bashrc-hez, miközben a PS1-gyel nem kezdesz semmit. Nem értem, mit akarsz, de nem igazán jó, amit csinálsz, és nem ott van a hiba, ajol keresed. Arról nem is beszélve, hogy a .bashrc-hez hozzáfűzésben idézőjel nélkül hivatkozol a változóra, bár a konkrét esetben az idézőjel sem segítene.

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

"an az a hülyeség azzal a color_prompt-tal, utána van a PS1 definíciója, ez utóbbi jó, majd a hibás color_promt-ot hozzáfűzöd a .bas..."

Miért nem lehet ezt az egészet 1 stringnek kezelni? Minden könyv, forrás azt írja, hogyha 2 db ' közé teszek valamit, és közte átléptetem az előforduló ' jeleket, akkor abból olyan string lesz, amit nem fog értelmezni a bash. Nos ez nagyon nincs így ez látszik.

-- Zoli

Szeretném, ha kitennéd a <code></code> tag-et, ahova kell, mert így sokszor nagyon nehezen olvashatók a hozzászólásaid. Azért nem értettem, mit akarsz, mert már a kezdő aposztrofot nem vettem észre a # előtt.

Az a gyanúm, az echo-s változatban az volt a baj, hogy nem tetted idézőjelek közé a változódat. Abban sem vagyok biztos, hogy a

sudo echo "$valtozo" >>/root/.bashrc

jó, mert szerintem az echo ugyan root joggal fog futni, de a hozzáfűzést már ez a shell csinálja, neki meg nincs joga a /root-ba írni. Nem tudom amúgy, nem használok sudo-t.

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

> Minden könyv, forrás azt írja, hogyha 2 db ' közé teszek valamit, és közte átléptetem az előforduló ' jeleket, akkor abból olyan string lesz, amit nem fog értelmezni a bash. Nos ez nagyon nincs így ez látszik.

Ha talalsz olyan konyvet, vagy forrast, amelyik ezt egyben leirja, akkor azt a konyvet dobd a kukaba, azt a forrast felejtsd el, mert hulyeseget terjeszt.

(Meg szerencse, hogy kesobb kiderult, hogy ezt nem egy helyrol, hanem legalabb ket kulon helyrol szedted, igy mar legalabb az kiderult, hogy nem a Buki-konyv a szar, hanem amit valahonnan hozzaolvastal.)

Szerk: amit irtal, az az idezojelre majdnem igaz, de az aposztrofra nagyon nem.

Nem értem, hogy miért nem érted.

Ezt a szöveget szeretném hozzáfűni ahhoz a 2 fájl végéhez:

# return value visalisation
PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\];)\"; else echo \"\[\033[01;31m\];(\"; fi) $(if [[ ${EUID} == 0 ]]; then echo '\[\033[01;31m\]\h'; else echo '\[\033[1;32m\]\u@\h'; fi)\[\033[01;34m\] \w \$\[\033[00m\] "

Ez bonyolult az echo nak? Nem lehet? Minden internetes forrás, a Büki könyv leírja, hogy vándor, hogyha szeretnéd a stringedet levédeni, mert esetleg tartalmaz olyan karaktert, amit a shell értelmezni tud, akkor tedd be 2db ' jel közé és ha van közte ' jel, akkor azt \ karakterrel léptesd át. Na de ez nem működik a gyakorlatban egy ilyen hosszú stringnél. Hát megzavarja minden, zavarja a sortörés, zavarja az if, a $ jel, minden.

-- Zoli

Az aposztrofot nem tudod escape-elni, hacsak így nem:

echo $'ez itt egy aposztrof: \' és így tovább'

Viszont ezzel az lesz a baj, hogy értelmezni fogja a \t, \n, \x és hasonló szekvenciákat. A here document a barátod, mint írtam.

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

Tudom. Akkor ezek szerint mégsem igaz az amit a Büki könyvben ír a szerző a 8. oldal legtetején, idézem:
"Az egyszeres idézőjelek ('...') használata teljes elzárást jelent."

és az interneten hozzáolvasva kiderül, hogyha tartalmaz a string ' jeleket, akkor azokat escapelni kell. De még át kell ugrani egy rakás másik jelet is, mint pl a sorvége stb jeleket...

Egyébként megoldom másképp, elmentettem egy fájba(PS1) a stringet, és cat tal hozzáfűzöm ahhoz a 2 fájlhoz így:

sudo cat PS1 >>/home/zoli/.bashrc;cat PS1 >>/root/.bashrc

Talán ez a legegyszerűbb megoldás erre a kis semmiségre. Csak kezd tele lenni a hócipőm a különböző íráskkal, az ember a saját bőrén tapasztalja meg, hogy több a kivétel mint a szabály. Már rájöttem, hogy jobban járok, hogyha nem olvasgatom mások kódjait, csak a legritkább esetben, mert más gondolkodásmóddal írta úgyis, lehet, hogy rögösebb és nehezebb a saját utam, de legalább én írom magamnak, és nem más "hülyeségeit" próbálom a saját hülyeségeimmel összevetni. Azt is észrevettem, hogy sokszor fölöslegesen túlbonyolítanak egy adott feladatot a példákban különböző internetes forrásokban, a Büki András héjprogramozás könyvében meg aztán, amikor a szabályos kifejezéseket a telefonszámos példán keresztül szeretné megértetni az aztán a katasztrófa, még a maradék kedve is elmegy az olvasónak tőle. Arról szól az egész könyv, hogy a szerző mekkora kockafej, hogy tud minél bonyolultabban megoldani egy problémát. Az olvasó meg egyre hülyébnek érzi magát... Pedig a Szerző linuxvilágos cikkeiben van pár cikk, amik sokkal egyszerűbb példékat sorakoztat fel.
Viszonylag jól megtanultam a szabályos kifejezéseket - nem csak a Büki könyvéből és írásaiból, hanem sok helyről, de ehhez kell egy idő mire leülepszik, de akkor már ha ránézek pl egy menetrendre, már arról is az jut eszembe, hogyan lehetne regex el minél egyértelműbben leírni a megállókat...

-- Zoli

Ha jól emlékszem, több, mint 10 éve én is olvastam az általad említett könyvet. Messze nem teljes, de az alapok elsajátításához jó.

Az aposztrof tényleg teljes elzárást ad, éppen ezért nem értelmezi a shell olyankor a backslash-t sem, valamint nyilván önmagára, az aposztrofra nem lehet érvényes ez az elzárás, hiszen a második aposztrof lesz a string vége. Sor végét is elzárja, a kezdő és záró aposztrofnak nem muszáj ugyanabban a sorban lennie. Amúgy meg:

Advanced Bash-Scripting Guide

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

A Büki könyv jót ír, te csinálod rosszul.

Először is vedd észre, hogy nem ugyanaz a sima aposztrófok közé rakás, és az ha van egy dollár jel a nyitó aposztróf előtt. Félek hogy ez elkerülte a figyelmedet.

Ha nincs előtte dollár jel, akkor az aposztrófon belül tényleg semelyik karakternek nincs speciális jelentése, kizárólag az aposztrófnak (bezárja). Tehát ez:


echo '# return value visalisation
PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\];)\"; else echo \"\[\033[01;31m\];(\"; fi) $(if [[ ${EUID} == 0 ]]; then echo \'\[\

hibás pár karakterrel az előtt ahol levágtam az idézett szöveget, hiszen becsukod az aposztrófot és utána azon kívül folytatod. Korábbi hozzászólásomban bemutattam hogy hogyan kell csinálni: '\'' (az első becsukja, a következő kettőből egy literális aposztróf lesz, majd a negyedik újra kinyitja).

Nem értem miért bonyolítod túl feleslegesen a saját életedet (hacsaknem tanulási célból): miért lenne jobb plusz egy réteg escape-eléssel szívni hogy egy echo illessze a fájl végére, ahelyett hogy fognál egy szövegszerkesztőt és beírnád oda?

Ez egyszer lesz a literális "his\", ezt követi az "s", most jön egy szóköz, amely szeparálja a paramétereket. Ezután jön az echo második paramétere a "car", majd elkezdesz egy stringet, ami után newline-t mondasz, így a shell kiteszi a PS2 promptot, ez többnyire a >, s várja, hogy az imént megkezdett stringedet bezárd egy aposztroffal.

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

Az aposztrofon belül nem néz semmit a shell, a backslash-t sem, így nem is tudod az aposztrofot escape-elni. Literális lesz a backslash-ed, majd az azt követő aposztrof bezárja a stringedet. Persze, azáltal, hogy rögtön utána folytatódik a string, konkatenálódik az "s", de ez utóbbinál a shell már érzékeny a speciális karakterekre.

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

Ha jót ír a Büki, akkor mutasd meg, hogy hogyan kell echo-zni ezt a stringet: Mutass egy teljes elzárást két db ' jellel:

# return value visalisation
PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\]\342\234\223\"; else echo \"\[\033[01;31m\]\342\234\227\"; fi) $(if [[ ${EUID} == 0 ]]; then echo '\[\033[01;31m\]\h'; else echo '\[\033[01;32m\]\u@\h'; fi)\[\033[01;34m\] \w \$\[\033[00m\] "

De ugyanígy nézzen ki a kimenete!:-)

-- Zoli

Bosszantasz már itt:

#!/bin/bash

echo '# return value visalisation
PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\]\342\234\223\"; else echo \"\[\033[01;31m\]\342\234\227\"; fi) $(if [[ ${EUID} == 0 ]]; then echo '"'"'\[\033[01;31m\]\h'"'"'; else echo '"'"'\[\033[01;32m\]\u@\h'"'"'; fi)\[\033[01;34m\] \w \$\[\033[00m\] "'
exit 0

tr '[:lower:]' '[:upper:]' <<<locsemege
LOCSEMEGE

Ha tippelhetek: szerintem azt érted félre, hogy a szimpla aposztrófok közti "teljes kizárást" úgy képzeled, hogy kívülről befelé halad a shell az emésztéssel, tehát a legelső és legutolsó aposztróf között kizár mindent. Nem. Balról jobbra halad, az első aposztróf megkezdi ezt a módot, a második (ami a sztringed kellős közepén van) pedig bezárja.

Az echo zavarja meg az aramkoreidet. Ne akarj igy echozni.

A kovetkezo kodreszletet tedd be a /etc/profile -ba, vagy ha a disztrod tamogatja, akkor az /etc/profile.d/ ala (nevsorrend van, igy valahova a vegere):


#!/bin/sh

function _rval() {
  if [ $1 -eq 0 ]; then
    echo "\[\033[01;32m\];)"
  else
    echo "\[\033[01;31m\];("
  fi
}

function _ucolor() {
  if [[ ${EUID} == 0 ]]; then 
    echo "\[\033[01;31m\]\h"
  else 
    echo "\[\033[01;32m\]\u@\h"
  fi
}

PS1="\[\033[01;33m\]$? $(_rval $?)) $(_ucolor) \[\033[01;34m\] \w \$\[\033[00m\] "

Kicsit kiszerveztem a dolgokat fuggvenyekbe, hogy jobban elkulonuljon es konnyebb legyen karbantartani/boviteni, valamint javitottam az escapelesi hibakat.
--

Ki oda vagyik, hol szall a galamb, elszalasztja a kincset itt alant. 

Miért akarsz a prompton belül if-ezni? Csak túlbonyolítasz mindent. Egyáltalán miért akarsz if-ezni? Root .bashrc-jébe egyik prompt definíció, user .bashrc-jébe másik és kész. Vagy ha mindenképp el kell ágaznod, akkor if root vagyok így definiálom a promptot, else úgy definiálom.

Nem bonyolítom túl, mivel nem is én írtam, hanem az arch linux támogatói oldaláról van ezt a srting, azok meg ugye nagyon értik ám a dolgukat! :-)

Itt a forrás, ha érdekel: https://wiki.archlinux.org/index.php/Color_Bash_Prompt#Return_value_vis…

Én csak besárgítottam a hibakód részét...

-- Zoli

Szerintem fekete háttéren ez nagyon vadul néz ki:-)

PS1="\[\033[01;33m\]\$? \$(if [[ \$? == 0 ]]; then echo \"\[\033[01;32m\]\342\234\223\"; else echo \"\[\033[01;31m\]\342\234\227\"; fi) $(if [[ ${EUID} == 0 ]]; then echo '\[\033[01;31m\]\h'; else echo '\[\033[01;32m\]\u@\h'; fi)\[\033[01;34m\] \w \$\[\033[00m\] "

-- Zoli

Ugyan nem teljesen kapcsolódik a témához, de a Solarized nevü alkalmazással szégyentelen módon szinezek mindent amit használok, és teljesen jó a különféle editorjaimban.

http://ethanschoonover.com/solarized

Z

Sziasztok,

Szerteném pirosra színezni a 3. sort is, de az tartalmaz egy változót, ha beteszem idézőjelek közé, akkor nem érzékeli a változót a bash. Biztosan van rá megoldás, tudnátok tippet adni ehhez?

echo -e "\e[31mFinding the interface...\e[0m"
iface=`ip a | grep global | awk '{print $7}'`
echo Interface has been found : $iface

Köszönöm előre is!

-- Zoli

A Mageiában létezik colorprompt rpm csomag. Még én küldtem be annak idején a Mandrivának. Sok változáson ment keresztül. Jelenleg így néz ki:

92user-color.sh a fájl neve mely az /etc/profile.d-ben van:

cat /etc/profile.d/92user-color.sh
# Colorize the bash prompt based on which user is currently logged in.

# 3x = letter color, 4x = background color, 1 = extra brightness
# x = 0:black 1:red 2:green 3:yellow/brown 4:dark blue 3:purple 6:light blue 7:white

if [ -n "$PS1" ]; then

# This line duplicated from /etc/bashrc
[ "$PS1" = "\\s-\\v\\\$ " ] && PS1="[\u@\h \W]\\$ "

# Prepare our reset escape seq
psclear=$'\e[0m'
psreset=$'\017\e[10;0m'
if [ "$TERM" = "linux" ]; then
psreset=$'\017\e[?0c\e[10;0m'
fi

# Pick our colors
colorregex="3[12]m"
color="32m"
if [ "$UID" = "0" ]; then
color="31m"
fi
pscolor=$'\e[1;'$color

# If we've already manipulated the prompt, remaniplate our color
if echo "$PS1" | grep -q -E "$colorregex" 2>/dev/null; then
export PS1="$(echo -n "$PS1" | sed "s/$colorregex/$color/")"
else
export PS1=$'\\['"$psreset$pscolor"$'\\]'"$PS1"$'\\['"$psreset"$'\\]'
fi
fi

Ez semmi mást nem tesz mint piros a prompt ha root vagy, illetve zöld ha user vagy.

A .bashrc az meg szinte üres:
cat ~/.bashrc
# .bashrc

# User specific aliases and functions

# Source global definitions
if [ -f /etc/bashrc ]; then
. /etc/bashrc
fi

A .bash_profile már általam kibővitve meg ilyen:
cat ~/.bash_profile
# .bash_profile

# Get the aliases and functions
if [ -f ~/.bashrc ]; then
. ~/.bashrc
fi

export HISTCONTROL=ignorespace:ignoreboth:erasedups
export HISTIGNORE="&:ls:[bf]g:exit:[ \t]*:mc"

# User specific environment and startup programs

PATH=$PATH:$HOME/bin

export PATH
unset USERNAME
export KMIX_PULSEAUDIO_DISABLE=1