ersetzen in einem Rückgabestring eines vorher ausgeführten Programms

O

o_kiki_o

Grünschnabel
Hallo liebe Shell Spezialisten!

Ich habe mich soeben erst hier angemeldet, da ich seit gestern abend an einem für mich großen Problem sitze und nun nicht mehr weiter komme und auch gar keine Lust mehr habe.

Folgendes habe ich vor:
- ich entpacke eine zuvor geladene Zip Datei
- ich speichere die enthaltene Rückgabe in einer Variable
- nun möchte ich den Rückgabe-String verändern (daran haberts elend)

Also folgendes ist in meinem Rückgabe String:
Code:
Archiv: meineZipDatei.zip
  inflate: datei1.txt
  inflate: datei2.txt
  inflate: datei3.txt

Natürlich sind in den meisten Zip-Dateien mehrere Dateien enthalten, ich möchte jedenfalls den String am liebsten in ein Array gewandelt haben, jedoch reicht auch ein String mit den Dateien als kommaseparierte Werte.

Ich stelle mir das ganze so vor:
1. erste Zeile löschen
2. alle Leerzeichen entfernen
3. "inflating:" löschen
4. alle Zeilenumbrüche durch ein Semikolon ersetzen
fertig

Ich habe mit sed und grep probiert, auch mit replace, aber alles brachte mich nicht zum Erfolg.
Ich habe es doch nichteinmal fertig gebracht, das Wort "Archiv" durch was anderes zu ersetzen, weshalb es auch zwecklos wäre, die vielen verschiedenen Test die ich unternommen habe, hier zu posten.

nachfolgenden Code habe ich (Anfang abgeschnitten)
in der Variable "RET" ist der oben beschriebene String enthalten.
Code:
# ZIP Datei auspacken
RET=`/usr/bin/unzip -j -o "${TempDATADIR}/${FILENAME}${ErwZIP}" -d "$TempDATADIR"`

# Ergebniss von unzip zurueckliefern (enthält die Dateinamen)
echo "$RET"

nun wäre es echt super, wenn mir jemand das ganze erklären könnte, denn auch sehr vieles und langes googlen, studieren von
http://www.schatenseite.de/uploads/media/shell.pdf
und
http://www.selflinux.org/selflinux/html/bash_basic.html
und http://www.linuxfibel.de/printversion/bashprog.htm
und
http://pegasus.rutgers.edu/~elflord/unix/bash-tute.html
sowie den man Pages der verschiedenen Befehle
hat mich kein Stück näher an das Ergebnis gebracht, denn ich bin absoluter Neuling in der Shell Programmierung.
 
Zuletzt bearbeitet:
Unschön aber es geht:

Code:
echo $RET | sed 's/^Archiv:\s.*\?\.zip\s//;s/inflate:\s//g;s/\s/,/g'
 
Hi,

mein Vorschlag wäre z. B.:

Code:
RET=$(/usr/bin/unzip -j -o "${TempDATADIR}/${FILENAME}${ErwZIP}" -d "$TempDATADIR" | grep inflating | awk '{print $2}' | sed 's/$/;/g')

Da die Ausgabe schön spaltenorientiert ist, bietet sich awk hier ganz gut an.
Es gibt aber auch viele andere Möglichkeiten, sich den Text zurechtzustutzen - bestimmt auch noch elegantere ;-P

Gruß Daniel
 
Zuletzt bearbeitet:
Unschön aber es geht:

Code:
echo $RET | sed 's/^Archiv:\s.*\?\.zip\s//;s/inflate:\s//g;s/\s/,/g'

oh das sieht gut aus, ich werds gleich mal probieren, aber kannste mir das vielleicht erklären?

ich wills doch auch verstehen
.
.
.
EDIT (autom. Beitragszusammenführung) :
.

zur Lösung von smg:

das funktioniert leider nicht, folgendes kommt raus:
Code:
Archive:,zipdatei.zip,inflating:,datei1.txt,inflating:,datei2.txt,inflating:,datei3.txt

zur Lösung von Fallout:

diese Lösung funktioniert einwandfrei
folgendes wird ausgegeben:
Code:
datei1.txt
datei2.txt
datei3.txt


So nun mangelt es mir nur noch an dem Verständnis für die Lösungswege.
 
Zuletzt bearbeitet:
Code:
#!/bin/bash

RET="Archiv: meineZipDatei.zip inflate: datei1.txt inflate: datei2.txt inflate: datei3.txt"

val=$(echo $RET | sed 's/^Archiv:\s.*\?\.zip\s//;s/inflate:\s//g;')

for x in $val; do
    result[$count]=$x
    count=$(( $count + 1))
    done

# Nun ist es in einem Bash Array gespeichert.
# verifizieren:

for element in ${result[*]}; do echo $element; done
Besser wäre es ohne grep:

RET=$(/usr/bin/unzip -j -o "${TempDATADIR}/${FILENAME}${ErwZIP}" -d "$TempDATADIR" | awk '/inflating/{print $2}' | sed 's/$/;/g')[/code]

Dann hast dus aber nur in einem String und nicht in einem Array.

Kombinationsvorschlag von Fallout und meinem Code:


Code:
#!/bin/bash

val=$(/usr/bin/unzip -j -o "${TempDATADIR}/${FILENAME}${ErwZIP}" -d "$TempDATADIR" | awk '/inflating/{print $2}' | sed 's/$/;/g')


for x in $val; do
    result[$count]=$x
    count=$(( $count + 1))
    done

# Nun ist es in einem Bash Array gespeichert.
# verifizieren:

for element in ${result[*]}; do echo $element; done
 
Zuletzt bearbeitet:
WICHTIG:
zu achten ist auf die Zeilenumbrüche im String:
Code:
Archiv: zipdate.zip
 Inflating.....
 
Bei dir sind Zeilenumbrüche da? Bei mir nicht. Hast du nen komisches Zip eventuell?
 
Bei dir sind Zeilenumbrüche da? Bei mir nicht. Hast du nen komisches Zip eventuell?

nee, nen ganz stink normales WinZip 9irgendwas

ahso du meinst das unzip, nee ich denke mal dass das ein ganz normales ist, ich benutze Suse 9.3
 
Zuletzt bearbeitet:
Strange, also hier klappt das tadellos, da mein unzip nämlich keine Zeilenumbrüche erzeugt.
 
also ich poste hier mal eben meinen ganzen Script, vielleicht nützt es ja auch einem anderen mal

Code:
#!/bin/bash
#
# Download an ZIP File and unpacking this, give return unpacked File-locations
#
#
# Optionen:
#
# -h = Hilfe
#
# -u arg = Angabe der Download URl (Argument
# -f arg = Angabe des neuen Dateinamens
# -b arg = Angabe des Speicherverzeichnis


# Globale Variablen
SCRIPTNAME=$(basename $0 .sh)
EXIT_SUCCESS=0
EXIT_FAILURE=1
EXIT_ERROR=2
EXIT_BUG=10


# Variablen für Optionsschalter hier mit Default-Werten vorbelegen
OPTFILE=""


# Funktion Benutzungshinweis
function usage {
    echo ""
    echo ""
    echo ""
    echo "Usage: $SCRIPTNAME [-h] [-u Donwload Uri ZIP File] [-f new File Name] [-b Base Url Homepage] "
    echo ""
    echo ""
    echo ""  >&2
    [[ $# -eq 1 ]] && exit $1 || exit $EXIT_FAILURE
}

# Argumente uebernehmen
while getopts ':u:f:b:h' OPTION ; do
    case $OPTION in
    u)  FILEURL="$OPTARG"
        ;;
    f)  FILENAME="$OPTARG"
        ;;
    b)  BASEDIR="$OPTARG"
        ;;
    h)  echo " Hilfe zum Programm "
        echo ""
        echo ""
        echo ""
        echo ""
        echo ""
        echo ""
        echo ""
        echo ""
        echo "" >&2
        usage $EXIT_SUCCESS
        ;;
    \?) echo "Unbekannte Option \"-$OPTARG\"." >&2
        usage $EXIT_ERROR
        ;;
    :)  echo "Option \"-$OPTARG\" benötigt ein Argument." >&2
        usage $EXIT_ERROR
        ;;
    *)  echo "ungültiger Aufruf - undefinierter Fehler" >&2
        usage $EXIT_BUG
        ;;
    esac
done


# ARG FILEURL pruefen
if [ -z $FILEURL ]
then
    usage $EXIT_ERROR
fi


# ARG FILENAME pruefen
if [ -z $FILENAME ]
then
    usage $EXIT_ERROR
fi


# ARG BASEURL pruefen
if [ -z $BASEDIR ]
then
    usage $EXIT_ERROR
fi


# BASEDIR pruefen
if ! test -d $BASEDIR
    then
        # anlegen
        mkdir $BASEDIR
        chmod 777 $BASEDIR
fi


# Pseudo ZIP File fuer WGET anlegen
if ! test -w "${BASEDIR}/${FILENAME}"
    then
        touch "${BASEDIR}/${FILENAME}"
fi


# Datei downloaden mit wget
RETA=$(/usr/bin/wget -q -O"${BASEDIR}/${FILENAME}" "${FILEURL}")


# ZIP Datei auspacken | grep und awk -> alle Dateinamen mit Pfad angegeben, je Zeile einen Namen
RETB=$(/usr/bin/unzip -j -o "${BASEDIR}/${FILENAME}" -d "$BASEDIR" | grep inflating | awk '{print $2}')


# ZIP Datei loeschen
if test -r "${BASEDIR}/${FILENAME}"
    then
        rm -f "${BASEDIR}/${FILENAME}"
fi


# Ergebniss von unzip zurueckliefern (enthält die Dateinamen)
echo "$RETB"


exit $EXIT_SUCCESS

zu der Lösung von SMG:
also deine Lösung mit der Schleife gefällt mir auch sehr gut, allerdings bevorzuge ich mal die kürzere Variante von Fallout, da mir diese völlig ausreichend ist. Diese liefert mir jede einzelne Datei mit einem Umbruch getrennt.

Somit kann ich diese schön in php verarbeiten und die Dateien der Reihe nach einlesen.

Vielen Dank für die rege Mithilfe, auch wenn ich die Funktion von grep und awk noch nicht so ganz nachvollziehen kann.
 
Zuletzt bearbeitet:
*g* okay :)
also ich finds nur komisch, dass das bei dir newlines erzeugt, bei mir jedoch keine.
 
also lieber smg ich werde nun doch deine Variante benutzen, da sie mir sicherer erscheint.

Wenn nun auf anderen Maschinen das unzip auch alles in eine Zeile packt, sehe ich bei der Variante von Fallout alt aus, denn da hab ich ja nicht die Möglichkeit, die Trennzeichen (Semikolon) zusätzlich anzugeben.
Dann würden alle Dateinamen mit Pfad und ohne Trennzeichen hintereinander stehen, was natürlich nicht weiter zuverarbeiten wäre.
 

Ähnliche Themen

Zeilenweise suchen, löschen und ersetzen / Inhalt einfügen

[Tcl / Shell] Ändern einer Datei per vi - Änderungsdatum einer Datei erfassen

For Schleife in eine Variable(String) einlesen

HP PSC 2175 - CUPS druckt nicht

defektes Programm entfernen

Zurück
Oben