Werte an ein Shell Script übergeben

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
Kalli87
User
Beiträge: 281
Registriert: Montag 10. November 2014, 11:27

Neues Thema, neues Fragen, neues Problem

Mir wurde ein Shell Script vor die Nase gesetzt das alte und neue Daten zusammenfasst.
Ich soll nun eine GUI dazu programmieren. Die GUI is is ja nicht das Problem das hab ich schon bereits erledigt.
Mein Problem besteht eher darin das ich in der GUI Entry-Felder habe und wenn ich den Button "Zusammenfassen" klicke sollen die Werte die eingegeben wurden an das besagt Shell Script übergeben werden.

Wie soll das ganze funktionieren? Muss ich dazu das Skript in meiner GUI einlesen und dann die Werte dementsprechend übergeben? Oder wie soll das ganze passieren?

Danke
Sirius3
User
Beiträge: 17754
Registriert: Sonntag 21. Oktober 2012, 17:20

@Kalli87: das hängt halt davon ab, wie das Shellskript aussieht.
Kalli87
User
Beiträge: 281
Registriert: Montag 10. November 2014, 11:27

Ok hier das Script dazu.

Code: Alles auswählen

cd /home/david

echo "-----Programm zum Zusammenführen von Patienten-----"
echo " "
echo "Bitte geben Sie für das Protokoll Ihren Namen ein:"
read name;
echo " "
echo "Bitte geben Sie die ALTE Patientennummer ein:"
read altePat
QUELL_PATNU=$altePat
echo " "
echo "Bitte geben Sie die NEUE Patientennummer ein:"
read neuePat
ZIEL_PATNU=$neuePat
echo " "
echo "Wollen Sie die ALTE Patientennummer:" $altePat 
echo "mit der NEUEN Patientennummer:" $neuePat "Zusammenführen?"
echo "(Ja/Nein)"
read antw
echo " "

pf=`echo $QUELL_PATNU | awk '{printf("%06.f\n",$QUELL_PATNU)}'`
        e1=`echo $pf | awk '{printf("%03.f\n",substr($QUELL_PATNU,0,length($QUELL_PATNU)-3))}'`
        e2=`echo $pf | awk '{printf("%04.f\n",substr($QUELL_PATNU,0,length($QUELL_PATNU)-2))}'`
        e3=`echo $pf | awk '{printf("%06.f\n",substr($QUELL_PATNU,0,length($QUELL_PATNU)))}'`
        quell_pfad="$e1/$e2/$e3"


pf=`echo $ZIEL_PATNU | awk '{printf("%06.f\n",$ZIEL_PATNU)}'`
        e1=`echo $pf | awk '{printf("%03.f\n",substr($ZIEL_PATNU,0,length($ZIEL_PATNU)-3))}'`
        e2=`echo $pf | awk '{printf("%04.f\n",substr($ZIEL_PATNU,0,length($ZIEL_PATNU)-2))}'`
        e3=`echo $pf | awk '{printf("%06.f\n",substr($ZIEL_PATNU,0,length($ZIEL_PATNU)))}'`
        ziel_pfad="$e1/$e2/$e3"

serverpfad=/home/david/trpword/pat_nr/A

quell_fullpfad=$serverpfad/$quell_pfad/*
#echo $quell_fullpfad
ziel_fullpfad=$serverpfad/$ziel_pfad/
#echo $ziel_fullpfad

case $antw in
	Ja) echo "Sind Sie Sicher?";
 	    echo "(Ja/Nein)";
	    read antw2;
	    		case $antw2 in
				Ja) dvmerge $altePat $neuePat diffpat delpat;
				    cp -a $quell_fullpfad $ziel_fullpfad;
				    echo " "
				    echo "### Die Patienten wurden erfolgreich Zusammengeführt ###";
				    echo " "
				    echo "Programm wird beendet!";
				    sleep 5;
					;;

				Nein) echo "Das Programm wird aus Sicherheitesgründen beendet!";
				      sleep 3
				      exit;
					;;
			esac
	    ;;
	Nein) echo "Das Programm wird aus Sicherheitsgründen beendet!";
	      sleep 3
	      exit;
		;;
esac

LOGFILE=/tmp/Protokoll.log
heute=`date "+%d.%m.%y %H:%M Uhr"`

if [ ! -e $LOGFILE ]
	then
	echo "Protokoll" > $LOGFILE
fi
echo " " >> $LOGFILE
echo "Datum" $heute >> $LOGFILE 
echo "alte Patientennummer:" $altePat >> $LOGFILE
echo "neue Patientennummer:" $neuePat >> $LOGFILE
echo "Ausgeführt von:" $name >> $LOGFILE

echo " "
read x
Sirius3
User
Beiträge: 17754
Registriert: Sonntag 21. Oktober 2012, 17:20

@Kalli87: Du mußt halt alle read-Aufrufe in Commandozeilen-Argumente umwandeln.

Obwohl, Du kannst das gesamte Skript wegwerfen, da es quasi nur aus einem Aufruf besteht "dvmerge $altePat $neuePat diffpat delpat;", den Du auch in Python direkt aufrufen kannst.
BlackJack

@Sirius3: Naja da ist noch ein ``cp`` und das Protokollieren der Aktion.

@Kalli87: Falls Du das Skript so in der Form verwenden musst, dann musst Du es aufrufen und die entsprechenden Daten die es erwartet in die Standardeingabe des Prozesses schreiben. Ansonsten würde ich auch eher wie Sirius3 die relevanten Teile des Skriptes in Python nachprogrammieren.

Da in jedem Fall ein externer Prozess gestartet werden muss: Das `subprocess`-Modul ist Dein Freund. (Und ``shell=True`` ist der Feind — nicht benutzen!)
Kalli87
User
Beiträge: 281
Registriert: Montag 10. November 2014, 11:27

@Sirius3: Ich hab überhaupt keine Ahnung davon, wie würde das denn aussehen?
Nachprogrammieren soll ich leider nix, das Script soll so wie es is aufgerufen werden, wenn Änderungen vorkommen sollen diese einfach nur im Script geändert werden, so wurde es mir gesagt.

@BlackJack: Wie würde das denn aussehen? Dieses mal brauch ich wirklich mehr Hilfe was das betrifft, da ich mit Shell-Scripte noch nie gearbeitet habe.
BlackJack

@Kalli87: Aus Sicht von `subprocess` ist das vollkommen egal in welcher Programmiersprache das Programm geschrieben wurde welches man damit startet. Du musst halt schauen welche Eingaben das Programm vom Benutzer verlangt, also entweder durch lesen und nachvollziehen des Shell-Skript-Quelltextes oder durch ausprobieren, oder eine Kombination von beidem, und das dann von Python aus starten und die erwarteten Informationen in einer umgeleitete Standardeingabe des externen Prozesses schreiben, so wie man die sonst als Antwort auf die Fragen vom Shell-Skript manuell an der Konsole eintippen würde. Also einfach mal nachvollziehen welche Angaben man für eine konkrete Zusammenführung eintippt, die in einer Zeichenkette im Python-Programm ablegen und dann schauen was man durch Platzhalter für Zeichenkettenformatierung ersetzen muss weil die Daten im allgemeinen Fall variabel sind und vom Anwender in der GUI eingegeben werden.
Kalli87
User
Beiträge: 281
Registriert: Montag 10. November 2014, 11:27

Hat einer nen Link für mich zu vernünftigen Lektüre?

Danke
BlackJack

@Kalli87: Wofür denn jetzt genau? Das `subprocess`-Modul ist dokumentiert und für Shell- bzw. Bash-Programmierung gibt es beispielsweise den Bash Beginner's Guide und den Bash Guide.
Sirius3
User
Beiträge: 17754
Registriert: Sonntag 21. Oktober 2012, 17:20

@Kalli87: ... obwohl wie schon gesagt das Skript irgendein Skript sein kann, da Du es ja anscheinend nicht verändern darfst, sondern Dich mit der bescheuerten TUI auseinandersetzen mußt. Kurz, die Zeilen, die Du im Terminal eintippst einfach per Subprocess-Communicate in die Standardeingabe füttern.
Kalli87
User
Beiträge: 281
Registriert: Montag 10. November 2014, 11:27

Sirius3 hat geschrieben:@Kalli87: ... obwohl wie schon gesagt das Skript irgendein Skript sein kann, da Du es ja anscheinend nicht verändern darfst, sondern Dich mit der bescheuerten TUI auseinandersetzen mußt. Kurz, die Zeilen, die Du im Terminal eintippst einfach per Subprocess-Communicate in die Standardeingabe füttern.
Genau das is das was ich umsetzen will, nur hab ich kein plan wie :D
Benutzeravatar
snafu
User
Beiträge: 6741
Registriert: Donnerstag 21. Februar 2008, 17:31
Wohnort: Gelsenkirchen

Kalli87 hat geschrieben:
Sirius3 hat geschrieben:Kurz, die Zeilen, die Du im Terminal eintippst einfach per Subprocess-Communicate in die Standardeingabe füttern.
Genau das is das was ich umsetzen will, nur hab ich kein plan wie :D
Na, das hat Sirius3 dir doch genau in dem Zitat verraten, unter das du die Frage gesetzt hast. Ich habe den wichtigen Satz sogar isoliert. :)

Jetzt musst du halt die Dokumentation von "subprocess" nehmen und dort suchen, was dieses "Communicate" wohl sein könnte und ob an der Stelle, wo es in der Doku auftaucht, etwas zur Standardeingabe ("stdin") zu lesen ist...
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

Wo genau liegt denn jetzt noch das Problem? Du kennst das Modul, welches Du benutzen solltest... leg doch einfach los!

Wenn die Kommunikation mit dem Shell-Script zu kompliziert ist, schreib Dir ein simples Dummy Script, welches zu Beginn schlicht nur etwas statisches ausgibt. Dann erweiterst Du es um das Auswerten von Eingaben... und dann hast Du das Handwerkszeug, das eigentliche Script anzusprechen!
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
Kalli87
User
Beiträge: 281
Registriert: Montag 10. November 2014, 11:27

Ihr sagt/schreibt das immer so leicht :D
Ich bin da so unwissend wie man nur sein kann, da wäre schön wenn man anhand eines Beispiels es sehen könnte wie das funktionieren würde.
Bin gerade auf dieser Seite unterwegs und mal gucken was ich daraus entnehmen kann ;)

@Hyperion: Das Problem is einfach das ich einfach zu blöd bin und ohne Beispiel hab ich meine Probleme es überhaupt zu verstehen und es umzusetzen.

Ich guck ja schon im Internet wo ich Beispiele finde die mir helfen es zu verstehen damit ich selbst dann anhand des Beispieles mir Gedanken machen kann um dann eine Lösung zu entwickeln.

Ps.:
Hier siehts auch gut aus
Sieht auch vernünftig aus
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

@Kalli87: Programmieren lernt man nur durch Üben und (gezieltes) Ausprobieren. Wie ich schon sagte, teste ``subprocess`` doch erst einmal mit einem simplen Shell-Script oder von mir aus auch einem Firefox-Aufruf o.ä.

Die Seite Python module of the week fand ich früher mal ganz nett.
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
Kalli87
User
Beiträge: 281
Registriert: Montag 10. November 2014, 11:27

@Hyperion: so ein Firefox Aufruf is ja gar nicht so schwer.

Code: Alles auswählen

import subprocess
subprocess.call(['firefox -new-tab www.google.de', '-1'], shell=True)
Mal aus Spaß probiert und es funktioniert, es wird auch ein neuer Tab mit Google aufgerufen.
Wenn ich statt Firefox mein Script eintrage wird es auch gestartet aber ab dann versteh ich nichts mehr was die Übergabe betrifft oder wie Parallel die GUI laufen soll.

Und Lektüre spricht mich auch nicht so richtig an, entweder is so veraltet das es mit Python 3.4 nicht funktioniert oder egal welchen Code ich teste von den Beispielen keiner geht.
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

``subprocess.call`` ist natürlich auch nicht der richtige Aufruf, wenn man mit dem Prozess noch *kommunizieren* will - aber dazu wurde Dir ja schon konkret die richtige Funktion genannt ;-)

Um die zu testen, bietet es sich evtl. an, nicht das vollständige Script zu nutzen, sondern ggf. nur bis *nach* der ersten Eingabe!
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
Kalli87
User
Beiträge: 281
Registriert: Montag 10. November 2014, 11:27

Ihr seit immer so gemein :D
Popen wäre die richtige Variante ich weiß später dann communicate verwenden soweit ich hab das schon geschnallt so is es ja nicht.
Sirius3
User
Beiträge: 17754
Registriert: Sonntag 21. Oktober 2012, 17:20

@Kalli87: wenn Du das schon "geschnallt" hast, warum zeigst Du dann einen falschen call-Aufruf?

So ist's richtig:

Code: Alles auswählen

import subprocess
subprocess.call(['firefox', '-new-tab', 'www.google.de', '-1'])
Kalli87
User
Beiträge: 281
Registriert: Montag 10. November 2014, 11:27

@Siruis3: Du weißt schon dass das "geschnallt" auf Popen und communicate bezogen war und nicht auf den call-Aufruf.

Aber egal rum zicken bringt uns nicht weiter, kann mir einer freundlicherweise erklären wie ich den eingegebenen Wert in einem Entry-Feld an das Script übergeben kann?
Sicherlich geht das wieder mit dem variablenamen.get() wie man sonst auch das eingegebene abfängt und weiter auswerten kann. Sicherlich stell ich mich gerade wieder zu dumm an um es zu sehen......
Antworten