Handwerkerrechung IPA-Bericht Ingrid Betschart **I{{IPA_Bericht_Betschart_Ingrid_html_45b542be23b0752c.jpg?206x88 }} PA-Bericht** **Inhaltsverzeichnis** **[[#_Toc207667|1.]]**[[#_Toc207667| ]]**[[#_Toc207667|Teil 1]]**[[#_Toc207667| 3]] **[[#_Toc207668|1.1]]**[[#_Toc207668| ]]**[[#_Toc207668|Aufgabenstellung]]**[[#_Toc207668| 3]] **[[#_Toc207669|1.2]]**[[#_Toc207669| ]]**[[#_Toc207669|Projektorganisation]]**[[#_Toc207669| 4]] **[[#_Toc207670|1.3]]**[[#_Toc207670| ]]**[[#_Toc207670|Vorkenntnisse]]**[[#_Toc207670| 4]] **[[#_Toc207671|1.4]]**[[#_Toc207671| ]]**[[#_Toc207671|Vorarbeiten]]**[[#_Toc207671| 4]] **[[#_Toc207672|1.5]]**[[#_Toc207672| ]]**[[#_Toc207672|Benutzte Firmenstandards]]**[[#_Toc207672| 4]] **[[#_Toc207673|1.6]]**[[#_Toc207673| ]]**[[#_Toc207673|Zeitplan]]**[[#_Toc207673| 5]] **[[#_Toc207674|1.7]]**[[#_Toc207674| ]]**[[#_Toc207674|Arbeitsprotokoll]]**[[#_Toc207674| 6]] **[[#_Toc207675|2.]]**[[#_Toc207675| ]]**[[#_Toc207675|Teil2]]**[[#_Toc207675| 12]] **[[#_Toc207676|2.1]]**[[#_Toc207676| ]]**[[#_Toc207676|Kurzfassung IPA-Bericht]]**[[#_Toc207676| 12]] **[[#_Toc207677|2.2]]**[[#_Toc207677| ]]**[[#_Toc207677|Randbedingungen des Gesamtprojekts]]**[[#_Toc207677| 12]] **[[#_Toc207678|2.3]]**[[#_Toc207678| ]]**[[#_Toc207678|Installationsanweisung der Entwicklungsumgebung]]**[[#_Toc207678| 13]] **[[#_Toc207679|2.3.1]]**[[#_Toc207679| ]]**[[#_Toc207679|xampp]]**[[#_Toc207679| 13]] **[[#_Toc207680|2.3.2]]**[[#_Toc207680| ]]**[[#_Toc207680|NetBeans]]**[[#_Toc207680| 13]] **[[#_Toc207681|2.3.3]]**[[#_Toc207681| ]]**[[#_Toc207681|FPDF]]**[[#_Toc207681| 14]] **[[#_Toc207682|2.4]]**[[#_Toc207682| ]]**[[#_Toc207682|Teilprojekt Logging]]**[[#_Toc207682| 14]] **[[#_Toc207683|2.4.1]]**[[#_Toc207683| ]]**[[#_Toc207683|Loggingvarianten]]**[[#_Toc207683| 15]] **[[#_Toc207684|2.4.2]]**[[#_Toc207684| ]]**[[#_Toc207684|Entscheidung für Log4php]]**[[#_Toc207684| 15]] **[[#_Toc207685|2.4.3]]**[[#_Toc207685| ]]**[[#_Toc207685|Tägliche Logdatei]]**[[#_Toc207685| 16]] **[[#_Toc207686|2.4.4]]**[[#_Toc207686| ]]**[[#_Toc207686|Verwaltung der Logdateien]]**[[#_Toc207686| 17]] **[[#_Toc207687|2.4.5]]**[[#_Toc207687| ]]**[[#_Toc207687|Anleitung zu Windows „Aufgabe planen“]]**[[#_Toc207687| 18]] **[[#_Toc207688|2.4.6]]**[[#_Toc207688| ]]**[[#_Toc207688|Test]]**[[#_Toc207688| 20]] **[[#_Toc207689|2.4.7]]**[[#_Toc207689| ]]**[[#_Toc207689|Reflexion Logging]]**[[#_Toc207689| 22]] **[[#_Toc207690|2.5]]**[[#_Toc207690| ]]**[[#_Toc207690|Teilprojekt Login]]**[[#_Toc207690| 22]] **[[#_Toc207691|2.5.1]]**[[#_Toc207691| ]]**[[#_Toc207691|Loginvarianten]]**[[#_Toc207691| 22]] **[[#_Toc207692|2.5.2]]**[[#_Toc207692| ]]**[[#_Toc207692|Sicherheitskonzept]]**[[#_Toc207692| 26]] **[[#_Toc207693|2.5.3]]**[[#_Toc207693| ]]**[[#_Toc207693|Anforderungen an das Login]]**[[#_Toc207693| 27]] **[[#_Toc207694|2.5.4]]**[[#_Toc207694| ]]**[[#_Toc207694|Datenbankanpassungen]]**[[#_Toc207694| 28]] **[[#_Toc207695|2.5.5]]**[[#_Toc207695| ]]**[[#_Toc207695|Benutzerverwaltung]]**[[#_Toc207695| 30]] **[[#_Toc207696|2.5.6]]**[[#_Toc207696| ]]**[[#_Toc207696|Benutzer einfügen]]**[[#_Toc207696| 30]] **[[#_Toc207697|2.5.7]]**[[#_Toc207697| ]]**[[#_Toc207697|Startseite]]**[[#_Toc207697| 30]] **[[#_Toc207698|2.5.8]]**[[#_Toc207698| ]]**[[#_Toc207698|Dateistruktur des Projekts]]**[[#_Toc207698| 31]] **[[#_Toc207699|2.5.9]]**[[#_Toc207699| ]]**[[#_Toc207699|Test]]**[[#_Toc207699| 32]] **[[#_Toc207700|2.5.10]]**[[#_Toc207700| ]]**[[#_Toc207700|Reflexion Login]]**[[#_Toc207700| 36]] **[[#_Toc207701|2.6]]**[[#_Toc207701| ]]**[[#_Toc207701|Schlusswort]]**[[#_Toc207701| 36]] **[[#_Toc207702|2.7]]**[[#_Toc207702| ]]**[[#_Toc207702|Quellenangaben]]**[[#_Toc207702| 36]] **[[#_Toc207703|2.7.1]]**[[#_Toc207703| ]]**[[#_Toc207703|Quellen aus Büchern]]**[[#_Toc207703| 36]] **[[#_Toc207704|2.7.2]]**[[#_Toc207704| ]]**[[#_Toc207704|Quellen aus dem Internet]]**[[#_Toc207704| 36]] **[[#_Toc207705|2.8]]**[[#_Toc207705| ]]**[[#_Toc207705|Abbildungsverzeichnis]]**[[#_Toc207705| 37]] **[[#_Toc207706|2.9]]**[[#_Toc207706| ]]**[[#_Toc207706|Tabellenverzeichnis]]**[[#_Toc207706| 37]] **[[#_Toc207707|2.10]]**[[#_Toc207707| ]]**[[#_Toc207707|Listings]]**[[#_Toc207707| 38]] **[[#_Toc207708|2.11]]**[[#_Toc207708| ]]**[[#_Toc207708|Glossar]]**[[#_Toc207708| 38]] **[[#_Toc207709|2.12]]**[[#_Toc207709| ]]**[[#_Toc207709|Anhang]]**[[#_Toc207709| 38]] **[[#_Toc207710|2.12.1]]**[[#_Toc207710| ]]**[[#_Toc207710|Benutzerhandbücher]]**[[#_Toc207710| 38]] **[[#_Toc207711|2.12.2]]**[[#_Toc207711| ]]**[[#_Toc207711|Sourcecode]]**[[#_Toc207711| 53]] \\ \\ ****====== 1. Teil 1 ====== ==== 1.1 Aufgabenstellung ==== Für die vorliegende Fakturierungssoftware soll eine Benutzerverwaltung erstellt werden. Damit soll es möglich sein, dass der einzelne Handwerker seine Rechnungen selbst erstellen und verwalten kann. Folgende Punkte sind zu beachten: Es sollen die üblichen Sicherheitsstandards für PHP-Anwendungen eingehalten werden (verschlüsselte Passwörter, kein Zugriff auf die Website ohne Login, sämtliche Texteingaben werden überprüft, allenfalls HTTPS Umgebung). Die Eingaben müssen plausibilisiert werden. Die Applikation soll gemäss einigen Anwendungsfällen getestet werden. Ein Logging soll es erlauben, Fehler nach der Produktivsetzung rasch zu ermitteln. Die Dokumentation umfasst ein knapp gefasstes Benutzerhandbuch und eine technische Dokumentation, die es einem Fachkollegen ermöglicht, direkt mit der Entwicklung der Software fortzufahren. Brauchbarkeit: Applikation kann ohne Änderungen verwendet werden oder mit wenigen Änderungen an eine spezielle Branche angepasst werden (Anpassungen an Formularen und Datenbank). Der Administrator kann Benutzer einfügen, ändern und löschen. Er hat auf alle Daten Zugriff. Der Benutzer (Handwerker) kann sich mit dem vom Administrator gesendeten Daten anmelden und sein Passwort ändern. Zudem kann er seine Firma einfügen. Zur Firma gehören Artikel, Kunden und Rechnungen. Datenbanken: Es kommt die relationale Datenbank MySQL zum Einsatz. Die Sql-Skripts werden per Phpmyadmin erzeugt. Während der IPA wird eine neue Tabelle für die Benutzer und die dazugehörigen Daten erstellt. Die bisherigen Tabellen werden von dieser neuen abhängig sein. Exception Handling: Fehler sollen in ein Logfile geschrieben werden und in der Produktiv-Version nicht für den Anwender ersichtlich sein. Die Logfiles werden täglich erzeugt. Alle voraussehbaren Fehler werden entweder durch If-Abfragen oder Try-Catch-Abfragen abgefangen und geloggt. Sicherheit: Es ist unmöglich, ohne Login auf die Unterseiten der Applikation zuzugreifen. Der Benutzer muss sich zuerst anmelden und kann erst dann auf die Unterseiten navigieren. Direkt über die URL soll es nicht möglich sein auf eine Seite zuzugreifen. Eingabefelder in Formularen werden gefiltert, so dass die üblichen Angriffsmuster ausgeschlossen werden können. Passwörter werden nur verschlüsselt in Sessions oder Datenbanken gespeichert. Überlegungen zur Sicherheit der Applikation werden angestellt. ==== 1.2 Projektorganisation ==== Als Projektmanagement-Methode wurde IPERKA gewählt. Im Zeitplan wurde bei den Tätigkeiten in Klammern der entsprechende Buchstabe hinzugefügt. IPERKA wurde für die gesamte Arbeit als auch für das Logging und das Login angewendet. ==== 1.3 Vorkenntnisse ==== PHP: bei einigen Projekten gebraucht FPDF: bei den Vorarbeiten einmal gebraucht MariaDB: bei einigen Projekten gebraucht HTML: bei einigen Projekten gebraucht CSS: bei einigen Projekten gebraucht ==== 1.4 Vorarbeiten ==== Die Programme XAMPP (Apache und MariaDB) und NetBeans wurden installiert. Dokumentation des Projektes „Handwerkerrechnung“. Programmierung am Projekt „Handwerkerrechnung“ ohne Log und ohne das Benutzerlogin. ==== 1.5 Benutzte Firmenstandards ==== NetBeans als Entwicklungsumgebung Xampp als Laufzeitumgebung ==== 1.6Zeitplan ==== {{IPA_Bericht_Betschart_Ingrid_html_81b102d62d67e90f.gif|Form1}}Abb. 1: Zeitplan. (eigenes Bild). ==== 1.7 Arbeitsprotokoll ==== | **Tag 1 -- 29.03.2016** || | **Ausgeführte Arbeit** | **Notizen** | | Aufgabenstellung studieren | Projekt teilt sich in zwei Teilaufgaben auf, Logging und Login. | | Zeitplan erstellen | Die Arbeiten sind nach IPERKA aufgeteilt. | | Vorlage für den IPA-Bericht erstellen | Gemäss Dokument //FArbeit_2016.pdf.// | | Programme installieren | NetBeans und Xampp runtergeladen und installiert. | | Datenbank einrichten | In Phpmyadmin die Datenbank eingerichtet. | | Beispiele für Log anschauen, ausprobieren und dokumentieren | Funktion //Error_log// studiert. Log4php und Log5php im Internet gesucht und angeschaut. Log5php ist unvollständig und funktioniert nicht. | | Log Variante aussuchen | Entscheidung für Log4php. Besitzt im Vergleich zu Error_log Loglevels. | | **Bemerkungen** | Bei der Xampp Installation gab es Probleme, musste es ein zweites Mal eine andere Version installieren. Sonst wurden Tagesziele erreicht. Bin im Zeitplan. | | Tag 1.5 -- 30.03.2016 || | **Ausgeführte Arbeit** | **Notizen** | | Lo4php in mein Projekt einfügen | Im Projekt einige Loglevels (//info// und //fatal)// eingetragen und überall, wo nötig, log4php eingebunden. Log4php entrümpelt: Nur wirklich notwendige Dateien und Ordner ins Projekt kopiert. | | Testen ob log4php im Projekt nun richtig funktioniert. | Tests vorbereitet und durchgeführt. Nur zwei Fälle in ein Testfall-Formular im Bericht eingetragen. Nämlich, ob //info// geloggt wird und ob, wenn die Datenbank nicht funktioniert, //fatal// geloggt wird. Testfall für //Artikel einfügen// erstellt. Die andern Programme teste ich auf das Logging in //info// und | \\ | \\ | //fatal// durch. Das Formular für den Anwendungsfall fand ich im Buch zum Modul 326 (WISS), das Testformular habe ich selbst erstellt. | | Logdatei mit Datum | //config.xml// Datei abgeändert, dass sie die Datei mit dem Datum im Dateinamen abspeichert. | | **Bemerkungen** | Beispiele für Log4php sind gut und haben sofort funktioniert. Keine Probleme und Ziel erreicht. | | **Tag 2.5 -- 31.03.2016** || | **Ausgeführte Arbeit** | **Notizen** | | Einrichten, dass ältere Logdateien gelöscht werden. | Zum periodischen Löschen der Log-Dateien Batch-Datei erstellt und in Windows //Aufgabe planen// aufgerufen, so dass jeden Tag zur selben Zeit die Logdateien, die älter als zwei Tage sind, gelöscht werden. Anleitung zu //Aufgabe planen// erstellt. Anleitung für die Batch-Datei im Internet gefunden. Test durchgeführt. | | Login Varianten studieren | Beispiele zum Login im Internet gesucht. Wie könnte die Tabelle für die Benutzerdaten aussehen? Wie werden die eingegebenen Daten mit den Daten aus der Datenbank verglichen? | | **Bemerkungen** | Habe den Login-Vorgang und die Varianten noch nicht ganz verstanden. Ich schaue es morgen nochmal genauer an und dazu noch die Sicherheit, Verschlüsselung der Benutzerdaten. | | **Tag 3.5 -- 01.04.2016** || | **Ausgeführte Arbeit** | **Notizen** | | Erster Besuchstag | Wir (Experte, Fachvorgesetzter und ich) haben uns einander gegenseitig vorgestellt. Vom Experten habe ich noch Infos erhalten. | | Login Varianten anschauen | Nach Rücksprache mit Ausbildner Entscheid für die einfachste Login-Variante (MD5 Verschlüsselung, keine Funktion für vergessenes Passwort etc.). | \\ | Sicherheit | Zerstören einer Session und Cookie überschreiben. | | Darstellung | Mit dem Zeichnen der Darstellungen zum Loginvorgang begonnen. | | **Bemerkungen** | Was ich gestern angeschaut hatte, verstand ich heute nicht mehr. Ich habe zu starke Kopfschmerzen wegen des Föhnsturms. Nun hat der Ausbildner mit mir nur noch die einfachste Login-Variante angeschaut. | | **Tag 4.5 -- 04.04.2016** || | **Ausgeführte Arbeit** | **Notizen** | | Darstellung | Darstellungen von gestern fertiggestellt. Das eine ist ein Sequenzdiagramm, dazu habe ich mir nochmal eines angeschaut. Das andere ist eine Eigenkreation. | | Loginvariante und Sicherheit dokumentieren | Notiert, woher die Login-Variante kommt, Session und Verschlüsselung erklärt und warum diese Variante ausgewählt wurde. | | **Bemerkungen** | Hoffe die Darstellungen sind nicht nur für mich logisch. Dass ich mich für diese einfache LoginVariante entschieden habe, liegt zum Teil daran, dass ich immer noch Mühe habe wegen des Wetters und nicht mit den Arbeiten in Rückstand geraten will. Bin nicht zufrieden, weil ich nicht weitere Varianten anschauen konnte. | | Tag 5.5 -- 05.04.2016 || | **Ausgeführte Arbeit** | **Notizen** | | Datenbank umgestalten | Überlegt wie die Tabellenstruktur für die Datenbank inklusive Benutzer-Tabelle aussehen soll. Mit Phpmyadmin in der Datenbank //rg// eine neue Tabelle für die Benutzerdaten erstellt und die Beziehungen zu den bisherigen Tabellen festgelegt. ERD und eine Darstellung mit allen Spalten und deren Datentypen gezeichnet. | | **Bemerkungen** | Ich bin zufrieden obwohl ich es minimalistisch | \\ | \\ | bezüglich der neuen Tabellenspalten gemacht habe. | | **Tag 6 -- 06.04.2016** || | **Ausgeführte Arbeit** | **Notizen** | | Benutzer erstellen und Login programmieren | Um Benutzer zu speichern oder zu überprüfen, mit PHP, HTML und CSS Formulare und MariaDB-Datenbankzugriffe programmiert. | | **Bemerkungen** | Nicht alles genau gleich gemacht, wie im Beispiel. Zufrieden, Ziel erreicht. | | **Tag 7 -- 07.04.2016** || | **Ausgeführte Arbeit** | **Notizen** | | Loginseite und Benutzerverwaltung weiterprogrammieren | Die Seiten für die Benutzerverwaltung programmiert. Neue PHP/HTML-Dateien für das Menü erstellt. Sodass der Administrator und ein normaler Benutzer nicht auf dasselbe zugreifen können. | | Dateistruktur anpassen | Dateistruktur geändert und die unterschiedlichen Zugriffrechte von Administrator und normalen Benutzern erklärt. Darstellung für die Datenstruktur (Dateiname und Lage im Verzeichnis) erstellt: Welche Dateien wie zusammenhängen, wer wo Zugriff hat. | | Login Test | Testfälle vorbereitet und getestet. | | **Bemerkungen** | Die Seiten für die Benutzerverwaltung waren kein Problem. Ebenso die Anpassung der Dateistruktur. Testfälle haben nicht alle funktioniert, fand das Problem nicht. Ziel nicht erreicht. | | Tag 8 -- 08.04.2016 || | **Ausgeführte Arbeit** | **Notizen** | | Weiter testen | Alle Testfälle (3 zum Login, 3 zur Benutzereinfügung) durchgespielt. Der Testfall „Benutzer schon vorhanden“ funktionierte nicht richtig. Nun habe ich die Funktion, die testen | \\ | \\ | soll, ob der Benutzername schon in der Datenbank vorkommt, korrigiert. Nun funktioniert es richtig. Der Fehler lag am Datenbankzugriff. | | Überprüfen ob jemand ohne Login direkt über URL auf eine Unterseite zugreifen will | „benutzer_ueberpruefen.php“ programmiert. Dient als Include-Datei für jede Seite, die Passwortgeschützt sein soll. In dieser Datei wird überprüft, ob Benutzername und Passwort, die in der Session gespeichert sind (aus der Formulareingabe) mit Name und Passwort aus der Datenbank übereinstimmen. Es funktioniert alles korrekt. | | Zweiter Besuchstag | Der Experte hat noch mehr Infos gegeben. Vor allem zur Präsentation und zum Gespräch das noch sein wird. | | **Bemerkungen** | Der Experte hat bemängelt, dass der Informationsteil von IPERKA jeweils fehlt. Auch das Arbeitsprotokoll sei nicht nach den Vorgaben von den Bewertungskriterien. Ich muss noch Anwendungsfälle erstellen und den Bericht mehr strukturieren. | | **Zusatz 09.04.2016 ca. 30 min** | Arbeitsprotokoll verbessert. | | **Tag 9 -- 11.04.2016** || | **Ausgeführte Arbeit** | **Notizen** | | IPA-Bericht verbessern/ergänzen | Einige Ergänzungen durchgeführt. Reflexionen erstellt. | | Benutzerhandbuch schreiben | Zwei Benutzerhandbücher erstellt: Eines für den Administrator und eines für die normalen Benutzer. Einige Teile sind in beiden gleich. | | **Bemerkungen** | Ich wurde rechtzeitig fertig mit den Handbüchern. Der Bericht hat noch viele Fehler. | | **Tag 10 -- 12.04.2016** || | **Ausgeführte Arbeit** | **Notizen** | | Glossar | Erstellt | | Bericht korrigieren | Rechtschreibfehler korrigiert | | Arbeitsprotokoll umstrukturiert | Persönliche Bemerkungen ins Feld Bemerkungen verschoben. | | Als PDF auf PKOrg hochladen | | | **Bemerkungen** | Der Sourcecode des Projektes ist vollständig kommentiert. Einige Sourcecodes des Vorprojektes sind unvollständig kommentiert. | Tabelle 1: Arbeitsprotokoll. ====== 2. Teil2 ====== ==== 2.1 Kurzfassung IPA-Bericht ==== **Ausgangssituation** Das Vorprojekt wurde in PHP, HTML, CSS und MariaDB als Datenbank geschrieben. Programiertools für das Projekt sind NetBeans und Phpmyadmin. Im Vorprojekt kann man Rechnungen als PDF erstellen. Dazu wird das Tool FPDF verwendet, das es erlaubt, PDFs zu generieren. Das Projekt läuft lokal mit xampp. Es sollte dann aber einmal als Webapplikation auf einem externen Server laufen. Das Projekt ist dazu da, dass ein Handwerker seine Firma, Kunden und Artikel verwalten kann. Mit diesen Daten kann er nun einfach Rechnungen erstellen. Die Rechnung wird als PDF gespeichert. **Umsetzung** Logging: Beim Logging fiel der Entscheid auf Log4php. Log4php verfügt über Loglevels. So kann man es in der Testphase und nach der Produktivsetzung unterschiedlich einsetzen. Benutzerverwaltung: Der Us und das Passwort werden in ein HTML Formular eingegeben. In der MariaDB-Datenbank sind die internen Benutzerdaten gespeichert. Das Passwort in der Datenbank ist mit MD5 verschlüsselt, damit ein Administrator kein Passwort sieht. Das eingegebene Passwort wird verschlüsselt und dann wird der Username und das verschlüsselte Passwort mit denen aus der Datenbank verglichen. Die Zutrittsdaten werden ebenfalls in einer Session gespeichert. Mit den Sessiondaten kann man auf jeder Seite überprüfen, ob jemand, ohne sich anzumelden, auf die Seite zugreifen wollte und den Zugriff verweigern. **Ergebnis** Das Logging funktioniert. Es werden nun Fehler, wie z.B. eine misslungene Datenbankverbindung geloggt. Das Login funktioniert auch. Man kommt nicht direkt auf andere Seiten des Projektes. Diese werden gesperrt. Das Login wird überprüft. ==== 2.2 Randbedingungen des Gesamtprojekts ==== Das Projekt besteht aus zwei Teilprojekten, Logging und Login. Die Applikation läuft auf einer Umgebung der Unix-Familie mit einem Apache-Webserver. Dies entspricht einer günstigen Webhosting-Umgebung. Widows Webhosting ist in der Regel teurer, weil Lizenzkosten anfallen. Sollte zu einem späteren Zeitpunkt das Loginsystem auf Active-Directory von Windows zugreifen, müsste der Apache-Webserver mit einem IIS-Webserver (Microsoft Internet Information Services) ersetzt werden. ==== 2.3 Installationsanweisung der Entwicklungsumgebung ==== Es wird NetBeans als Entwicklungsumgebung und xampp als Laufzeitumgebung verwendet. == 2.3.1 xampp == Xampp installieren: Auf __[[http://apachefriends.org/de/index.html|http://apachefriends.org/de/index.html]]__kann man verschiedene Versionen herunterladen. Das Projekt verwendete die Version 5.6.19 für Windows. Nach dem Download muss man das Antivirenprogramm stoppen und kann die Installationsdatei ausführen. Xampp 5.6.19 enthält folgende Versionen von den Teilprogrammen: {{IPA_Bericht_Betschart_Ingrid_html_f0c9f6393d5073a4.jpg?268x359}}Abb. 2: Versionen von Xampp-Teilprogrammen. (eigenes Bild). == 2.3.2 NetBeans == NetBeans IDE installieren: Auf __[[https://netbeans.org/downloads/index.html|https://netbeans.org/downloads/index.html]]__kann man verschiedene Versionen herunterladen. Nach dem Download kann man die Installationsdatei ausführen. In meinem Fall ist es die Version 8.1. == 2.3.3 FPDF == Zur PDF Generierung wurde die FPDF Version 1.7 verwendet. ==== 2.4 Teilprojekt Logging ==== Logging wird in der Entwicklungsphase zum Testen und in der Produktivphase zur Fehleraufzeichnung benutzt. In der Aufgabenstellung steht, es werde zur Fehlerermittlung gebraucht. Use Case Diagramm (Anwendungsfalldiagramm) zum Logging: {{IPA_Bericht_Betschart_Ingrid_html_bb61d3be8965f092.png?448x301}}Abb. 3: Use Case Diagramm Logging. während der Entwicklungsphase (eigenes Bild). {{IPA_Bericht_Betschart_Ingrid_html_55e0a95ee6cc01f0.png?480x329}}Abb. 4: Use Case Diagramm Logging. während der Produktionsphase (eigenes Bild). == 2.4.1 Loggingvarianten == Für das Logging mit php gibt es verschiedene Varianten: **Eigenentwicklung:** Schreiben von Mitteilungen und Fehlern in eine Textdatei. **error_log:**Diese in php eingebaute Funktion schreibt Fehler in eine Logdatei. Es gibt aber keine Möglichkeit Loglevels zu verwenden. Beispiele zur Funktion error_log findet man auf __[[http://php.net/manual/de/function.error-log.php|http://php.net/manual/de/function.error]][[http://php.net/manual/de/function.error-log.php|-]][[http://php.net/manual/de/function.error-log.php|log.php]]__[[http://php.net/manual/de/function.error-log.php|.]] **log4php:**Damit gibt es Möglichkeiten zur Unterscheidung der Loglevels. Diese heissen trace, debug, info, warn, error und fatal. == 2.4.2 Entscheidung für Log4php == Nun habe ich mich nach Absprache mit meinem Fachvorgesetzten für Log4php entschieden, weil es die Levels gibt und eine Eigenentwicklung in der zur Verfügung stehenden Zeit nicht in Frage kommt. Log4php kann man von __[[https://logging.apache.org/log4php/download.html|https://logging.apache.org/log4php/download.html]]__herunterladen (zipVariante der Version 2.3.0). Auf __[[https://logging.apache.org/log4php/quickstart.html|https://logging.apache.org/log4php/quickstart.html]]__findet man Beispiele, wie log4php benutzt wird: logbeispiel.php trace("My first message."); %%//%% Not logged because TRACE < WARN $log->debug("My second message."); %%//%% Not logged because DEBUG < WARN $log->info("My third message."); %%//%% Not logged because INFO < WARN $log->warn("My fourth message."); %%//%% Logged because WARN >= WARN $log->error("My fifth message."); %%//%% Logged because ERROR >= WARN $log->fatal("My sixth message."); %%//%% Logged because FATAL >= WARN ?> config.xml Listing 1: php und config Datei von Log4php. Quelle : __[[https://logging.apache.org/log4php/quickstart.html|https://logging.apache.org/log4php/quickstart.html]]__ Nun ist das Beispiel in meinem Projekt eingebaut. In jeder Datei, wo etwas geloggt werden soll, ist nun log4php über folgende Codezeilen eingebunden. require 'log/log4php/Logger.php'; Logger::configure%%('%%log/config.xml'); $log = Logger::getLogger%%('%%myLogger'); Listing 2: php Code log einbinden, konfigurieren und starten Zeilen die etwas loggen sollen sind wie folgt geschrieben: $log->info("Hier steht der Text, der in die Logdatei geschrieben wird"); Listing 3: php Code um eine Info zu loggen == 2.4.3 Tägliche Logdatei == Damit die Logdatei nicht zu gross wird, kann man jeden Tag eine neue, mit dem Datum im Dateinamen, erzeugen lassen. Wie man das Datum in den Dateinamen bringt, sieht man auf folgender Seite. __[[https://logging.apache.org/log4php/docs/appenders/daily-file.html|https://logging.apache.org/log4php/docs/appenders/daily]][[https://logging.apache.org/log4php/docs/appenders/daily-file.html|-]][[https://logging.apache.org/log4php/docs/appenders/daily-file.html|file.html]]__[[https://logging.apache.org/log4php/docs/appenders/daily-file.html|.]] == 2.4.4 Verwaltung der Logdateien == Damit sich nicht zu viele Dateien im Logverzeichnis ansammeln, sollten diese automatisch gelöscht werden. Mithilfe einer Batch-Datei und dem Windows Aufgabenplaner kann man einrichten, dass ältere Logdateien automatisch gelöscht werden. Quelle: __[[https://znil.net/index.php?title=Windows:Dateien_die_%C3%A4lter_sind_als_X_Tage_per_Skript_/_Batch_I%C3&B6schen|https://znil.net/index.php?title=Windows:Dateien_die_%C3%A4lter_sind_als_X_Tage_per_Skript_/_]] [[https://znil.net/index.php?title=Windows:Dateien_die_%C3%A4lter_sind_als_X_Tage_per_Skript_/_Batch_I%C3&B6schen|Batch_I%C3&B6schen]]__ In meinem Projekt sieht die Batch-Datei nun so aus: forfiles /P "C:\xampp\htdocs\Handwerkerrechnung\log" /S /M *.log /D -2 /C "cmd /c del /q @path" Listing 4: Batch-Datei um Logdateien zu löschen Erklärungen der einzelnen Teile: /P "C:\xampp\htdocs\Handwerkerrechnung\log" Von hier aus wird die Suche gestartet /S Alle Unterordner /M *.log Suchmaske -- hier alle Dateien mit der Endung .log /D -2 Letztes Änderungsdatum älter als zwei Tage zum heutigen Datum /C "cmd /c del /q @path" Befehl //löschen//der mit diesen Dateien ausgeführt werden soll Die Datei kann nun über die Kommandozeile ausgeführt werden. Zuerst ins Verzeichnis wo diese Datei gespeichert ist gehen. cd C:\xampp\htdocs\Handwerkerrechnung\log Die Datei kann man einfach ausführen indem man nun den Dateinamen eingibt log_loeschen Nun wird die Datei ausgeführt. Besser ist es in Windows eine Aufgabe einzurichten. Damit kann man die Datei regelmässig z.B. täglich zur selben Zeit, ausführen lassen. ****== 2.4.5 Anleitung zu Windows „Aufgabe planen“ == Unter „Einstellungen“ im Suchfenster „Aufgaben“ eingeben „Aufgaben planen“ anklicken {{IPA_Bericht_Betschart_Ingrid_html_8666959db54fd8b9.jpg?432x243}}Abb. 5: Anleitung zum Aufgabenplaner von Windows. (eigenes Bild). Auf der rechten Seite „Aufgabe erstellen...“ anklicken {{IPA_Bericht_Betschart_Ingrid_html_da5c49e2ac3b4e40.jpg?432x330}}Abb. 6: Anleitung zum Aufgabenplaner von Windows. (eigenes Bild). Name eingeben und dann auf Register „Trigger“ klicken Im Register „Trigger“ auf die Schaltfläche „neu...“ klicken {{IPA_Bericht_Betschart_Ingrid_html_3f3149e98c70548.jpg?434x375}}Abb. 7: Anleitung zum Aufgabenplaner von Windows. (eigenes Bild). Hier kann man nun das Datum ab wann, die Uhrzeit und wie häufig die Aufgabe ausgeführt werden soll eingeben. Auf „OK“ klicken und dann weiter zum Register „Aktionen“. Hier auch wieder auf „neu...“ klicken. {{IPA_Bericht_Betschart_Ingrid_html_f6fbd8046a17ceec.jpg?340x376}}Abb. 8: Anleitung zum Aufgabenplaner von Windows. (eigenes Bild). Den Pfad des Programmes oder Skriptes, das ausgeführt werden soll eingeben oder auf „durchsuchen“ klicken um es zu suchen. Dann auf „OK“ klicken. Wenn alle Einstellungen gemacht sind auf „OK“ klicken == 2.4.6 Test == Randbedingungen für alle Tests: Testumgebung xampp (Apache Version 2.4.17, MariaDB Version 10.1.10, PHP Version 5.6.19) Drehbuch Anwendungsfall: Artikel einfügen | Anwendungsfall: | Artikel einfügen || | Ziel: | Ausgefülltes Formular wird abgeschickt und die Daten in der Datenbank gespeichert || | Kategorie: | Primär || | Vorbedingung: | Es müssen Daten ins Formular eingegeben worden sein. || | Nachbedingung Erfolg: | Daten sind in Datenbank gespeichert || | Nachbedingung Fehlschlag: | Fehler wurde in Logdatei eingetragen || | Akteure: | Benutzer || | Auslösendes Ereignis: | Artikeldaten eingegeben und Formular abgeschickt || | Beschreibung: | 1. | Benutzer füllt das Formular aus | | \\ | 2. | Er klickt auf speichern | | \\ | 3. | Wenn die Daten gültig sind werden sie nun in die Datenbank gespeichert. | | \\ | 4. | Wenn Datenbank nicht funktioniert, wird eine Fehlermeldung in die Logdatei geschrieben. | | Erweiterungen: | 1. | Neben Loglevel //fatal// auch //info// loggen. Damit man sieht, ob das Formular abgeschickt wurde. | Tabelle 2: Anwendungsfall Artikel einfügen. (Vorlage aus WISS Modul 326 S.227). Test: Artikel einfügen | Testfall Nummer: | 1 | | Voraussetzung: | ab Loglevel //info// wird geloggt | | Eingaben: | Artikelnummer: 5 Beschreibung: neuer Artikel Einheit: Stk Preis pro Einheit: 4.5 | | Erwartetes Ergebnis: | Die Info: „Formular in artikel_einfuegen.php abgesendet.“ Sollte in der Logdatei erscheinen. | | Tatsächliches Ergebnis: | INFO - Formular in artikel_einfuegen.php abgesendet. | Tabelle 3: Testfall 1 INFO loggen. Test: Artikel einfügen | Testfall Nummer: | 2 | | Voraussetzung: | ab Loglevel //info// wird geloggt, Datenbank ausgeschaltet | | Eingaben: | Artikelnummer: 5 Beschreibung: neuer Artikel Einheit: Stk Preis pro Einheit: 4.5 | | Erwartetes Ergebnis: | Die Info: „Formular in artikel_einfuegen.php abgesendet“ und die Fehlermeldung: „Verbindungsfehler : [Inhalt von mysqli connect error].“ Sollte in der Logdatei erscheinen. | | Tatsächliches Ergebnis: | INFO - Formular in artikel_einfuegen.php abgesendet. FATAL - Verbindungsfehler : Es konnte keine Verbindung hergestellt werden, da der Zielcomputer die Verbindung verweigerte. | Tabelle 4: Testfall 2 Ausfall der Datenbank. Die Tests sind gut verlaufen. Es wurde immer das Verlangte geloggt. == 2.4.7 Reflexion Logging == Mit der Teilarbeit Logging bin ich zufrieden. Ich kam gut vorwärts. Log4php ist sehr gut. Ich glaube, dass ich damit die beste Variante ausgesucht habe. Ich würde wohl nichts anders machen. ==== 2.5 Teilprojekt Login ==== Meine Aufgabe ist es ein Login einzurichten, damit man nicht einfach auf alle Seiten des Projektes zugreifen kann. Dazu braucht es eine Loginseite und auf jeder andern Seite eine Überprüfung, ob die Person eingeloggt ist. Die internen Benutzerdaten müssen auf irgendeine Art im System gespeichert sein, sei es in einer Datei, einer Datenbank oder einem Benutzerverwaltungssystem. Das intern gespeicherte Passwort muss verschlüsselt sein, damit der Systemadministrator das Passwort nicht lesen kann. Use Case Diagramm eines Logins: {{IPA_Bericht_Betschart_Ingrid_html_fb64b4fc6bae30c5.png?539x306}}Abb. 9: Use Case Diagramm Login. (eigenes Bild). == 2.5.1 Loginvarianten == Das Grundprinzip des Logins ist immer ähnlich. Unterschiede gibt es in folgenden Bereichen: * Art der Verschlüsselung des Passwortes * Mechanismen zur Anmeldung über das Internet (Mail mit Bestätigungslink)  Mechanismen zur Rücksetzung eines vergessenen Passwortes Die folgende Skizze zeigt, wie es sich für das Projekt verhält. {{IPA_Bericht_Betschart_Ingrid_html_7966b73e6db8d37f.gif|Form2}}Abb. 10: Darstellung des Login-Vorgangs. (eigenes Bild). Es wird ein PHP-Formular ausgefüllt und der (externe) Username und das Passwort werden Server geschickt, unverschlüsselt. Das Passwort wird verschlüsselt und Username und Passwort werden mit Username und Passwort aus der Datenbank verglichen. Die extern eingegebenen Daten werden in eine Session gespeichert, damit sie global zur Verfügung stehen und für die Zugriffsverwaltung weiterer Seiten zur Verfügung stehen. Hier dasselbe nochmal als Sequenzdiagramm. {{IPA_Bericht_Betschart_Ingrid_html_fc6b0839f70fd794.jpg?358x516}}Abb. 11: Loginvorgang als Sequenzdiagramm. (eigenes Bild). Auf der Seite __[[http://www.php-kurs.info/tutorial-login_programmieren.html|http://www.php]][[http://www.php-kurs.info/tutorial-login_programmieren.html|-]][[http://www.php-kurs.info/tutorial-login_programmieren.html|kurs.info/tutorial]][[http://www.php-kurs.info/tutorial-login_programmieren.html|-]][[http://www.php-kurs.info/tutorial-login_programmieren.html|login_programmieren.html]]__gibt es ein einfaches Beispiel, wie man eine Login programmiert. Zuerst muss man eine Session starten. Mithilfe der Session kann man überprüfen, ob der Benutzer eingeloggt ist. Wenn er noch nicht eingeloggt ist, wird ihm ein Formular angezeigt. Wenn er es ausfüllt und abschickt, werden die eingegebenen Daten mit den Daten im Array verglichen. Im Beispiel sind die Daten im Array //$_logindaten//fest einprogrammiert. Im Projekt sollen dann die Benutzerdaten aus der Datenbank abgerufen werden und mit den eingegebenen Daten verglichen werden. Ist das Login erfolgreich wird es in der Session gespeichert. "admin", "passwort"=>"12345"); if (isset($_POST["loginname"]) && isset($_POST["loginpasswort"])) { if ($_logindaten["name"] == $_POST["loginname"] && $_logindaten["passwort"] == $_POST["loginpasswort"]) { # Userdaten korrekt - User ist eingeloggt # Login merken ! $_SESSION["login"] = 1; } } if ($_SESSION["login"] != 1) { include("login-formular.html"); exit; } # User ist eingeloggt ?> Listing 5: Login in php. Quelle: __[[http://www.php-kurs.info/tutorial-login_programmieren.html|http://www.php]][[http://www.php-kurs.info/tutorial-login_programmieren.html|-]][[http://www.php-kurs.info/tutorial-login_programmieren.html|kurs.info/tutorial]][[http://www.php-kurs.info/tutorial-login_programmieren.html|-]][[http://www.php-kurs.info/tutorial-login_programmieren.html|login_programmieren.html]]__ Auf folgender Seite gibt es noch zusätzliche Informationen zu Sessions.__[[http://www.php-kurs.info/tutorial-sessions_cookies.html|http://www.php]][[http://www.php-kurs.info/tutorial-sessions_cookies.html|kurs.info/tutorial]][[http://www.php-kurs.info/tutorial-sessions_cookies.html|-]][[http://www.php-kurs.info/tutorial-sessions_cookies.html|sessions_cookies.html]]__[[http://www.php-kurs.info/tutorial-sessions_cookies.html|.]] Sessions werden dazu gebraucht um Daten temporär zu speichern. Eine Session startet man mit session_start(). Diese ist ein Array und kann man mit Daten füllen. Ein Beispiel: $_SESSION[„Benutzer“] = „Ben“; $_SESSION[„Benutzer_Id“] = 1; Beim Logout kann man mit session_destroy()die Session zerstören. Das heisst: Daten die mit der aktuellen Session zusammenhängen werden gelöscht. Das Session-Cookie wird aber nicht gelöscht. Um den Benutzer also richtig auszuloggen muss man die Session-ID löschen. Um diese zu überschreiben gibt es auf folgender Seite Code __[[http://php.net/manual/de/function.session-destroy.php|http://php.net/manual/de/function.session]][[http://php.net/manual/de/function.session-destroy.php|destroy.php]]__[[http://php.net/manual/de/function.session-destroy.php|.]] == 2.5.2 Sicherheitskonzept == Es gibt diverse Gefährdungslagen für Webapplikationen. Nicht alle Gefährdungen lassen sich durch die Programmierung verhindern. Dazu gehören Distributed Denial of Service (DDOS) Attacken (Webserver wird mit Anfragen zahlreicher Clients bombardiert und zum Absturz gebracht), unbefugter Zugriff über das Webseitenmanagementsystem des Internetservice Providers, zum Beispiel wegen unbehobenen bekannten Sicherheitslücken (z.B. Parallels Plesk), Zugriff per FTP (mit unverschlüsseltem Passwort) oder durch Viren auf dem Server. Über die Programmierung lassen sich folgende Attacken verhindern: Cross-site scripting (XSS), Session Hijacking und SQL Injection Attacken können durch die Überprüfung von Eingabefeldern verhindert werden (Verhinderung des Einschleusens von JavaScript Code). Cross Site Forgery (CSRF) Attacken (Fälschung des Querystrings) können durch Filterung des QueryStrings verhindert werden. Im Programm werden sämtliche GET- und POST-Parameter gefiltert. == 2.5.3 Anforderungen an das Login == **Überprüfen ob jemand eingeloggt ist** Das Login wird eingerichtet, damit nicht jeder auf die Seiten Zugriff hat. Um Seiten zu schützen, muss man auf jeder dieser Seiten überprüfen, ob jemand mit gültigem Login darauf zugreifen will. Mithilfe der Daten aus der Session kann das für jede einzelne Seite überprüft werden. Wenn jemand also direkt den Pfad einer Seite eingibt, muss diese gesperrt sein. **Sicherheit der Benutzerdaten** Passwörter sollten nie unverschlüsselt in die Datenbank gespeichert werden. Sie sollten mindestens mit MD5 verschlüsselt werden. Das Passwort ist nur beim ersten Absenden des Loginformulars unverschlüsselt (sicherheitshalber müsste der Versand in einer https-Umgebung erfolgen). Sobald das Passwort in einer Session-Variable gespeichert wird, wird es verschlüsselt. Dann kann man den Vergleich mit den Daten aus der Datenbank erfolgen. In der folgenden Zeile wird der Inhalt der Variable $passwort mit MD5 verschlüsselt. $passwort = md5($passwort); Wie weiter oben schon erwähnt, ist das Grundprinzip des Loginvorgangs immer dasselbe. Es gibt aber unterschiedliche Varianten, wie die SQL-Befehle aussehen und wie die Daten verschlüsselt werden. Für dieses Projekt reicht es aus, das Passwort mit MD5 zu verschlüsseln. **Sicherheit der Formulare** Bei allen Eingabefeldern Cross-Site-Scripting (XSS) verhindern. Dazu kann man eine Funktion benutzen, die **<** und **>**Zeichen in **<**und **>**umwandelt. $var = htmlspecialchars($var); == 2.5.4 Datenbankanpassungen == Es braucht für die Benutzerdaten eine neue Tabelle. Im Vorprojekt gibt es eine Firmen-ID in der Tabelle Firma. Diese Firmen-ID kann im aktuellen Projekt der Benutzer-ID gleichgesetzt werden. Jeder Benutzer soll nämlich nur eine Firma eintragen und bearbeiten können. Wenn ein Benutzer gelöscht wird, sollen die dazugehörigen Firmen-, Kunden- und Artikeldaten auch gelöscht werden. Wird nur eine Firma gelöscht, soll der Benutzer bestehen bleiben, aber, wie schon im Vorprojekt, die dazugehörigen Kunden- und Artikeldaten gelöscht werden. Es muss also so sein, dass die Tabelle //Firma//von der Tabelle //Benutzer//abhängig ist. Die Tabellen //Kunde//und //Artikel//sind weiterhin von der Tabelle //Firma//abhängig. **ERD** {{IPA_Bericht_Betschart_Ingrid_html_b89b77db0be462ba.jpg?466x369}}Abb. 12: ERD der Datenbanktabellen. Das Vorprojekt wurde um die Tabelle //benutzer//erweitert. Die //firma_id//der Tabelle //firma//des Vorprojektes wurde der //benutzer_id//gleichgesetzt (eigenes Bild). **Datentypen der Spalten** | benutzer | \\ | | benutzer_id | Int PK | | i_benutzer | Varchar | | i_pw | Varchar | Tabelle 5: Spalten und deren Datentypen aus der Tabelle benutzer. | firma || | benutzer_id | Int FK | | firma | Varchar | | logo | Varchar | | branche | Varchar | | strasse | Varchar | | plz | Int | | ort | Varchar | | telefon | Varchar | | mobile | Varchar | | fax | Varchar | | email | Varchar | | homepage | Varchr | | mwst_nr | Varchar | | rg_nr | Int | | konto | Varchar | Tabelle 6: Spalten und deren Datentypen aus der Tabelle firma. | kunde | \\ | | kunden_id | Int PK | | kunden_nr | Int | | benutzer_id | Int FK | | anrede | Varchar | | nachname | Varchar | | vorname | Varchar | | strasse | Varchar | | plz | Int | | ort | Varchar | | telefon | Varchar | | mobile | Varchar | Tabelle 7: Spalten und deren Datentypen aus der Tabelle kunde. | artikel | \\ | | art_id | Int PK | | art_nr | Int | | benutzer_id | Int FK | | beschreibung | Text | | einheit | Varchar | | preis_p_e | Float | | menge | Int | Tabelle 8: Spalten und deren Datentypen aus der Tabelle artikel. == 2.5.5 Benutzerverwaltung == Es gibt einen Administrator. Dieser kann Benutzer einfügen, Passwörter von Benutzern ändern und Benutzer löschen. Er hat auch Zugriff auf alle Firmen und dazugehörige Daten (Artikel, Kunden und Rechnungen). Der Benutzer kann sich dann mit dem erhaltenen Namen und Passwort einloggen. Er kann das Passwort ändern, eine Firma einfügen, diese bearbeiten und dazugehörige Daten (Artikel, Kunden und Rechnungen) eintragen und bearbeiten. == 2.5.6 Benutzer einfügen == Um einen Benutzer zu erstellen muss der Administrator einen Benutzernamen eingeben und das Passwort zweimal. Dann wird überprüft, ob das Passwort beide Male dasselbe ist und ob es diesen Benutzer noch nicht gibt. == 2.5.7 Startseite == Auf der Startseite kann sich nun der Benutzer anmelden. Für den Administrator und den normalen Benutzer gibt es aber unterschiedliche Menüseiten. Das ist so, weil der Administrator auf alle Firmen zugreifen kann und der normale Benutzer nur auf seine eigene Firma. Für den Administrator wird die Indexdatei des Vorprojektes benutzt. Dort kann man aus einem Dropdown-Menü eine Firma auswählen bei der man etwas bearbeiten will. Der Administrator hat auch noch andere Unterseiten, die nur er benutzen kann. Die Unterschiede zwischen den Zugriffen die der Administrator hat und denjenigen, die der normale Benutzer hat, sind zu unterschiedlich, so dass man es nicht auf derselben Seite programmiert. Das wäre zu unübersichtlich. Auch für die Seite zur Verwaltung der Firmendaten wären die Unterschiede zu gross. Deshalb werden der Administrator und der normale Benutzer auf unterschiedliche Seiten geleitet. == 2.5.8 Dateistruktur des Projekts == {{IPA_Bericht_Betschart_Ingrid_html_270cd4859692c35.jpg?544x494}}Abb. 12: Darstellung der Dateistruktur des ganzen Projektes. (eigenes Bild). === 2.5.9 Test === Randbedingungen für alle Tests: Testumgebung xampp Version 5.6.19 (Apache Version 2.4.17, MariaDB Version 10.1.10, PHP Version 5.6.19) Drehbuch Anwendungsfall: Login | Anwendungsfall: | Login | | Ziel: | Der Benutzer ist eingeloggt und wird auf die richtige Seite weitergeleitet. | | Kategorie: | primär | | Vorbedingung: | Der Benutzer muss gültige Logindaten haben. | | Nachbedingung Erfolg: | Benutzer wird auf die richtige Seite weitergeleitet. | | Nachbedingung Fehlschlag: | Keine Weiterleitung und Fehlermeldung: Benutzername oder Passwort falsch | | Akteure: | Benutzer | | Auslösendes Ereignis: | Der Benutzer gibt die Daten ein. | | Beschreibung: | Der Benutzer gibt die Daten ins Formular ein Er klickt auf anmelden Die eingegebenen Daten werden gespeichert und mit den Benutzerdaten aus der Datenbank verglichen. Wenn die Daten miteinander übereinstimmen und der Benutzer der Administrator ist, wird er auf die Administrator-Menüseite weitergeleitet. Wenn die Daten miteinander übereinstimmen und es ein normaler Benutzer ist wird er auf die normale Menüseite weitergeleitet. Wenn die Daten nicht übereinstimmen, wird eine Fehlermeldung angezeigt. | Tabelle 9: Anwendungsfall Login. (Vorlage aus WISS Modul326 S.227). Test: Login | Testfall Nummer: | 1 | | Voraussetzung: | Benutzer in Datenbank vorhanden | | Eingaben: | Benutzername: admin Passwort: 123 | | Erwartetes Ergebnis: | Wird auf Administrator-Menüseite weitergeleitet | | Tatsächliches Ergebnis: | Wird auf Administrator-Menüseite weitergeleitet | Tabelle 10: Testfall 1 Login als Administrator. | Testfall Nummer: | 2 | | Voraussetzung: | Benutzer in Datenbank vorhanden | | Eingaben: | Benutzername: maurer Passwort: maurer | | Erwartetes Ergebnis: | Wird auf normale Menüseite weitergeleitet | | Tatsächliches Ergebnis: | Wird auf normale Menüseite weitergeleitet | Tabelle 11: Testfall 2 Login als normaler Benutzer. | Testfall Nummer: | 3 | | Voraussetzung: | Benutzer nicht in Datenbank vorhanden | | Eingaben: | Benutzername: abc Passwort: 123 | | Erwartetes Ergebnis: | Fehlermeldung: Benutzername oder Passwort falsch | | Tatsächliches Ergebnis: | Benutzername oder Passwort falsch | Tabelle 12: Testfall 3 Benutzer der nicht vorhanden ist. Anwendungsfall: Benutzer einfügen | Anwendungsfall: | Benutzer einfügen | | Ziel: | Der Administrator gibt Daten für einen neuen Benutzer ein. | | Kategorie: | primär | | Vorbedingung: | Der Administrator gibt die Daten ein | | Nachbedingung Erfolg: | Der neue Benutzer und das Passwort wurden in die Datenbank gespeichert. | | Nachbedingung Fehlschlag: | Daten werden nicht in die Datenbank gespeichert und Fehlermeldung | | Akteure: | Administrator | | Auslösendes Ereignis: | Der Administrator gibt die Daten ein. | | Beschreibung: | Der Administrator gibt die Daten ins Formular ein Er klickt auf speichern Die eingegebenen Daten werden gespeichert und mit den Benutzerdaten aus der Datenbank verglichen und ob zweimal dasselbe Passwort eingegeben wurde. Wenn es diesen Benutzernamen noch nicht gibt und zweimal dasselbe Passwort eingegeben wurde, werden die Daten in der Datenbank gespeichert. Wenn es diesen Benutzernamen schon gibt oder zweimal ein anderes Passwort eingegeben wurde oder ein Feld leer gelassen wurde wird eine Fehlermeldung angezeigt. | | Erweiterungen: | | Tabelle 13: Anwendungsfall Benutzer einfügen. (Vorlage aus WISS Modul 326 S.227). Test: Benutzer einfügen | Testfall Nummer: | 1 | | Voraussetzung: | Benutzername noch nicht vorhanden | | Eingaben: | Benutzername: abc Passwort: abc Passwort wiederholen: abc | | Erwartetes Ergebnis: | Der neue Benutzer und sein Passwort werden in die Datenbank gespeichert. | | Tatsächliches Ergebnis: | Benutzer wurde erstellt. | Tabelle 14: Testfall 1 neuer Benutzer. | Testfall Nummer: | 2 | | Voraussetzung: | Benutzer schon vorhanden | | Eingaben: | Benutzername: maurer Passwort: m2 Passwort wiederholen: m2 | | Erwartetes Ergebnis: | Die Daten werden nicht in die Datenbank gespeichert und es wird die Fehlermeldung: Benutzername maurer schon vorhanden | | Tatsächliches Ergebnis: | Benutzername maurer schon vorhanden | Tabelle 15: Testfall 2 Benutzer schon vorhanden. | Testfall Nummer: | 3 | | Voraussetzung: | | | Eingaben: | Benutzername: blabla Passwort: bla Passwort wiederholen: asdf | | Erwartetes Ergebnis: | Die Daten werden nicht in die Datenbank gespeichert und es wird die Fehlermeldung: Passwörter stimmen nicht überein | | Tatsächliches Ergebnis: | Passwörter stimmen nicht überein. | Tabelle 16: Testfall 3 unterschiedliche Passwörter. Beim Testen funktionierte „Benutzer schon vorhanden“ nicht. Der Benutzer wurde, obwohl es den Namen schon gab, gespeichert. Deshalb musste die Funktion, die das überprüft, nochmal geändert werden. Nun funktioniert alles richtig. === 2.5.10 Reflexion Login === Wegen der knappen Zeit konnte nur ein sehr einfaches Login programmiert werden. Mir ist bewusst, dass es weitaus komplexere Lösungen gibt. ===== 2.6 Schlusswort ===== Beim Logging war die Auswahl von möglichen Lösungen klein. Mit Log4php der Apache Foundation habe ich eine zuverlässige Softwarebibliothek gefunden, die einfach zu konfigurieren ist. Eine eigene Lösung zu programmieren hätte sich nicht gelohnt. Die Funktion error_log(), die Bestandteil von Php ist, hat einen wesentlich eingeschränkteren Funktionsumfang als Log4php. Beim Login gibt es eine grosse Anzahl von Varianten. Ich konnte in der zur Verfügung stehenden Zeit nur eine einfache Variante programmieren. Ich gestaltete die Dokumentation zu Beginn zu wenig strukturiert und musste im Nachhinein in der Doku herumflicken. Bei IPERKA liess ich das „I“ und manchmal auch das „P“ aus. Müsste ich die Arbeit nochmals beginnen, würde ich zuerst ein Inhaltsverzeichnis gemäss IPERKA erstellen und die Lücken nacheinander füllen. ===== 2.7 Quellenangaben ===== === 2.7.1 Quellen aus Büchern === Anwendungsfall WISS Modul Objektorientiert entwerfen und implementieren (326) === 2.7.2 Quellen aus dem Internet === __[[http://apachefriends.org/de/index.html|http://apachefriends.org/de/index.html]]__(29.03.2016)__[[https://netbeans.org/downloads/index.html|https://netbeans.org/downloads/index.html]]__(29.03.2016)__[[http://php.net/manual/de/function.error-log.php|http://php.net/manual/de/function.error]][[http://php.net/manual/de/function.error-log.php|-]][[http://php.net/manual/de/function.error-log.php|log.php]]__(29.03.2016)__[[https://logging.apache.org/log4php/download.html|https://logging.apache.org/log4php/download.html]]__(29.03.2016)__[[https://logging.apache.org/log4php/quickstart.html|https://logging.apache.org/log4php/quickstart.html]]__(29.03.2016) __[[https://logging.apache.org/log4php/docs/appenders/daily-file.html|https://logging.apache.org/log4php/docs/appenders/daily]][[https://logging.apache.org/log4php/docs/appenders/daily-file.html|-]][[https://logging.apache.org/log4php/docs/appenders/daily-file.html|file.html]]__(30.03.2016)__[[https://znil.net/index.php?title=Windows:Dateien_die_%C3%A4lter_sind_als_X_Tage_per_Skript_/_Batch_I%C3&B6schen|https://znil.net/index.php?title=Windows:Dateien_die_%C3%A4lter_sind_als_X_Tage_per_Skript_/_]] [[https://znil.net/index.php?title=Windows:Dateien_die_%C3%A4lter_sind_als_X_Tage_per_Skript_/_Batch_I%C3&B6schen|Batch_I%C3&B6schen]]__(31.03.2016) __[[http://www.php-kurs.info/tutorial-login_programmieren.html|http://www.php]][[http://www.php-kurs.info/tutorial-login_programmieren.html|-]][[http://www.php-kurs.info/tutorial-login_programmieren.html|kurs.info/tutorial]][[http://www.php-kurs.info/tutorial-login_programmieren.html|-]][[http://www.php-kurs.info/tutorial-login_programmieren.html|login_programmieren.html]]__(31.03.2016) __[[http://www.php-kurs.info/tutorial-sessions_cookies.html|http://www.php]][[http://www.php-kurs.info/tutorial-sessions_cookies.html|-]][[http://www.php-kurs.info/tutorial-sessions_cookies.html|kurs.info/tutorial]][[http://www.php-kurs.info/tutorial-sessions_cookies.html|-]][[http://www.php-kurs.info/tutorial-sessions_cookies.html|sessions_cookies.html]]__(04.04.2016) __[[http://php.net/manual/de/function.session-destroy.php|http://php.net/manual/de/function.session]][[http://php.net/manual/de/function.session-destroy.php|-]][[http://php.net/manual/de/function.session-destroy.php|destroy.php]]__[[http://php.net/manual/de/function.session-destroy.php|.]](04.04.2016) ===== 2.8 Abbildungsverzeichnis ===== Abb. 1: Zeitplan. (eigenes Bild). Abb. 2: Versionen von Xampp-Teilprogrammen. (eigenes Bild). Abb. 3: Use Case Diagramm Logging. während der Entwicklungsphase (eigenes Bild). Abb. 4: Use Case Diagramm Logging. während der Produktionsphase (eigenes Bild). Abb. 5: Anleitung zum Aufgabenplaner von Windows. (eigenes Bild). Abb. 6: Anleitung zum Aufgabenplaner von Windows. (eigenes Bild). Abb. 7: Anleitung zum Aufgabenplaner von Windows. (eigenes Bild). Abb. 8: Anleitung zum Aufgabenplaner von Windows. (eigenes Bild). Abb. 9: Use Case Diagramm Login. (eigenes Bild). Abb. 10: Darstellung was beim Login geschieht. (eigenes Bild). Abb. 11: Loginvorgang als Sequenzdiagramm. (eigenes Bild). Abb. 12: ERD der Datenbanktabellen. (eigenes Bild). Abb. 13: Darstellung der Dateistruktur des ganzen Projektes. (eigenes Bild). ===== 2.9 Tabellenverzeichnis ===== Tabelle 1: Arbeitsprotokoll. Tabelle 2: Anwendungsfall Artikel einfügen. (Vorlage aus WISS Modul326 S.227). Tabelle 3: Testfall 1 INFO loggen. Tabelle 4: Testfall 2 Ausfall der Datenbank. Tabelle 5: Spalten und deren Datentypen aus der Tabelle benutzer. Tabelle 6: Spalten und deren Datentypen aus der Tabelle firma. Tabelle 7: Spalten und deren Datentypen aus der Tabelle kunde. Tabelle 8: Spalten und deren Datentypen aus der Tabelle artikel. Tabelle 9: Anwendungsfall Login. (Vorlage aus WISS Modul326 S.227). Tabelle 10: Testfall 1 Login als Administrator. Tabelle 11: Testfall 2 Login als normaler Benutzer. Tabelle 12: Testfall 3 Benutzer der nicht vorhanden ist. Tabelle 13: Anwendungsfall Benutzer einfügen. (Vorlage aus WISS Modul326 S.227). Tabelle 14: Testfall 1 neuer Benutzer. Tabelle 15: Testfall 2 Benutzer schon vorhanden. Tabelle 16: Testfall 3 unterschiedliche Passwörter. ===== 2.10Listings ===== Listing 1: php und config Datei von Log4php. Listing 2: php Code log einbinden, konfigurieren und starten Listing 3: php Code um eine Info zu loggen Listing 4: Batch-Datei um Logdateien zu löschen Listing 5: Login in php. Quelle: [[http://www.php-kurs.info/tutorial-login_programmieren.html|http://www.php]][[http://www.php-kurs.info/tutorial-login_programmieren.html|-]][[http://www.php-kurs.info/tutorial-login_programmieren.html|kurs.info/tutorial]][[http://www.php-kurs.info/tutorial-login_programmieren.html|-]][[http://www.php-kurs.info/tutorial-login_programmieren.html|login_programmieren.html]] ===== 2.11Glossar ===== | CSRF | Cross-Site-Request-Forgery, Anfragenfälschung, Fälschung des Query-Strings | | FPDF | Opensource Library die es erlaubt, mithilfe von Php Pdf-Dateien zu erzeugen. | | https | HyperText Transfer Protocol Secure. Kommuikationsprotokoll um Daten abhörsicher zu übertragen. | | Log4php | Loggingtool der Apache Foundation. Erlaubt das Speichern von Informationen und Fehlern während der Laufzeit eines Programms. | | Logdatei | Textdatei mit Aufzeichnungen (Informationen, Fehler). | | Logging | Aufzeichnen von Meldungen in eine Logdatei. | | Login | Anmeldevorgang für ein Computersystem. | | MariaDB | Relationales Datenbanksystem. Löst MySQL in OpenSource Lösungen ab, weil MySQL im Besitz von Oracle ist. | | MD5 | Message Digest 5, ein Verschlüsselungsverfahren | | NetBeans | Entwicklungsumgebung für diverse Programmiersprachen. | | PHP | Serverseitige Skript-Sprache des Autors Rasmus Lerdorf, PHP ist eine Abkürzung von „Hypertext Preprocessor“ oder „Personal Home Page Tools“. | | PhpMyAdmin | Administrations-Interface für die Datenbanken MySQL oder MariaDB. | | Query-String | An die URL angehängte Variabelinformationen | | SQL Injection | Bösartiges Einfügen eines SQL-Befehls in ein Formularfeld | | XAMPP | Kombination des Webservers Apache, der Datenbank MariaDB und der Skriptsprache PHP. Erlaubt das Programmieren von Webseiten auf dem lokalen Rechner. | | XSS | Cross Site Scripting, illegales Einfügen von JavaScript-Code in Eingabefelder. | ===== 2.12Anhang ===== === 2.12.1 Benutzerhandbücher === {{IPA_Bericht_Betschart_Ingrid_html_e11ee165409bcb4a.gif |Form3}}Benutzerhandbuch für den Administrator Benutzerhandbuch Handwerkerrechung Ingrid Betschart RAFISA Inhalt __Startseite__................................................................................................................................................. 2 __Benutzer einfügen__................................................................................................................................... 3 __Benutzer verwalten__................................................................................................................................. 3 __Firmen verwalten__.................................................................................................................................... 4 __Firma auswählen__..................................................................................................................................... 5 __Kunden einfügen__..................................................................................................................................... 6 __Kunden verwalten__................................................................................................................................... 6 __Artikel einfügen__....................................................................................................................................... 7 __Artikel verwalten__..................................................................................................................................... 7 __Rechnung erstellen__.................................................................................................................................. 9 __Rechnungen verwalten__............................................................................................................................ 9 __Abmelden__.............................................................................................................................................. 10 Startseite Zuerst muss man sich anmelden {{IPA_Bericht_Betschart_Ingrid_html_e641978fd4ec9f14.jpg?299x228}}Wenn die Anmeldung erfolgreich ist, wird man auf die Menüseite weitergeleitet. {{IPA_Bericht_Betschart_Ingrid_html_565f3c25bfd781ec.jpg?414x378}}Benutzer einfügen {{IPA_Bericht_Betschart_Ingrid_html_bad2f36009c8968d.jpg?299x200}}Hier kann man einen neuen Benutzer erfassen. Das Passwort muss zweimal eingegeben werden. Benutzer verwalten Hier kann man einen der Benutzer auswählen indem man neben dem Namen des gewünschten Benutzers anklickt. Danach gibt es die Möglichkeiten den Benutzer zu bearbeiten oder zu löschen. {{IPA_Bericht_Betschart_Ingrid_html_79f18fbecd79f703.jpg?299x156}}Bei Benutzer bearbeiten erscheint folgendes Formular: {{IPA_Bericht_Betschart_Ingrid_html_c2310ea3b3b433e2.jpg?299x227}}Nun kann man für den Benutzer ein neues Passwort eingeben. Bei Benutzer löschen erscheint folgendes Formular: {{IPA_Bericht_Betschart_Ingrid_html_40111099ae39ea1b.jpg?257x195}}Wenn man auf „LÖSCHEN“ klickt wird der Benutzer gelöscht. Firmen verwalten Hier kann man eine der Firmen auswählen indem man neben dem Namen der gewünschten Firma anklickt. Danach gibt es die Möglichkeiten die Firma zu bearbeiten oder zu löschen. {{IPA_Bericht_Betschart_Ingrid_html_b712a7f110f266db.jpg?254x122}}Bei Firma bearbeiten erscheint folgendes Formular: {{IPA_Bericht_Betschart_Ingrid_html_7b986528c453ab1d.jpg?249x358}}Nun kann man die Firmendaten bearbeiten. Bei Firma löschen erscheint folgendes Formular: {{IPA_Bericht_Betschart_Ingrid_html_9bf45e018f0156c9.jpg?245x185}}Wenn man auf „LÖSCHEN“ klickt wird die Firma gelöscht. Firma auswählen Hier kann aus einem Dropdown-Menü eine Firma ausgewählt werden um Daten derer Kunden, Artikel und Rechnungen zu bearbeiten. Wenn eine Firma ausgewählt wurde sieht die Seite so aus: {{IPA_Bericht_Betschart_Ingrid_html_a0b651eb0759929a.jpg?411x344}}Kunden einfügen Auf der Menüseite muss zuerst eine Firma aus dem Dropdown-Menü ausgewählt werden. Hier kann man Kunden eintragen. Die Felder mit Stern sind Pflichtfelder. {{IPA_Bericht_Betschart_Ingrid_html_372219f7eb0a400e.jpg?242x241}}Kunden verwalten Auf der Menüseite muss zuerst eine Firma aus dem Dropdown-Menü ausgewählt werden. Hier kann man einen der Kunden auswählen indem man neben dem Namen des gewünschten Kunden anklickt. Danach gibt es die Möglichkeiten den Kunden zu bearbeiten oder zu löschen. {{IPA_Bericht_Betschart_Ingrid_html_25b57b89d51bbca5.jpg?241x112}}Bei Kunden bearbeiten erscheint folgendes Formular: {{IPA_Bericht_Betschart_Ingrid_html_8a336aa6cb169b63.jpg?242x273}}Nun kann man die Kundendaten bearbeiten. Bei Kunden löschen erscheint folgendes Formular: {{IPA_Bericht_Betschart_Ingrid_html_e561f276571e41c.jpg?299x229}}Wenn man auf „LÖSCHEN“ klickt wird der Kunde gelöscht. Artikel einfügen Auf der Menüseite muss zuerst eine Firma aus dem Dropdown-Menü ausgewählt werden. Hier kann man Artikel erfassen. Alle Felder sind Pflichtfelder. {{IPA_Bericht_Betschart_Ingrid_html_983bcda3e7f2b4d7.jpg?300x194}}Artikel verwalten Auf der Menüseite muss zuerst eine Firma aus dem Dropdown-Menü ausgewählt werden. Hier kann man einen der Artikel auswählen indem man neben der Nummer des gewünschten Artikels anklickt. Danach gibt es die Möglichkeiten den Artikel zu bearbeiten oder zu löschen. {{IPA_Bericht_Betschart_Ingrid_html_22c78e30df0bc00c.jpg?305x156}}Bei Artikel bearbeiten erscheint folgendes Formular: {{IPA_Bericht_Betschart_Ingrid_html_39448842e43776fb.jpg?303x251}}Nun kann man die Artikeldaten bearbeiten. Bei Artikel löschen erscheint folgendes Formular: {{IPA_Bericht_Betschart_Ingrid_html_d26a0adc515d2271.jpg?299x206}}Wenn man auf „LÖSCHEN“ klickt wird der Artikel gelöscht. Rechnung erstellen Auf der Menüseite muss zuerst eine Firma aus dem Dropdown-Menü ausgewählt werden. Bei „Neue Rechnung“ kommt man auf folgende Seite: {{IPA_Bericht_Betschart_Ingrid_html_2578398f66b1b9b.jpg?605x142}}Links kann man Artikel auswählen indem man auf klickt. Aus dem Dropdown-Menü kann man den Kunden auswählen. Hat man alles ausgewählt, was auf die Rechnung soll, muss man auf „zur Rechnung hinzufügen“ klicken. Dann erscheinen die Daten auf der rechten Seite. {{IPA_Bericht_Betschart_Ingrid_html_cbdb4508f051ae7.jpg?605x161}}Jetzt kann man auf der rechten Seite bei jedem Artikel bei „Menge“ noch die gewünschte Menge eintragen. Wenn nun alle Daten für die Rechnung stimmen, kann man auf „pdf“ klicken und es wird eine PDFDatei erstellt. In dieser ist alles schon mit Briefkopf, Artikelauflistung, Preisberechnungen und auf einer zusätzlichen Seite mit Einzahlungsschein, richtig formatiert. Rechnungen verwalten Auf der Menüseite muss zuerst eine Firma aus dem Dropdown-Menü ausgewählt werden. Hier kann man aus dem Dropdown-Menü eine Rechnung auswählen und auf „Rechnung anzeigen“ klicken um sich die PDF-Datei anzuschauen. {{IPA_Bericht_Betschart_Ingrid_html_236b049608e5f61e.jpg?294x127}}So sieht die Seite aus, wenn eine Rechnung ausgewählt wurde. {{IPA_Bericht_Betschart_Ingrid_html_b8e4a739d2378561.jpg?605x328}}Abmelden Um sich abzumelden muss man auf die Menüseite zurück und auf „abmelden“ klicken. Seite {{IPA_Bericht_Betschart_Ingrid_html_356ed7b15893f770.gif |Form4}}Benutzerhandbuch Handwerkerrechung Ingrid Betschart RAFISA Inhalt Startseite ................................................................................................................................................. 2 Passwort ändern ...................................................................................................................................... 2 Neue Firma erfassen................................................................................................................................ 3 Firmenlogo hochladen ............................................................................................................................. 3 Firma verwalten ...................................................................................................................................... 4 Kunden einfügen ..................................................................................................................................... 5 Kunden verwalten ................................................................................................................................... 5 Artikel einfügen ....................................................................................................................................... 6 Artikel verwalten ..................................................................................................................................... 6 Neue Rechnung ....................................................................................................................................... 7 Rechnungen verwalten ............................................................................................................................ 8 Abmelden ................................................................................................................................................ 8 Startseite Zuerst muss man sich anmelden {{IPA_Bericht_Betschart_Ingrid_html_e641978fd4ec9f14.jpg?299x228}}Wenn die Anmeldung erfolgreich ist, wird man auf die Menüseite weitergeleitet. {{IPA_Bericht_Betschart_Ingrid_html_bef52d03f74b8efd.jpg?413x308}}Zuerst sollte man das Passwort ändern. Passwort ändern {{IPA_Bericht_Betschart_Ingrid_html_69dd1d3a7bd3eab0.jpg?299x114}}Dann muss man „zurück“ um die Firmendaten erfassen zu können. Neue Firma erfassen Hier kann man die Firmendaten eintragen. Unter Firmenlogo hochladen kann man Logos hochladen, von denen man dann im Dropdown-Menü eines auswählen kann. Die Felder mit Stern sind Pflichtfelder. Wenn man eine Homepage eintragen will, muss man **http://www.**am Anfang****schreiben. {{IPA_Bericht_Betschart_Ingrid_html_34aebd76dd651b3a.jpg?298x379}}Firmenlogo hochladen Hier kann man über „Durchsuchen“ auf dem Computer ein Logo auswählen und es mit „Logo hochladen“ hochladen. {{IPA_Bericht_Betschart_Ingrid_html_cc460a619dedd883.jpg?299x75}}Wenn man schon eine Firma erfasst hat sieht die Menüseite so aus: {{IPA_Bericht_Betschart_Ingrid_html_a114b173dbc94a28.jpg?411x318}}Firma verwalten Hier ist dasselbe Formular wie bei „Neue Firma erfassen“. Aber die Daten die schon eingetragen wurden sind schon in den Formularfeldern eingefügt. {{IPA_Bericht_Betschart_Ingrid_html_673fde3a0679eee2.jpg?301x346}}Kunden einfügen Hier kann man Kunden eintragen. Die Felder mit Stern sind Pflichtfelder. {{IPA_Bericht_Betschart_Ingrid_html_372219f7eb0a400e.jpg?271x270}}Kunden verwalten Hier kann man einen der Kunden auswählen indem man neben dem Namen des gewünschten Kunden anklickt. Danach gibt es die Möglichkeiten den Kunden zu bearbeiten oder zu löschen. {{IPA_Bericht_Betschart_Ingrid_html_25b57b89d51bbca5.jpg?268x124}}Bei Kunden bearbeiten erscheint folgendes Formular: {{IPA_Bericht_Betschart_Ingrid_html_8a336aa6cb169b63.jpg?267x301}}Nun kann man die Kundendaten bearbeiten. Bei Kunden löschen erscheint folgendes Formular: {{IPA_Bericht_Betschart_Ingrid_html_e561f276571e41c.jpg?299x229}}Wenn man auf „LÖSCHEN“ klickt wird der Kunde gelöscht. Artikel einfügen Hier kann man Artikel erfassen. Alle Felder sind Pflichtfelder. {{IPA_Bericht_Betschart_Ingrid_html_983bcda3e7f2b4d7.jpg?300x194}}Artikel verwalten Hier kann man einen der Artikel auswählen indem man neben der Nummer des gewünschten Artikels anklickt. Danach gibt es die Möglichkeiten den Artikel zu bearbeiten oder zu löschen. {{IPA_Bericht_Betschart_Ingrid_html_22c78e30df0bc00c.jpg?305x156}}Bei Artikel bearbeiten erscheint folgendes Formular: {{IPA_Bericht_Betschart_Ingrid_html_39448842e43776fb.jpg?303x251}}Nun kann man die Artikeldaten bearbeiten. Bei Artikel löschen erscheint folgendes Formular: {{IPA_Bericht_Betschart_Ingrid_html_d26a0adc515d2271.jpg?299x206}}Wenn man auf „LÖSCHEN“ klickt wird der Artikel gelöscht. Neue Rechnung Auf folgender Seite kann man Rechnungen erstellen und eine PDF-Datei erstellen lassen. {{IPA_Bericht_Betschart_Ingrid_html_2578398f66b1b9b.jpg?605x142}}Links kann man Artikel auswählen indem man auf klickt. Aus dem Dropdown-Menü kann man den Kunden auswählen. Hat man alles ausgewählt, was auf die Rechnung soll, muss man auf „zur Rechnung hinzufügen“ klicken. Dann erscheinen die Daten auf der rechten Seite. {{IPA_Bericht_Betschart_Ingrid_html_cbdb4508f051ae7.jpg?605x161}}Jetzt kann man auf der rechten Seite bei jedem Artikel bei „Menge“ noch die gewünschte Menge eintragen. Wenn nun alle Daten für die Rechnung stimmen, kann man auf „pdf“ klicken und es wird eine PDFDatei erstellt. In dieser ist alles schon mit Briefkopf, Artikelauflistung, Preisberechnungen und auf einer zusätzlichen Seite mit Einzahlungsschein, richtig formatiert. Rechnungen verwalten Hier kann man aus dem Dropdown-Menü eine Rechnung auswählen und auf „Rechnung anzeigen“ klicken um sich die PDF-Datei anzuschauen. {{IPA_Bericht_Betschart_Ingrid_html_236b049608e5f61e.jpg?264x114}}So sieht die Seite aus, wenn eine Rechnung ausgewählt wurde. {{IPA_Bericht_Betschart_Ingrid_html_b8e4a739d2378561.jpg?600x325}}Abmelden Um sich abzumelden muss man auf die Menüseite zurück und auf „abmelden“ klicken. === 2.12.2 Sourcecode === Code des aktuellen Projektes index.php Startseite

Die Handwerkerrechnung

Benutzername oder Passwort falsch

"; } } ?>

Anmelden

Benutzername:
Passwort:
© by Rafisa
menue.php Startseite

Die Handwerkerrechnung

Passwort ändern
"; if (!isset($firmenarray[0]%%['%%firma'])) { %%/*%% * Firma einfügen darf nur möglich sein, wenn dieser Benutzer noch keine eingefügt hat. %%*/%% echo "Neue Firma erfassen
"; } else { %%/*%% * Wenn schon eine Firma eingefügt wurde sind folgende Links auswählbar %%*/%% echo "Firma verwalten
"; echo "Kunden einfügen

"; echo "Kunden verwalten

"; echo "Artikel einfügen

"; echo "Artikel verwalten
"; echo "Neue Rechnung

"; echo "Rechnungen verwalten

"; } %%/*%% * Schaltfläche für Abmeldung %%*/%% echo "
"; echo ""; echo "
"; if (isset($_POST%%['%%abmelden'])) { %%/*%% * Session überschreiben %%*/%% if (ini_get("session.use_cookies")) { $params = session_get_cookie_params(); setcookie(session_name(), %%''%%, time() - 42000, $params["path"], $params["domain"], $params["secure"], $params["httponly"] ); } session_destroy(); %%/*%% * Nach der Abmeldung wird wieder die Startseite angezeigt %%*/%% header("Location: index.php"); } ?>
© by Rafisa
menue_admin.php Startseite

Die Handwerkerrechnung

Benutzer einfügen
Benutzer verwalten
Firmen verwalten

Firma auswählen um deren Kunden,
Rechnungen und Artikel einzufügen
oder zu bearbeiten.

info("Formular in menue_admin.php abgesendet."); } if (isset($_POST%%['%%firma'])) { $firma = $_POST%%['%%firma']; } %%/*%% * Datenbankzugriff um firma, benutzer_id in Array zu speichern %%*/%% $firmenarray = alle_f($log); ?>

Kunden einfügen

"; echo "Kunden verwalten

"; echo "Artikel einfügen

"; echo "Artikel verwalten
"; echo "Neue Rechnung

"; echo "Rechnungen verwalten

"; } %%/*%% * Schaltfläche für Abmeldung %%*/%% echo "
"; echo ""; echo "
"; if (isset($_POST%%['%%abmelden'])) { %%/*%% * Session überschreiben %%*/%% if (ini_get("session.use_cookies")) { $params = session_get_cookie_params(); setcookie(session_name(), %%''%%, time() - 42000, $params["path"], $params["domain"], $params["secure"], $params["httponly"] ); } session_destroy(); %%/*%% * Nach der Abmeldung wird wieder die Startseite angezeigt %%*/%% header("Location: index.php"); } ?>
© by Rafisa
pw_aendern.php Passwort ändern

Die Handwerkerrechnung


Benutzername: Passwort:
info("Formular geaendert in pw_aendern.php abgesendet."); $benutzer_id = $_POST%%['%%benutzer_id']; $i_pw = $_POST%%['%%i_pw']; $i_pw = md5($i_pw); %%/*%% * Änderungen in die Datenbank speichern %%*/%% b_aendern($benutzer_id, $i_pw, $log); %%/*%% * Damit die Seite neu geladen wird, nachdem die Änderungen gespeichert wurden. %%*/%% header("Location: pw_aendern.php"); } echo "Zurück"; ?>
© by Rafisa
benutzer_einfuegen.php Neuen Benutzer einfügen

Die Handwerkerrechnung

Neuen Benutzer einfügen

Benutzername:
Passwort:
Passwort wiederholen:
Benutzer wurde erstellt.

"; } else { echo "

Passwörter stimmen nicht überein.

"; } } ?> Zurück
© by Rafisa
benutzer_verwalten.php Benutzer verwalten

Die Handwerkerrechnung

"; %%/*%% * Schleife um alle Benutzer aufzulisten * $j = 1 damit admin, der Arraystelle 0 hat, nicht aufgelistet wird. %%*/%% for ($j = 1; $j < count($benutzerarray); $j++) { echo "" . $benutzerarray[$j]%%['%%benutzer_id'] . " " . $benutzerarray[$j]%%['%%i_benutzer'] . "
\n"; } %%/*%% * Button um die Auswahl an Formular "aendern" zu senden. %%*/%% echo ""; %%/*%% * Button um die Auswahl an Formular "loeschen" zu senden. %%*/%% echo ""; echo ""; %%/*%% * von submit "aendern" Daten in Variablen speichern %%*/%% if (isset($_POST%%['%%aendern'])) { $log->info("Formular aendern in benutzer_verwalten.php abgesendet."); if (isset($_POST%%['%%benutzer'])) { %%/*%% * in $benutzer_id ist nun die Nummer des Radiobuttons %%*/%% $benutzer_id = $_POST%%['%%benutzer']; %%/*%% * ID und Benutzername des ausgewählten Benutzers in $benutzerarray speichern %%*/%% $benutzerarray = einzel_b($benutzer_id, $log); %%/*%% * Formular um Benutzerdaten zu ändern, * wird nur angezeigt wenn ein Radiobutton ausgewählt und * "Benutzer bearbeiten" angeklickt wird. %%*/%% ?>

Benutzer ID:
Passwort:
info("Formular geaendert in benutzer_verwalten.php abgesendet."); $benutzer_id = $_POST%%['%%benutzer_id']; $i_pw = $_POST%%['%%i_pw']; $i_pw = md5($i_pw); %%/*%% * Datenbankzugriff um die Änderungen zu speichern %%*/%% b_aendern($benutzer_id, $i_pw, $log); %%/*%% * Damit die Seite neu geladen wird, nachdem die Änderungen gespeichert wurden. %%*/%% header("Location: benutzer_verwalten.php"); } %%/*%% * von submit "loeschen" Daten in Variablen speichern %%*/%% if (isset($_POST%%['%%loeschen'])) { $log->info("Formular loeschen in benutzer_verwalten.php abgesendet."); if (isset($_POST%%['%%benutzer'])) { %%/*%% * in $benutzer_id ist nun die Nummer des Radiobuttons %%*/%% $benutzer_id = $_POST%%['%%benutzer']; %%/*%% * ID und Benutzername des ausgewählten Benutzers in $benutzerarray speichern %%*/%% $benutzerarray = einzel_b($benutzer_id, $log); %%/*%% * Formular um Benutzer zu löschen, * wird nur angezeigt wenn ein Radiobutton ausgewählt und * "Benutzer löschen" angeklickt wird. %%*/%% ?>

Benutzer ID:
Benutzer:

info("Formular geloescht in benutzer_verwalten.php abgesendet."); $benutzer_id = $_POST%%['%%benutzer_id']; $i_benutzer = $_POST%%['%%i_benutzer']; %%/*%% * Datenbankzugriff um den ausgewählten Benutzer zu löschen %%*/%% b_loeschen($benutzer_id, $log); %%/*%% * Damit die Seite neu geladen wird, nachdem gelöscht wurde. %%*/%% header("Location: benutzer_verwalten.php"); } echo "Zurück"; ?>
© by Rafisa
config.xml log_loeschen.bat forfiles /P "C:\xampp\htdocs\Handwerkerrechnung\log" /S /M *.log /D -2 /C "cmd /c del /q @path" firma_verwalten.php Firma verwalten

Die Handwerkerrechnung

Firmenlogo hochladen
"; %%/*%% * alle Daten dieser Firma in $firmenarray speichern %%*/%% $firmenarray = einzel_f($benutzer_id, $log); if(!isset($_POST%%['%%geaendert'])){ %%/*%% * Formular um Firmendaten zu ändern %%*/%% ?>

Firmenname*:
Logo: "; echo ""; } } echo "
"; closedir($auslesen); %%/*%% * Ende Verzeichnis auslesen %%*/%% ?>
Branche:
Strasse*:
PLZ*:
Ort*:
Telefon:
Mobile:
Fax:
E-Mail:
Homepage:
MWST Nr*:
Konto*:
info("Formular geaendert in firma_verwalten.php abgesendet."); $benutzer_id = $_POST%%['%%benutzer_id']; %%/*%% * Firma speichern und XSS verhindern %%*/%% $firma = $_POST%%['%%firma']; $firma = htmlspecialchars($firma); %%/*%% * Logo speichern %%*/%% $logo = $_POST%%['%%logo']; %%/*%% * Branche speichern und überprüfen ob nur Buchstaben eingegeben wurden. %%*/%% $branche = $_POST%%['%%branche']; $branche = nur_Buchstaben($branche); %%/*%% * Strasse speichern und überprüfen ob Sonderzeichen eingegeben wurden. %%*/%% $strasse = $_POST%%['%%strasse']; $strasse = strasse($strasse); %%/*%% * PLZ speichern und überprüfen ob eine Zahl eingegeben wurde zwischen 1000 und 9658 %%*/%% $plz = $_POST%%['%%plz']; $plz = plz($plz); %%/*%% * Ort speichern und überprüfen ob nur Buchstaben ev. mit Leerzeichen oder Bindestrich eingegeben wurden. %%*/%% $ort = $_POST%%['%%ort']; $ort = namen($ort); %%/*%% * Telefonnummer speichern und überprüfen Erlaubte Formate: 021-423-23-23 oder 021 423 23 23 %%*/%% $telefon = $_POST%%['%%telefon']; $telefon = telefon($telefon); %%/*%% * Handynummer speichern und überprüfen Erlaubte Formate: 079-423-23-23 oder 079 423 23 23 %%*/%% $mobile = $_POST%%['%%mobile']; $mobile = telefon($mobile); %%/*%% * Faxnummer speichern und überprüfen Erlaubte Formate: 021-423-23-23 oder 021 423 23 23 %%*/%% $fax = $_POST%%['%%fax']; $fax = telefon($fax); %%/*%% * E-Mail speichern und Gültigkeit überprüfen %%*/%% $email = $_POST%%['%%email']; $email_ok = email($email); %%/*%% * Homepage speichern und Gültigkeit überprüfen %%*/%% $homepage = $_POST%%['%%homepage']; if (urlValidate($homepage) || $homepage == "") { $homepage_ok = true; } else { $homepage_ok = false; } %%/*%% * MWST-Nummer speichern und Gültigkeit überprüfen. %%*/%% $mwst_nr = $_POST%%['%%mwst_nr']; $mwst_nr = mwst($mwst_nr); %%/*%% * Kontonummer speichern und Gültigkeit überprüfen. %%*/%% $konto = $_POST%%['%%konto']; $konto = konto($konto); %%/*%% * überprüfen ob alle Pflichfelder ausgefüllt wurden %%*/%% if ($firma == "" || $strasse == "" || $plz == "" || $ort == "" || $mwst_nr %%==%% "" || $konto == "" || $email_ok == false || $homepage_ok == false) { echo "Die Felder Firmenname, Strasse, PLZ, Ort, MWST Nr und Konto müssen ausgefüllt sein!"; %%/*%% * Formular mit bisher eingegebenen Daten anzeigen. %%*/%% ?>

Firmenname*: Hier fehlt was."; } ?>
Logo: "; while ($datei = readdir($auslesen)) { if (!is_dir($datei)) { if ($logo == $datei) { echo ""; } echo ""; } } echo "
"; closedir($auslesen); %%/*%% * Ende Verzeichnis auslesen %%*/%% ?>
Branche:
Strasse*: Hier fehlt was."; } ?>
PLZ*: ">Bitte gültige PLZ eingeben."; } ?>
Ort*: Hier fehlt was."; } ?>
Telefon:
Mobile:
Fax:
E-Mail: Bitte gültige E-Mailadresse eingeben."; } ?>
Homepage: Bitte gültige Homepage eingeben."; } ?>
MWST Nr*: Hier fehlt was."; } ?>
Konto*: Hier fehlt was."; } ?>
info("Formular loeschen in firma_verwalten.php abgesendet."); if (isset($_POST%%['%%benutzer_id'])) { $benutzer_id = $_POST%%['%%benutzer_id']; $firmenarray = einzel_f($benutzer_id, $log); ?>

Firma:
Branche:

info("Formular geloescht in firma_verwalten.php abgesendet."); $benutzer_id = $_POST%%['%%benutzer_id']; $firma = $_POST%%['%%firma']; $branche = $_POST%%['%%branche']; %%/*%% * Firma aus der Datenbank löschen %%*/%% f_loeschen($benutzer_id, $log); %%/*%% * Damit die Seite neu geladen wird, nachdem gelöscht wurde. %%*/%% header("Location: menue.php"); } echo "Zurück"; ?>
© by Rafisa
benutzer_ueberpruefen.php "; exit; } ?> Dateien aus dem Vorprojekt ueberpruefen.php 9658) { $plz = ""; } return $plz; } %%/*%% * Funktion um die Eingabe darauf zu überprüfen ob sie nur Buchstaben, * Leerzeichen und Bindestrich enthält * Stimmt die Eingabe nicht mit den Kriterien überein, wird die übergebene * Variable leer gesetzt. %%*/%% function namen($wort) { if (!preg_match%%('/%%^[a-zäöüA-ZÄÖÜ -]*$%%/'%%, $wort)) { $wort = ""; } return $wort; } %%/*%% * Funktion um eine E-Mailadresse zu überprüfen. * Vorgefertigte Funktion filter_var verwendet. * Wenn die Funktion nicht false zurückgibt oder die Variable leer ist, * wird true zurückgegeben, sonst false %%*/%% function email($email) { $email_ok = filter_var($email, FILTER_VALIDATE_EMAIL); if ($email_ok != false || $email == "") { return $email_ok = true; } else { return $email_ok = false; } } %%/*%% * Funktion um eine Homepage zu überprüfen. * Funktion aus dem Internet. https://www.datenreise.de/php-url-korrekte-syntax-und-existenzpruefen/ * Gibt je nachdem true oder false zurück %%*/%% function urlValidate($url) { $url = trim($url); if (preg_match%%('%%%^(?:(?:https?):%%//%%)(?:\S+(?::\S*)?@|\d{1,3}(?:\.\d{1,3}){3}|(?:(?:[az\d\x{00a1}-\x{ffff}]+-?)%%*[%%a-z\d\x{00a1}-\x{ffff}]+)(?:\.(?:[a-z\d\x{00a1}-\x{ffff}]+-?)%%*[%%az\d\x{00a1}-\x{ffff}]+)%%*(%%?:\.[a-z\x{00a1}-\x{ffff}]{2,6}))(?::\d+)?(?:[^\s]*)?$%iu', $url)) { if (ini_get%%('%%allow_url_fopen')) { $headers = @get_headers($url, 1); if (preg_match%%('/%%^HTTP\/.*\s+(200|401)%%/'%%, $headers[0])) { return true; } elseif (preg_match%%('/%%^HTTP\/.*\s+(300|301|302|303|307|308)%%/'%%, $headers[0])) { if ($headers !== false && isset($headers%%['%%Location'])) { if ($headers%%['%%Location'] != $url) { return urlValidate($headers%%['%%Location']); } else { %%//%% Never ending story return false; } } else { return false; } } else { return false; } } elseif (function_exists%%('%%curl_version')) { $user_agent = "Mozilla/5.0 (Windows NT 6.1; Win64; x64; rv:16.0) Gecko/20121026 Firefox/16.0"; $ch = @curl_init($url); @curl_setopt($ch, CURLOPT_HEADER, 1); @curl_setopt($ch, CURLOPT_NOBODY, 1); @curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 0); @curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); @curl_setopt($ch, CURLOPT_HEADER, 1); @curl_setopt($ch, CURLOPT_TIMEOUT, 5); @curl_setopt($ch, CURLOPT_USERAGENT, $user_agent); @curl_exec($ch); $http_statuscode = curl_getinfo($ch, CURLINFO_HTTP_CODE); if (preg_match%%('/%%^200|301|302$%%/'%%, $http_statuscode)) { return true; } } else { throw new Exception%%('%%curl and allow_url_fopen are not avaiable.'); } } return false; } ?> artikel_einfuegen.php Neuen Artikel erfassen

Die Handwerkerrechnung

info("Formular in artikel_einfuegen.php abgesendet."); %%//%%Artikelnummer speichern und überprüfen ob es eine Zahl ist. $art_nr = $_POST%%['%%art_nr']; $art_nr = int($art_nr); $benutzer_id = $_POST%%['%%benutzer_id']; %%//%%Beschreibung speichern und <> Eingaben umwandeln $beschreibung = $_POST%%['%%beschreibung']; $beschreibung = htmlspecialchars($beschreibung); %%//%%Einheit speichern und <> Eingaben umwandeln $einheit = $_POST%%['%%einheit']; $einheit = htmlspecialchars($einheit); %%//%%Preis pro Einheit speichern und überprüfen ob Zahlen eingegeben wurden. $preis_p_e = $_POST%%['%%preis_p_e']; $preis_p_e = float($preis_p_e); %%//%%Pflichtfelder überprüfen if ($art_nr == 0 || $beschreibung == "" || $einheit == "" || $preis_p_e == 0) { %%//%%Formular mit bisher eingegebenen Daten anzeigen. ?>

Artikelnummer*: Hier fehlt was."; } ?>
Beschreibung*: Hier fehlt was."; } ?>
Einheit*: Hier fehlt was."; } ?>
Preis pro Einheit*: Hier fehlt was."; } ?>

Artikelnummer*:
Beschreibung*:
Einheit*:
Preis pro Einheit*:

Zurück"; } else { echo "Zurück"; } ?>
© by Rafisa
artikel_verwalten.php Artikel verwalten

Die Handwerkerrechnung

"; echo "\n"; %%//%%Schleife um alle Artikel aufzulisten for ($j = 0; $j < count($artikelarray); $j++) { echo "" . $artikelarray[$j]%%['%%art_nr'] . " " . utf8_encode($artikelarray[$j]%%['%%beschreibung']) . "
\n"; } %%//%%Button um die Auswahl zu senden an Formular "aendern". echo ""; %%//%%Button um die Auswahl zu senden an Formular "loeschen". echo ""; echo ""; %%//%%Formular um Artikeldaten zu ändern, wird nur angezeigt wenn ein Radiobutton ausgewählt und "Artikel bearbeiten" angeklickt wird. if (isset($_POST%%['%%aendern'])) { $log->info("Formular aendern in artikel_verwalten.php abgesendet."); if (isset($_POST%%['%%artikel'])) { %%//%%in $art_id ist nun die Nummer des Radiobuttons, die gleich der Artikel-Id ist $art_id = $_POST%%['%%artikel']; $artikelarray = einzel_a($benutzer_id, $art_id, $log); ?>

Artikelnummer*:
Beschreibung*:
Einheit*:
Preis pro Einheit*:
info("Formular geaendert in artikel_verwalten.php abgesendet."); $benutzer_id = $_POST%%['%%benutzer_id']; $art_id = $_POST%%['%%art_id']; %%//%%Artikelnummer speichern und überprüfen ob es eine Zahl ist. $art_nr = $_POST%%['%%art_nr']; $art_nr = int($art_nr); %%//%%Beschreibung speichern und <> Eingaben umwandeln $beschreibung = $_POST%%['%%beschreibung']; $beschreibung = htmlspecialchars($beschreibung); %%//%%Einheit speichern und <> Eingaben umwandeln $einheit = $_POST%%['%%einheit']; $einheit = htmlspecialchars($einheit); %%//%%Preis pro Einheit speichern und überprüfen ob Zahlen eingegeben wurden. $preis_p_e = $_POST%%['%%preis_p_e']; $preis_p_e = float($preis_p_e); %%//%%Pflichtfelder überprüfen if ($art_nr == 0 || $beschreibung == "" || $einheit == "" || $preis_p_e == 0) { echo "Alle Felder müssen ausgefüllt sein!" %%//%%Formular mit bisher eingegebenen Daten anzeigen. ?>

Artikelnummer*: Hier fehlt was."; } ?>
Beschreibung*: Hier fehlt was."; } ?>
Einheit*: Hier fehlt was."; } ?>
Preis pro Einheit*: Hier fehlt was."; } ?>
info("Formular loeschen in artikel_verwalten.php abgesendet."); if (isset($_POST%%['%%artikel'])) { %%//%%in $art_id ist nun die Nummer des Radiobuttons, die gleich der Artikel-Id ist $art_id = $_POST%%['%%artikel']; $artikelarray = einzel_a($benutzer_id, $art_id, $log); ?>

Artikelnummer:
Beschreibung:

info("Formular geloescht in artikel_verwalten.php abgesendet."); $benutzer_id = $_POST%%['%%benutzer_id']; $art_id = $_POST%%['%%art_id']; $art_nr = $_POST%%['%%art_nr']; $beschreibung = $_POST%%['%%beschreibung']; $einheit = $_POST%%['%%einheit']; %%//%%DB-Verbindung um die gewünschten Daten zu löschen a_loeschen($benutzer_id, $art_id, $log); %%//%%Damit die Seite neu geladen wird, nachdem gelöscht wurde. header("Location: artikel_verwalten.php"); } %%//%%Je nachdem ob admin oder normaler Benutzer eingeloggt ist, auf andere Seite. if(isset($_GET%%['%%benutzer_id'])) { echo "Zurück"; } else { echo "Zurück"; } ?>
© by Rafisa
druck.php info("beschreibung in druck.php abgesendet."); $art_nr = $_POST%%['%%art_nr']; $beschreibung = $_POST%%['%%beschreibung']; $einheit = $_POST%%['%%einheit']; $preis_p_e = $_POST%%['%%preis_p_e']; $menge = $_POST%%['%%menge']; %%//%%Kundenadresse $anrede = $_POST%%['%%anrede']; $namen = $_POST%%['%%namen']; $adresse = $_POST%%['%%adresse']; $ort = $_POST%%['%%ort']; $firma_id = $_POST%%['%%firma_id']; $rg_nr = $_POST%%['%%rg_nr']; } %%//%%Rechnungsnummer speichern rg_nr_speichern($firma_id, $rg_nr, $log); %%//%%Ende Rechnungsnummer %%//%%DB-Anbindung für Firmendaten $firmenarray = einzel_f($firma_id, $log); %%//%%Ende DB-Anbindung Firmendaten %%//%%neues PDF-Dokument erstellen $pdf = new PDF_MC_Table(); $pdf->Open(); $pdf->AddPage(); $pdf->SetAutoPageBreak(true); %%//%%Schriftart definieren $pdf->SetFont%%('%%helvetica', %%''%%, 12); %%//%%Ausgabe der Firmendaten $pdf->Image("logos/" . utf8_encode($firmenarray[0]%%['%%logo']), 20, 10, 30); $pdf->Text(20, 30, $firmenarray[0]%%['%%branche']); $pdf->Text(20, 50, $firmenarray[0]%%['%%firma']); $pdf->Text(20, 55, $firmenarray[0]%%['%%strasse']); $pdf->Text(20, 60, $firmenarray[0]%%['%%plz'] . " " . $firmenarray[0]%%['%%ort']); $pdf->Text(20, 70, "Telefon: " . $firmenarray[0]%%['%%telefon']); $pdf->Text(20, 75, "Mobile: " . $firmenarray[0]%%['%%mobile']); $pdf->Text(20, 80, "Fax: " . $firmenarray[0]%%['%%fax']); $pdf->Text(20, 85, "E-Mail: " . $firmenarray[0]%%['%%email']); $pdf->Text(20, 90, "Homepage: " . $firmenarray[0]%%['%%homepage']); %%//%%Ausgabe des Datums $datum = date("d.m.Y", time()); $pdf->Text(140, 100, $firmenarray[0]%%['%%ort'] . ", " . $datum . ""); %%//%%Ausgabe der Rechnungsnummer $pdf->Text(20, 100, "Rechnungsnummer: " . $firmenarray[0]%%['%%rg_nr'] . " MWST-Nummer: " . $firmenarray[0]%%['%%mwst_nr']); %%//%%$adresse in einen Array speichern Elemente trennen bei \n $adressarray = explode("\n", $adresse); %%//%%Ausgabe der Kundenadresse $pdf->Text(140, 50, $anrede); $pdf->Text(140, 55, utf8_decode($namen)); %%//%%Vorname Nachname $pdf->Text(140, 60, utf8_decode($adresse)); %%//%%Strasse Nr $pdf->Text(140, 65, utf8_decode($ort)); %%//%%PLZ Ort %%//%%Artikel auflisten %%//%%leere Zelle, damit die andern Zellen weiter unten als die Rechnungsnummer sind. %%//%%Parameter für Cell: Zellenbreite, Zellenhöhe, Inhalt, Rahmen, Position nach Ausgabe der Zelle, Textausrichtung $pdf->Cell(190, 100, "", 0, 2); $total = 0; %%//%%Gesamtpreis ohne MWST $pdf->SetWidths(array(10, 28, 50, 16, 35, 16, 25)); %%//%%Spaltenbreiten festlegen for ($i = 0; $i < count($beschreibung); $i++) { if ($i == 0) { $pdf->SetAligns(array%%('%%L','L', 'L', 'L', 'L', 'L', 'L')); %%//%%Textausrichtung der Spalten %%//%%Damit in erster Zeile der Spaltenname steht $preis[$i] = "Preis"; $pdf->Row(array("",$art_nr[$i], utf8_decode($beschreibung[$i]), utf8_decode($einheit[$i]), $preis_p_e[$i], $menge[$i], $preis[$i])); } $pdf->SetAligns(array%%('%%L', 'R', 'L', 'L', 'R', 'R', 'R')); if ($i > 0) { $preis[$i] = $preis_p_e[$i] * $menge[$i]; %%//%%Preis formatieren auf 2 Nachkommastellen mit Punkt getrennt und 1'000er Zeichen $preis_format[$i] = number_format($preis[$i], 2, ".", "'"); $pdf->Row(array("", $art_nr[$i], utf8_decode($beschreibung[$i]), utf8_decode($einheit[$i]), $preis_p_e[$i], $menge[$i], $preis_format[$i])); } $total += $preis[$i]; } $mwst = $total * 0.08; $gesamt = $total + $mwst; %%//%%Gesamtpreis mit MWST $pdf->SetAligns(array%%('%%L','L', 'L', 'L', 'L', 'L', 'R')); $pdf->Row(array("", "Total", "", "", "", "", number_format(round($total, 2), 2, ".", "'"))); $pdf->Row(array("", "MWST 8%", "", "", "", "", number_format(round($mwst, 2), 2, ".", "'"))); $pdf->Row(array("", "Gesamtpreis", "", "", "", "", number_format(round($gesamt / 5, 2) * 5, 2, ".", "'")));%%//%%gerundet auf 5 Rappen %%//%%Seitenzahl und Gesamtseitenzahl anzeigen $pdf->Footer(); $pdf->AliasNbPages%%('{%%nb}'); %%//%%Damit auf letzter Seite keine Seitenzahlen stehen $pdf->NoHF(); %%//%%Seite für den Einzahlungsschein $pdf->AddPage(); $pdf->AddFont%%('%%ocrb10',%%''%%,'ocrb10.php');%%//%%Vorgegebene Schriftart für Einzahlungsscheine $pdf->SetFont%%('%%ocrb10', %%''%%, 8); %%//%%erste Spalte $pdf->Text(2, 205, $firmenarray[0]%%['%%firma']); $pdf->Text(2, 210, $firmenarray[0]%%['%%strasse']); $pdf->Text(2, 215, $firmenarray[0]%%['%%plz'] . " " . $firmenarray[0]%%['%%ort']); $pdf->Text(25, 235, $firmenarray[0]%%['%%konto']); $pdf->Text(2, 239, "CHF"); $pdf->Text(40, 245, number_format(round($gesamt / 5, 2) * 5, 2, ".","")); $pdf->Text(2, 255, utf8_decode($namen)); %%//%%Vorname Nachname $pdf->Text(2, 260, utf8_decode($adresse)); %%//%%Strasse Nr $pdf->Text(2, 265, utf8_decode($ort)); %%//%%PLZ Ort %%//%%zweite Spalte $pdf->Text(62, 205, $firmenarray[0]%%['%%firma']); $pdf->Text(62, 210, $firmenarray[0]%%['%%strasse']); $pdf->Text(62, 215, $firmenarray[0]%%['%%plz'] . " " . $firmenarray[0]%%['%%ort']); $pdf->Text(85, 235, $firmenarray[0]%%['%%konto']); $pdf->Text(62, 239, "CHF"); $pdf->Text(100, 245, number_format(round($gesamt / 5, 2) * 5, 2, ".","")); %%//%%dritte Spalte $pdf->Text(125, 205, "Rechnung"); $pdf->Text(125, 210, "Nr. ". $rg_nr); $pdf->Text(125, 215, "vom " . $datum); $pdf->Text(125, 245, utf8_decode($namen)); %%//%%Vorname Nachname $pdf->Text(125, 250, utf8_decode($adresse)); %%//%%Strasse Nr $pdf->Text(125, 255, utf8_decode($ort)); %%//%%PLZ Ort %%//%%Ausgabe zum Browser $dateiname = $firmenarray[0]%%['%%firma'] . "_" . $datum . "_RgNr" . $firmenarray[0]%%['%%rg_nr'] . ".pdf"; $pdf->Output($dateiname, 'I'); %%//%%PDF speichern in Unterordner rechnungen $pdf->Output("rechnungen/" . $dateiname, "F"); ?> firma_einfuegen.php Neue Firma erfassen

Die Handwerkerrechnung

info("Formular in firma_einfuegen.php abgesendet."); $benutzer_id = $_POST%%['%%benutzer_id']; %%//%%Firma speichern und <> Eingaben umwandeln $firma = $_POST%%['%%firma']; $firma = htmlspecialchars($firma); $logo = $_POST%%['%%logo']; %%//%%Branche speichern und überprüfen ob nur Buchstaben eingegeben wurden. $branche = $_POST%%['%%branche']; $branche = nur_Buchstaben($branche); %%//%%Strasse speichern und überprüfen ob Sonderzeichen eingegeben wurden. $strasse = $_POST%%['%%strasse']; $strasse = strasse($strasse); %%//%%PLZ speichern und überprüfen ob eine Zahl eingegeben wurde zwischen 1000 und 9658 $plz = $_POST%%['%%plz']; $plz = plz($plz); %%//%%Ort speichern und überprüfen ob nur Buchstaben ev. mit Leerzeichen oder Bindestrich eingegeben wurden. $ort = $_POST%%['%%ort']; $ort = namen($ort); %%//%%Telefonnummer speichern und überprüfen Erlaubte Formate: 021-423-23-23 oder 021 423 23 23 $telefon = $_POST%%['%%telefon']; $telefon = telefon($telefon); %%//%%Handynummer speichern und überprüfen Erlaubte Formate: 079-423-23-23 oder 079 423 23 23 $mobile = $_POST%%['%%mobile']; $mobile = telefon($mobile); %%//%%Faxnummer speichern und überprüfen Erlaubte Formate: 021-423-23-23 oder 021 423 23 23 $fax =$_POST%%['%%fax']; $fax = telefon($fax); %%//%%E-Mail speichern und Gültigkeit überprüfen $email = $_POST%%['%%email']; $email_ok = email($email); %%//%%Homepage speichern und Gültigkeit überprüfen $homepage = $_POST%%['%%homepage']; if (urlValidate($homepage) || $homepage == "") { $homepage_ok = true; } else { $homepage_ok = false; } %%//%%MWST-Nummer speichern und Gültigkeit überprüfen. $mwst_nr = $_POST%%['%%mwst_nr']; $mwst_nr = mwst($mwst_nr); %%//%%Kontonummer speichern und Gültigkeit überprüfen. $konto = $_POST%%['%%konto']; $konto = konto($konto); %%//%%Pflichtfelder überprüfen if ($firma == "" || $strasse == "" || $plz == "" || $ort == "" || $mwst_nr %%==%% "" || $konto == "" || $email_ok == false || $homepage_ok == false) { echo "Die Felder Firmenname, Strasse, PLZ, Ort, MWST Nr und Konto müssen ausgefüllt sein!"; %%//%%Formular mit bisher eingegebenen Daten anzeigen. ?>

Firmenname*: Hier fehlt was."; } ?>
Logo: "; while ($datei = readdir($auslesen)) { if (!is_dir($datei)) { if ($logo == $datei) { echo ""; } echo ""; } } echo "
"; closedir($auslesen); %%//%%Ende Verzeichnis auslesen ?>
Branche:
Strasse*: Hier fehlt was."; } ?>
PLZ*: ">Bitte gültige PLZ eingeben."; } ?>
Ort*: Hier fehlt was."; } ?>
Telefon:
Mobile:
Fax:
E-Mail: Bitte gültige E-Mailadresse eingeben."; } ?>
Homepage: Bitte gültige Homepage eingeben."; } ?>
MWST Nr*: Hier fehlt was."; } ?>
Konto*: Hier fehlt was."; } ?>

Firmenlogo hochladen

Firmenname*:
Logo: "; while ($datei = readdir($auslesen)) { if (!is_dir($datei)) { echo ""; } } echo "
"; closedir($auslesen); %%//%%Ende Verzeichnis auslesen ?>
Branche:
Strasse*:
PLZ*:
Ort*:
Telefon:
Mobile:
Fax:
E-Mail:
Homepage:
MWST Nr*:
Konto*:

Zurück"; ?>
© by Rafisa
firmen_verwalten.php Firmen verwalten

Die Handwerkerrechnung

"; %%//%%Schleife um alle Firmen aufzulisten for ($j = 0; $j < count($firmenarray); $j++) { echo "" .$firmenarray[$j]%%['%%benutzer_id']." ". utf8_encode($firmenarray[$j]%%['%%firma']) . " " . utf8_encode($firmenarray[$j]%%['%%branche']) . "
\n"; } %%//%%Button um die Auswahl zu senden an Formular "aendern". echo ""; %%//%%Button um die Auswahl zu senden an Formular "loeschen". echo ""; echo ""; %%//%%Formular um Firmendaten zu ändern, wird nur angezeigt wenn ein Radiobutton ausgewählt und "Firma bearbeiten" angeklickt wird. if (isset($_POST%%['%%aendern'])) { $log->info("Formular aendern in firmen_verwalten.php abgesendet."); if (isset($_POST%%['%%firma'])) { %%//%%in $benutzer_id ist nun die Nummer des Radiobuttons, die gleich der Firmen-Id ist $benutzer_id = $_POST%%['%%firma']; $firmenarray = einzel_f($benutzer_id, $log); ?>

Firmenname*:
Logo: "; echo ""; } } echo "
"; closedir($auslesen); %%//%%Ende Verzeichnis auslesen ?>
Branche:
Strasse*:
PLZ*:
Ort*:
Telefon:
Mobile:
Fax:
E-Mail:
Homepage:
MWST Nr*:
Konto*:
info("Formular geaendert in firmen_verwalten.php abgesendet."); $benutzer_id = $_POST%%['%%benutzer_id']; %%//%%Firma speichern und <> Eingaben umwandeln $firma = $_POST%%['%%firma']; $firma = htmlspecialchars($firma); $logo = $_POST%%['%%logo']; %%//%%Branche speichern und überprüfen ob nur Buchstaben eingegeben wurden. $branche = $_POST%%['%%branche']; $branche = nur_Buchstaben($branche); %%//%%Strasse speichern und überprüfen ob Sonderzeichen eingegeben wurden. $strasse = $_POST%%['%%strasse']; $strasse = strasse($strasse); %%//%%PLZ speichern und überprüfen ob eine Zahl eingegeben wurde zwischen 1000 und 9658 $plz = $_POST%%['%%plz']; $plz = plz($plz); %%//%%Ort speichern und überprüfen ob nur Buchstaben ev. mit Leerzeichen oder Bindestrich eingegeben wurden. $ort = $_POST%%['%%ort']; $ort = namen($ort); %%//%%Telefonnummer speichern und überprüfen Erlaubte Formate: 021-423-23-23 oder 021 423 23 23 $telefon = $_POST%%['%%telefon']; $telefon = telefon($telefon); %%//%%Handynummer speichern und überprüfen Erlaubte Formate: 079-423-23-23 oder 079 423 23 23 $mobile = $_POST%%['%%mobile']; $mobile = telefon($mobile); %%//%%Faxnummer speichern und überprüfen Erlaubte Formate: 021-423-23-23 oder 021 423 23 23 $fax = $_POST%%['%%fax']; $fax = telefon($fax); %%//%%E-Mail speichern und Gültigkeit überprüfen $email = $_POST%%['%%email']; $email_ok = email($email); %%//%%Homepage speichern und Gültigkeit überprüfen $homepage = $_POST%%['%%homepage']; if (urlValidate($homepage) || $homepage == "") { $homepage_ok = true; } else { $homepage_ok = false; } %%//%%MWST-Nummer speichern und Gültigkeit überprüfen. $mwst_nr = $_POST%%['%%mwst_nr']; $mwst_nr = mwst($mwst_nr); %%//%%Kontonummer speichern und Gültigkeit überprüfen. $konto = $_POST%%['%%konto']; $konto = konto($konto); %%//%%Pflichtfelder überprüfen if ($firma == "" || $strasse == "" || $plz == "" || $ort == "" || $mwst_nr %%==%% "" || $konto == "" || $email_ok == false || $homepage_ok == false) { echo "Die Felder Firmenname, Strasse, PLZ, Ort, MWST Nr und Konto müssen ausgefüllt sein!"; %%//%%Formular mit bisher eingegebenen Daten anzeigen. ?>

Firmenname*: Hier fehlt was."; } ?>
Logo: "; while ($datei = readdir($auslesen)) { if (!is_dir($datei)) { if ($logo == $datei) { echo ""; } echo ""; } } echo "
"; closedir($auslesen); %%//%%Ende Verzeichnis auslesen ?>
Branche:
Strasse*: Hier fehlt was."; } ?>
PLZ*: ">Bitte gültige PLZ eingeben."; } ?>
Ort*: Hier fehlt was."; } ?>
Telefon:
Mobile:
Fax:
E-Mail: Bitte gültige E-Mailadresse eingeben."; } ?>
Homepage: Bitte gültige Homepage eingeben."; } ?>
MWST Nr*: Hier fehlt was."; } ?>
Konto*: Hier fehlt was."; } ?>
info("Formular loeschen in firmen_verwalten.php abgesendet."); if (isset($_POST%%['%%firma'])) { %%//%%in $benutzer_id ist nun die Nummer des Radiobuttons, die gleich der Firmen-Id ist $benutzer_id = $_POST%%['%%firma']; %%//%%echo "post firma: ".$_POST%%['%%firma']; $firmenarray = einzel_f($benutzer_id, $log); ?>

Firma:
Branche:

info("Formular geloescht in firmen_verwalten.php abgesendet."); $benutzer_id = $_POST%%['%%benutzer_id']; $firma = $_POST%%['%%firma']; $branche = $_POST%%['%%branche']; %%//%%DB-Verbindung um die gewünschten Daten zu löschen f_loeschen($benutzer_id, $log); %%//%%Damit die Seite neu geladen wird, nachdem gelöscht wurde. header("Location: firmen_verwalten.php"); } echo "Zurück"; ?>
© by Rafisa
kunden_einfuegen.php Neuen Kunden erfassen

Die Handwerkerrechnung

info("Formular in kunden_einfuegen.php abgesendet."); $kunden_nr = $_POST%%['%%kunden_nr']; $benutzer_id = $_POST%%['%%benutzer_id']; $anrede = $_POST%%['%%anrede']; %%//%%Nachname speichern und überprüfen ob nur Buchstaben ev. mit Leerzeichen oder Bindestrich eingegeben wurden. $nachname = $_POST%%['%%nachname']; $nachname = namen($nachname); %%//%%Vorname speichern und überprüfen ob nur Buchstaben ev. mit Leerzeichen oder Bindestrich eingegeben wurden. $vorname = $_POST%%['%%vorname']; $vorname = namen($vorname); %%//%%Strasse speichern und überprüfen ob Sonderzeichen eingegeben wurden. $strasse = $_POST%%['%%strasse']; $strasse = strasse($strasse); %%//%%PLZ speichern und überprüfen ob eine Zahl eingegeben wurde zwischen 1000 und 9658 $plz = $_POST%%['%%plz']; $plz = plz($plz); %%//%%Ort speichern und überprüfen ob nur Buchstaben ev. mit Leerzeichen oder Bindestrich eingegeben wurden. $ort = $_POST%%['%%ort']; $ort = namen($ort); %%//%%Telefonnummer speichern und überprüfen Erlaubte Formate: 021-423-23-23 oder 021 423 23 23 $telefon = $_POST%%['%%telefon']; $telefon = telefon($telefon); %%//%%Handynummer speichern und überprüfen Erlaubte Formate: 079-423-23-23 oder 079 423 23 23 $mobile = $_POST%%['%%mobile']; $mobile = telefon($mobile); %%//%%Pflichtfelder überprüfen if ($anrede == "" || $nachname == "" || $vorname == "" || $strasse == "" %%|%%| $plz == "" || $ort == "") { %%//%%Formular mit bisher eingegebenen Daten anzeigen. ?>

Anrede*: Frau Herr Frau Herr
Nachname*: Hier fehlt was."; } ?>
Vorname*: Hier fehlt was."; } ?>
Strasse*: Hier fehlt was."; } ?>
PLZ*: ">Bitte gültige PLZ eingeben."; } ?>
Ort*: Hier fehlt was."; } ?>
Telefon:
Mobile:

Anrede*: Frau Herr
Nachname*:
Vorname*:
Strasse*:
PLZ*:
Ort*:
Telefon:
Mobile:

Zurück"; } else { echo "Zurück"; } ?>
© by Rafisa
kunden_verwalten.php Kunden verwalten

Die Handwerkerrechnung

"; echo "\n"; %%//%%Schleife um alle Kunden aufzulisten for ($j = 0; $j < count($kundenarray); $j++) { echo "" . $kundenarray[$j]%%['%%kunden_nr'] . " " . utf8_encode($kundenarray[$j]%%['%%vorname']) . " " . utf8_encode($kundenarray[$j]%%['%%nachname']) . "
\n"; } %%//%%Button um die Auswahl zu senden an Formular "aendern". echo ""; %%//%%Button um die Auswahl zu senden an Formular "loeschen". echo ""; echo ""; %%//%%Formular um Kundendaten zu ändern, wird nur angezeigt wenn ein Radiobutton ausgewählt und "Kunden bearbeiten" angeklickt wird. if (isset($_POST%%['%%aendern'])) { $log->info("Formular aendern in kunden_verwalten.php abgesendet."); if (isset($_POST%%['%%kunde'])) { %%//%%in $kunden_id ist nun die Nummer des Radiobuttons, die gleich der Kunden-Id ist $kunden_id = $_POST%%['%%kunde']; %%//%%echo $kunden_id ."kundenid".$benutzer_id."firmaid"; $kundenarray = einzel_k($benutzer_id, $kunden_id, $log); ?>

Anrede*: Frau Herr Frau Herr
Nachname*:
Vorname*:
Strasse*:
PLZ*:
Ort*:
Telefon:
Mobile:
info("Formular geaendert in kunden_verwalten.php abgesendet."); $benutzer_id = $_POST%%['%%benutzer_id']; $kunden_id = $_POST%%['%%kunden_id']; $kunden_nr = $_POST%%['%%kunden_nr']; $anrede = $_POST%%['%%anrede']; %%//%%Nachname speichern und überprüfen ob nur Buchstaben ev. mit Leerzeichen oder Bindestrich eingegeben wurden. $nachname = $_POST%%['%%nachname']; $nachname = namen($nachname); %%//%%Vorname speichern und überprüfen ob nur Buchstaben ev. mit Leerzeichen oder Bindestrich eingegeben wurden. $vorname = $_POST%%['%%vorname']; $vorname = namen($vorname); %%//%%Strasse speichern und überprüfen ob Sonderzeichen eingegeben wurden. $strasse = $_POST%%['%%strasse']; $strasse = strasse($strasse); %%//%%PLZ speichern und überprüfen ob eine Zahl eingegeben wurde zwischen 1000 und 9658 $plz = $_POST%%['%%plz']; $plz = plz($plz); %%//%%Ort speichern und überprüfen ob nur Buchstaben ev. mit Leerzeichen oder Bindestrich eingegeben wurden. $ort = $_POST%%['%%ort']; $ort = namen($ort); %%//%%Telefonnummer speichern und überprüfen Erlaubte Formate: 021-423-23-23 oder 021 423 23 23 $telefon = $_POST%%['%%telefon']; $telefon = telefon($telefon); %%//%%Handynummer speichern und überprüfen Erlaubte Formate: 079-423-23-23 oder 079 423 23 23 $mobile = $_POST%%['%%mobile']; $mobile = telefon($mobile); %%//%%Pflichtfelder überprüfen if ($anrede == "" || $nachname == "" || $vorname == "" || $strasse == "" %%|%%| $plz == "" || $ort == "") { echo "Die Felder Anrede, Nachname, Vorname, Strasse, PLZ und Ort müssen ausgefüllt sein!" ?>

Anrede*: Frau Herr Frau Herr
Nachname*: Hier fehlt was."; } ?>
Vorname*: Hier fehlt was."; } ?>
Strasse*: Hier fehlt was."; } ?>
PLZ*: ">Bitte gültige PLZ eingeben."; } ?>
Ort*: Hier fehlt was."; } ?>
Telefon:
Mobile:
info("Formular loeschen in kunden_verwalten.php abgesendet."); if (isset($_POST%%['%%kunde'])) { %%//%%in $kunden_id ist nun die Nummer des Radiobuttons, die gleich der Kunden-Id ist $kunden_id = $_POST%%['%%kunde']; $kundenarray = einzel_k($benutzer_id, $kunden_id, $log); ?>

Kundennummer:
Vorname:
Nachname:

info("Formular geloescht in kunden_verwalten.php abgesendet."); $benutzer_id = $_POST%%['%%benutzer_id']; $kunden_id = $_POST%%['%%kunden_id']; $kunden_nr = $_POST%%['%%kunden_nr']; $vorname = $_POST%%['%%vorname']; $nachname = $_POST%%['%%nachname']; %%//%%DB-Verbindung um die gewünschten Daten zu löschen k_loeschen($benutzer_id, $kunden_id, $log); %%//%%Damit die Seite neu geladen wird, nachdem gelöscht wurde. header("Location: kunden_verwalten.php"); } %%//%%Je nachdem ob admin oder normaler Benutzer eingeloggt ist, auf andere Seite. if(isset($_GET%%['%%benutzer_id'])) { echo "Zurück"; } else { echo "Zurück"; } ?>
© by Rafisa
logo_hochladen.php Logo hochladen

Die Handwerkerrechnung

1000000) { echo "Das Bild ist zu gross. "; $hochgeladen = 0; } %%//%% Überprüfung des Dateiformats if ($datei_ueberpruefen != "jpg" && $datei_ueberpruefen != "gif" && $datei_ueberpruefen != "png") { echo "Es sind nur Bilder erlaubt. "; $hochgeladen = 0; } %%//%% Überprüft ob $hochgeladen durch einen Fehler auf 0 gesetzt wurde. if ($hochgeladen == 0) { echo "Datei wurde nicht hochgeladen. "; } else { if (move_uploaded_file($_FILES["logo"]["tmp_name"], $datei)) { echo "Die Datei " . basename($_FILES["logo"]["name"]) . " wurde hochgeladen."; } else { echo "Es ist ein Fehler beim Hochladen aufgetreten. "; } } } ?>

Logo suchen und hochladen

Bilddatei wählen:
Zurück
© by Rafisa
rechnung.php info("Formular links in rechnung.php abgesendet."); $links = $_POST%%['%%links']; %%//%%fals kein Artikel gecheckt ist $artikel nicht gesetzt if (isset($_POST%%['%%artikel'])) { $artikel = $_POST%%['%%artikel']; %%//%%Inhalt der Checkboxen von Formular "links", nur der Index } $kundenwahl = $_POST%%['%%kundenwahl']; } ?> Neue Rechnung

Die Handwerkerrechnung

Zurück"; } else { echo "Zurück"; } ?>
\n"; if (isset($artikel)) { %%//%%$artikel ist erst gesetzt, falls dieses Formular schon abgesendet wurde $j = 0; $nicht_gecheckt = true; for ($i = 0; $i < count($artikelarray); $i++) { for ($j = 0; $j < count($artikel); $j++) { if ($i == $artikel[$j]) { $nicht_gecheckt = false; } } if ($nicht_gecheckt) { echo " " . utf8_encode($artikelarray[$i]%%['%%beschreibung']) . "
\n"; } else { echo " " . utf8_encode($artikelarray[$i]%%['%%beschreibung']) . "
\n"; } $nicht_gecheckt = true; } } else %%{//%%beim ersten Laden ungechecktes Formular darstellen for ($i = 0; $i < count($artikelarray); $i++) { echo " " . utf8_encode($artikelarray[$i]%%['%%beschreibung']) . "
\n"; } } %%//%%Liste um Kunde auszuwählen $kundenarray = alle_k($benutzer_id, $log); ?>
\n"; %%//%%Adresse des Kunden anzeigen %%//%%DB-Verbindung $kundenarray = einzel_k($benutzer_id, $kundenwahl, $log); if (isset($kundenarray[0])) { echo "
"; echo "
"; echo "
"; echo "
"; } else { echo "
"; } %%//%%Ende Adresse des Kunden %%//%%Zähler für Rechnungsnummer $firmenarray = einzel_f($benutzer_id, $log); $rg_nr = $firmenarray[0]%%['%%rg_nr'] + 1; echo "Rechnungsnummer
"; %%//%%Spaltentitel echo ""; echo ""; echo ""; echo ""; echo "
\n"; %%//%%Tabelleninhalt if (isset($_POST%%['%%links']) && isset($_POST%%['%%artikel'])) { %%//%%$artikel ist der von Formular links erzeugte Array. Darin sind nur die Indexnummern der gecheckten Felder, z.B 1,2 %%//%%$artikelarray ist der Array von der DB eingelesen for ($i = 0; $i < count($artikel); $i++) { $j = $artikel[$i]; echo ""; echo ""; echo ""; echo ""; echo "
\n"; } } ?>
© by Rafisa
rechnungen_verwalten.php Rechnungen verwalten

Die Handwerkerrechnung

"; echo "\n"; %%//%% Es werden alle Zeilen aus dem Verzechnis /rechnungen ausgelesen %%//%% und in einem Dropdown angezeigt. $auslesen = opendir("rechnungen"); echo "
"; closedir($auslesen); %%//%%Ende Verzeichnis auslesen echo ""; echo ""; %%//%%Ausgewählte Datei öffnen if (isset($_POST%%['%%anzeigen'])) { $log->info("Formular anzeigen in rechnungen_verwalten.php abgesendet."); $ausgewaehlte_rg = $_POST%%['%%rechnung']; echo "
"; echo ""; echo "
"; } %%//%%Je nachdem ob admin oder normaler Benutzer eingeloggt ist, auf andere Seite. if(isset($_GET%%['%%benutzer_id'])) { echo "Zurück"; } else { echo "Zurück"; } ?>
© by Rafisa
fpdf_tabelle.php _noHF = TRUE; } function Footer() { %%//%% 1,5 cm über dem unteren Seitenrand positionieren $this->SetY(-15); %%//%% Schriftart Arial, kursiv in Größe 8 definieren $this->SetFont%%('%%Arial', 'I', 8); %%//%% Ausgabe des Fusszeilentextes, nur wenn Variabel noHF TRUE ist. if ($this->_noHF == FALSE) { $this->Cell(0, 10, 'Seite ' . $this->PageNo() . %%'/{%%nb}', 0, 0, 'C'); } } function SetWidths($w) { %%//%%Set the array of column widths $this->widths = $w; } function SetAligns($a) { %%//%%Set the array of column alignments $this->aligns = $a; } function Row($data) { %%//%%Calculate the height of the row $nb = 0; for ($i = 0; $i < count($data); $i++) { $nb = max($nb, $this->NbLines($this->widths[$i], $data[$i])); } $h = 5 * $nb; %%//%%Issue a page break first if needed $this->CheckPageBreak($h); %%//%%Draw the cells of the row for ($i = 0; $i < count($data); $i++) { $w = $this->widths[$i]; $a = isset($this->aligns[$i]) ? $this->aligns[$i] : 'L'; %%//%%Save the current position $x = $this->GetX(); $y = $this->GetY(); %%//%%Draw the border %%//%%$this->Rect($x, $y, $w, $h); %%//%%Print the text $this->MultiCell($w, 5, $data[$i], 0, $a); %%//%%Put the position to the right of the cell $this->SetXY($x + $w, $y); } %%//%%Go to the next line $this->Ln($h); } function CheckPageBreak($h) { %%//%%If the height h would cause an overflow, add a new page immediately if ($this->GetY() + $h > $this->PageBreakTrigger) { $this->AddPage($this->CurOrientation); } } function NbLines($w, $txt) { %%//%%Computes the number of lines a MultiCell of width w will take $cw = &$this->CurrentFont%%['%%cw']; if ($w == 0) { $w = $this->w - $this->rMargin - $this->x; } $wmax = ($w - 2 * $this->cMargin) * 1000 / $this->FontSize; $s = str_replace("r", %%''%%, $txt); $nb = strlen($s); if ($nb > 0 and $s[$nb - 1] == "n") { $nb--; } $sep = -1; $i = 0; $j = 0; $l = 0; $nl = 1; while ($i < $nb) { $c = $s[$i]; if ($c == "n") { $i++; $sep = -1; $j = $i; $l = 0; $nl++; continue; } if ($c == ' ') { $sep = $i; } $l+=$cw[$c]; if ($l > $wmax) { if ($sep == -1) { if ($i == $j) { $i++; } } else { $i = $sep + 1; } $sep = -1; $j = $i; $l = 0; $nl++; } else { $i++; } } return $nl; } } datenbank.php fatal("Verbindungsfehler : $fehler"); exit(); } if (!mysqli_select_db($db_verbindung, $db)) { %%//%%echo "DB nicht vorhanden."; $log->fatal("DB nicht vorhanden."); } return $db_verbindung; } %%/*%% * Funktion um einen SQL-Befehl auszuführen * Wird nur von Funktionen in dieser Datei gebraucht * @param $db_verbindung string $sql string $log string * @return nichts %%*/%% function sql_ausfuehren($db_verbindung, $sql, $log) { $sql_ausfuehren = mysqli_query($db_verbindung, $sql); if (!$sql_ausfuehren) { $fehler = mysqli_error($db_verbindung); %%//%%echo "sql Fehler: ".$fehler; $log->fatal("sql Fehler: " . $fehler); } } %%/*%% * Funktionen zu "Benutzer" * %%/*%% *Funktion in der alle Benutzernamen aus der Datenbank in einen Array gespeichert werden. * Wird in benutzer_einfuegen.php gebraucht * @param $log string * @return $benutzerarray array mit allen Benutzernamen %%*/%% function benutzer_namen($log){ $tabelle = "benutzer"; $benutzerarray = array(); $db_verbindung = verbindung($log); $sql = "SELECT i_benutzer FROM $tabelle"; sql_ausfuehren($db_verbindung, $sql, $log); if ($db_ergebnis = mysqli_query($db_verbindung, $sql)) { $i = 0; while ($zeile = mysqli_fetch_object($db_ergebnis)) { $benutzerarray[$i] = $zeile->i_benutzer; $i++; } mysqli_free_result($db_ergebnis); } mysqli_close($db_verbindung); return $benutzerarray; } %%/*%% * Funktion in der alle Benutzer aus der Datenbank in einen Array gespeichert werden. * Wird in index.php, benutzer_einfuegen.php und benutzer_verwalten.php gebraucht * @param $log string * @return $benutzerarray array mit allen Benutzerdaten(BenutzerID, Benutzername und Passwort) %%*/%% function alle_b($log) { $tabelle = "benutzer"; $benutzerarray = array(); $db_verbindung = verbindung($log); $sql = "SELECT * FROM $tabelle"; sql_ausfuehren($db_verbindung, $sql, $log); if ($db_ergebnis = mysqli_query($db_verbindung, $sql)) { $i = 0; while ($zeile = mysqli_fetch_object($db_ergebnis)) { $benutzerarray[$i] = array( 'benutzer_id' => $zeile->benutzer_id, 'i_benutzer' => $zeile->i_benutzer, 'i_pw' => $zeile->i_pw); $i++; } mysqli_free_result($db_ergebnis); } mysqli_close($db_verbindung); return $benutzerarray; } %%/*%% * Funktion um einen Benutzer in der Datenbank zu speichern * Wird in benutzer_einfuegen.php gebraucht * @param $i_benutzer string $i_pw string $log string * @return nichts %%*/%% function benutzer_erstellen($i_benutzer, $i_pw, $log) { $tabelle = "benutzer"; $db_verbindung = verbindung($log); $sql = "INSERT INTO $tabelle (i_benutzer, i_pw) VALUES %%('%%$i_benutzer','$i_pw');"; sql_ausfuehren($db_verbindung, $sql, $log); mysqli_close($db_verbindung); } %%/*%% * Funktion um einen bestimmten Benutzer auszulesen * Wird in benutzer_verwalten.php gebraucht * @param $benutzer_id int $log string * @return $benutzerarray array mit den Daten eines Benutzers(BenutzerID und Benutzername) %%*/%% function einzel_b($benutzer_id, $log) { $tabelle = "benutzer"; $benutzerarray = array(); $db_verbindung = verbindung($log); $sql = "SELECT * FROM $tabelle WHERE benutzer_id = $benutzer_id"; sql_ausfuehren($db_verbindung, $sql, $log); if ($db_ergebnis = mysqli_query($db_verbindung, $sql)) { $zeile = mysqli_fetch_object($db_ergebnis); $benutzerarray[0] = array( 'benutzer_id' => $zeile->benutzer_id, 'i_benutzer' => $zeile->i_benutzer); mysqli_free_result($db_ergebnis); } mysqli_close($db_verbindung); return $benutzerarray; } %%/*%% * Funktion um Daten eines bestimmten Benutzers zu ändern * Wird in benutzer_verwalten.php und pw_aendern.php gebraucht * @param $benutzer_id int $i_pw string $log string * @return nichts %%*/%% function b_aendern($benutzer_id, $i_pw, $log) { $tabelle = "benutzer"; $db_verbindung = verbindung($log); $sql = "UPDATE $tabelle SET i_pw='$i_pw' WHERE benutzer_id=$benutzer_id"; $sql = utf8_decode($sql); sql_ausfuehren($db_verbindung, $sql, $log); mysqli_close($db_verbindung); } %%/*%% * Funktion um einen bestimmten Benutzer aus der Datenbank zu löschen * Wird in benutzer_verwalten.php gebraucht * @param $benuzter_id int $log string * @return nichts %%*/%% function b_loeschen($benutzer_id, $log) { $tabelle = "benutzer"; $db_verbindung = verbindung($log); $sql = "DELETE FROM $tabelle WHERE benutzer_id = $benutzer_id"; sql_ausfuehren($db_verbindung, $sql, $log); mysqli_close($db_verbindung); } %%/*%% * Funktion um Benutzer zu überprüfen * Wird in benutzer_ueberpruefen.php gebraucht * @param $log string * @return $benutzerarray array mit Benutzername und Passwort %%*/%% function benutzer_ueberpruefen($log) { $tabelle = "benutzer"; $benutzerarray = array(); $db_verbindung = verbindung($log); $sql = "SELECT * FROM $tabelle"; sql_ausfuehren($db_verbindung, $sql, $log); if ($db_ergebnis = mysqli_query($db_verbindung, $sql)) { $i = 0; while ($zeile = mysqli_fetch_object($db_ergebnis)) { $benutzerarray[$zeile->i_benutzer] = $zeile->i_pw; $i++; } } return $benutzerarray; } %%/*%% * Funktionen zu "Firma" * * Funktion um Firmendaten in Datenbank zu speichern * Wird in firma_einfuegen.php gebraucht * @param $benuzter_id int $firma string $logo string $branche string * $strasse string $plz int $ort string $telefon string $moblie string * $fax string $email string $homepage string $mwst_nr string $konto string $log string * @return nichts %%*/%% function f_einfuegen($benutzer_id, $firma, $logo, $branche, $strasse, $plz, $ort, $telefon, $mobile, $fax, $email, $homepage, $mwst_nr, $konto, $log) { $tabelle = "firma"; $db_verbindung = verbindung($log); $sql = "INSERT INTO $tabelle (benutzer_id, firma, logo, branche, strasse, plz, ort, telefon, mobile,fax, email, homepage, mwst_nr, konto) VALUES ($benutzer_id, '$firma', '$logo', '$branche','$strasse',$plz, '$ort','$telefon','$mobile','$fax', '$email','$homepage','$mwst_nr', '$konto');"; %%//%%Umlaute umwandeln damit sie in DB richtig sind $sql = utf8_decode($sql); sql_ausfuehren($db_verbindung, $sql, $log); mysqli_close($db_verbindung); } %%/*%% * Funktion die alle Firmen und deren Daten in einen Array speichert * Wird in firmen_verwalten.php und menue_admin.php gebraucht * @param $log string * @return $firmenarray array mit den Firmendaten(BenutzerID, Name, Logo, Branche, * Strasse, PLZ, Ost Telefon, Mobile, Fax, E-Mail, Homepage, MWST-Nummer, * Rechnungsnummer und Kontonummer) %%*/%% function alle_f($log) { $tabelle = "firma"; $firmenarray = array(); $db_verbindung = verbindung($log); $sql = "SELECT * FROM $tabelle ORDER BY firma ASC"; sql_ausfuehren($db_verbindung, $sql, $log); if ($db_ergebnis = mysqli_query($db_verbindung, $sql)) { $i = 0; while ($zeile = mysqli_fetch_object($db_ergebnis)) { $firmenarray[$i] = array( 'benutzer_id' => $zeile->benutzer_id, 'firma' => $zeile->firma, 'logo' => $zeile->logo, 'branche' => $zeile->branche, 'strasse' => $zeile->strasse, 'plz' => $zeile->plz, 'ort' => $zeile->ort, 'telefon' => $zeile->telefon, 'mobile' => $zeile->mobile, 'fax' => $zeile->fax, 'email' => $zeile->email, 'homepage' => $zeile->homepage, 'mwst_nr' => $zeile->mwst_nr, 'rg_nr' => $zeile->rg_nr, 'konto' => $zeile->konto); $i++; } mysqli_free_result($db_ergebnis); } mysqli_close($db_verbindung); return $firmenarray; } %%/*%% * Funktion um die Daten einer bestimmten Firma auszulesen * Wird in druck.php, druck_orange.php, rechnungen_verwalten.php, rechnung.php * firma_verwalten.php, firmen_verwalten.php und menue.php gebraucht * @param $benutzer_id int $log string * @return $firmenarray array mit den Firmendaten(BenutzerID, Name, Logo, Branche, * Strasse, PLZ, Ost Telefon, Mobile, Fax, E-Mail, Homepage, MWST-Nummer, * Rechnungsnummer und Kontonummer) %%*/%% function einzel_f($benutzer_id, $log) { $tabelle = "firma"; $firmenarray = array(); $db_verbindung = verbindung($log); $sql = "SELECT * FROM $tabelle WHERE benutzer_id = $benutzer_id"; sql_ausfuehren($db_verbindung, $sql, $log); if ($db_ergebnis = mysqli_query($db_verbindung, $sql)) { $zeile = mysqli_fetch_object($db_ergebnis); %%//%%isset Benutzer_id überprüfen, weil sonst Notice wenns leer ist if (isset($zeile->benutzer_id)) { $firmenarray[0] = array( 'benutzer_id' => $zeile->benutzer_id, 'firma' => $zeile->firma, 'logo' => $zeile->logo, 'branche' => $zeile->branche, 'strasse' => $zeile->strasse, 'plz' => $zeile->plz, 'ort' => $zeile->ort, 'telefon' => $zeile->telefon, 'mobile' => $zeile->mobile, 'fax' => $zeile->fax, 'email' => $zeile->email, 'homepage' => $zeile->homepage, 'mwst_nr' => $zeile->mwst_nr, 'rg_nr' => $zeile->rg_nr, 'konto' => $zeile->konto); mysqli_free_result($db_ergebnis); } } mysqli_close($db_verbindung); return $firmenarray; } %%/*%% * Funktion um Firmendaten einer bestimmten Firma zu ändern * Wird in firmen_verwalten.php und firma_verwalten.php gebraucht * @param $benuzter_id int $firma string $logo string $branche string * $strasse string $plz int $ort string $telefon string $moblie string * $fax string $email string $homepage string $mwst_nr string $konto string $log string * @return nichts %%*/%% function f_aendern($benutzer_id, $firma, $logo, $branche, $strasse, $plz, $ort, $telefon, $mobile, $fax, $email, $homepage, $mwst_nr, $konto, $log) { $tabelle = "firma"; $db_verbindung = verbindung($log); $sql = "UPDATE $tabelle SET firma='$firma', logo='$logo', branche='$branche', strasse='$strasse', plz=$plz, ort='$ort', telefon='$telefon', mobile='$mobile', fax='$fax', email='$email', homepage='$homepage', mwst_nr='$mwst_nr', konto='$konto' WHERE benutzer_id=$benutzer_id"; %%//%%Umlaute umwandeln damit sie in DB richtig sind $sql = utf8_decode($sql); sql_ausfuehren($db_verbindung, $sql, $log); mysqli_close($db_verbindung); } %%/*%% * Funktion um eine bestimmte Firma zu löschen * Wird in firmen_verwalten.php und firma_verwalten.php gebraucht * @param $benutzer_id int $log string * @return nichts %%*/%% function f_loeschen($benutzer_id, $log) { $tabelle = "firma"; $db_verbindung = verbindung($log); $sql = "DELETE FROM $tabelle WHERE benutzer_id = $benutzer_id"; sql_ausfuehren($db_verbindung, $sql, $log); mysqli_close($db_verbindung); } %%/*%% * Funktionen zu "Kunde" * * Funktion um die Daten eines Kunden zu speichern * Wird in kunden_einfuegen.php gebraucht * @param $kunden_nr int $benutzer_id int $anrede string $nachname string * $vornamestring $strasse string $plz int $ort string $telefon string * $mobile string $log string * @return nichts %%*/%% function k_einfuegen($kunden_nr, $benutzer_id, $anrede, $nachname, $vorname, $strasse, $plz, $ort, $telefon, $mobile, $log) { $tabelle = "kunde"; $db_verbindung = verbindung($log); $sql = "INSERT INTO $tabelle (kunden_nr, benutzer_id, anrede, nachname, vorname, strasse, plz, ort, telefon, mobile) VALUES ($kunden_nr, $benutzer_id, '$anrede', '$nachname','$vorname','$strasse',$plz, '$ort','$telefon','$mobile');"; %%//%%Umlaute umwandeln damit sie in DB richtig sind $sql = utf8_decode($sql); sql_ausfuehren($db_verbindung, $sql, $log); mysqli_close($db_verbindung); } %%/*%% * Funktion in der die Daten aller Kunden einer bestimmten Firma in * einen Array gespeichert werden * Wird in kunden_verwalten.php und rechnung.php gebraucht * @param $benutzer_id inst $log string * @return $kundenarray array mit den Daten der Kunden(KundenID, Kundennummer, * BenutzerID, Anrede, Nachname, Vorname, Strasse, PLZ, Ort, Telefon und Mobile) %%*/%% function alle_k($benutzer_id, $log) { $tabelle = "kunde"; $kundenarray = array(); $db_verbindung = verbindung($log); $sql = "SELECT * FROM $tabelle WHERE benutzer_id = $benutzer_id"; sql_ausfuehren($db_verbindung, $sql, $log); if ($db_ergebnis = mysqli_query($db_verbindung, $sql)) { $i = 0; while ($zeile = mysqli_fetch_object($db_ergebnis)) { $kundenarray[$i] = array( 'kunden_id' => $zeile->kunden_id, 'kunden_nr' => $zeile->kunden_nr, 'benutzer_id' => $zeile->benutzer_id, 'anrede' => $zeile->anrede, 'nachname' => $zeile->nachname, 'vorname' => $zeile->vorname, 'strasse' => $zeile->strasse, 'plz' => $zeile->plz, 'ort' => $zeile->ort, 'telefon' => $zeile->telefon, 'mobile' => $zeile->mobile); $i++; } mysqli_free_result($db_ergebnis); } mysqli_close($db_verbindung); return $kundenarray; } %%/*%% * Funktion um die Daten eines bestimmten Kunden auszulesen * Wird in kunden_verwalten.php und rechnung.php gebraucht * @param $benutzer_id int $kunden_id int $log string * @return $kundenarray array mit den Daten(KundenID, Kundennummer, BenutzerID, * Anrede, Nachname, Vorname, Strasse, PLZ, Ort, Telefon und Mobile) %%*/%% function einzel_k($benutzer_id, $kunden_id, $log) { $tabelle = "kunde"; $kundenarray = array(); $db_verbindung = verbindung($log); $sql = "SELECT * FROM $tabelle WHERE benutzer_id = $benutzer_id AND kunden_id = $kunden_id"; sql_ausfuehren($db_verbindung, $sql, $log); if ($db_ergebnis = mysqli_query($db_verbindung, $sql)) { $zeile = mysqli_fetch_object($db_ergebnis); if (isset($zeile)) { $kundenarray[0] = array( 'kunden_id' => $zeile->kunden_id, 'kunden_nr' => $zeile->kunden_nr, 'benutzer_id' => $zeile->benutzer_id, 'anrede' => $zeile->anrede, 'nachname' => $zeile->nachname, 'vorname' => $zeile->vorname, 'strasse' => $zeile->strasse, 'plz' => $zeile->plz, 'ort' => $zeile->ort, 'telefon' => $zeile->telefon, 'mobile' => $zeile->mobile); } mysqli_free_result($db_ergebnis); } mysqli_close($db_verbindung); return $kundenarray; } %%/*%% * Funktion um die Daten eines bestimmten Kunden zu ändern * Wird in kunden_verwalten.php gebraucht * @param $kunden_nr int $benutzer_id int $anrede string $nachname string * $vornamestring $strasse string $plz int $ort string $telefon string * $mobile string $log string * @return nichts %%*/%% function k_aendern($kunden_id, $kunden_nr, $benutzer_id, $anrede, $nachname, $vorname, $strasse, $plz, $ort, $telefon, $mobile, $log) { $tabelle = "kunde"; $db_verbindung = verbindung($log); $sql = "UPDATE $tabelle SET kunden_id=$kunden_id, kunden_nr=$kunden_nr, benutzer_id=$benutzer_id, anrede='$anrede', nachname='$nachname', vorname='$vorname', strasse='$strasse', plz=$plz, ort='$ort', telefon='$telefon', mobile='$mobile' WHERE benutzer_id=$benutzer_id AND kunden_id = $kunden_id"; %%//%%Umlaute umwandeln damit sie in DB richtig sind $sql = utf8_decode($sql); sql_ausfuehren($db_verbindung, $sql, $log); mysqli_close($db_verbindung); } %%/*%% * Funktion um einen bestimmten Kunden zu löschen * Wird in kunden_verwalten.php gebraucht * @param $benutzer_id int $kunden_id int $log string * @return nichts %%*/%% function k_loeschen($benutzer_id, $kunden_id, $log) { $tabelle = "kunde"; $db_verbindung = verbindung($log); $sql = "DELETE FROM $tabelle WHERE benutzer_id = $benutzer_id AND kunden_id = $kunden_id"; %%//%%Umlaute umwandeln damit sie in DB richtig sind $sql = utf8_decode($sql); sql_ausfuehren($db_verbindung, $sql, $log); mysqli_close($db_verbindung); } %%/*%% * Funktion um den Zähler für die nächste Kundennummer zu erhöhen * Anhand der BenutzerID wird die Anzahl Zeilen dieser Firma * in der Tabelle kunde gezählt und um eins erhöht. * Diese Zahl wird in $kunden_nr gespeichert * Wird in kunden_einfuegen.php gebraucht * @param $benutzer_id int $log string * @return $kunden_nr int %%*/%% function k_nr_zaehler($benutzer_id, $log) { $tabelle = "kunde"; $kundenarray = array(); $db_verbindung = verbindung($log); $sql = "SELECT kunden_nr FROM $tabelle WHERE benutzer_id = $benutzer_id"; sql_ausfuehren($db_verbindung, $sql, $log); if ($db_ergebnis = mysqli_query($db_verbindung, $sql)) { %%//%%Initialisierung Kundenarray wegen max() $kundenarray = array("leer"); $i = 0; while ($zeile = mysqli_fetch_object($db_ergebnis)) { $kundenarray[$i] = $zeile->kunden_nr; $i++; } mysqli_free_result($db_ergebnis); %%//%%grösste Zahl im Array suchen und +1 für neue Kundennummer $kunden_nr = max($kundenarray) + 1; return $kunden_nr; } mysqli_close($db_verbindung); } %%/*%% * Funktionen zu "Artikel" * * Funktion um einen Artikel zu speichern * Wird in artikel_einfuegen.php gebraucht * @param $art_nr int $benutzer_id int $beschreibung string $einheit string * $preis_p_e float $log string * @return nichts %%*/%% function a_einfuegen($art_nr, $benutzer_id, $beschreibung, $einheit, $preis_p_e, $log) { $tabelle = "artikel"; $db_verbindung = verbindung($log); $sql = "INSERT INTO $tabelle (art_nr, benutzer_id, beschreibung, einheit, preis_p_e) VALUES ($art_nr, $benutzer_id, '$beschreibung','$einheit',$preis_p_e);"; %%//%%Umlaute umwandeln damit sie in DB richtig sind $sql = utf8_decode($sql); sql_ausfuehren($db_verbindung, $sql, $log); mysqli_close($db_verbindung); } %%/*%% * Funktion in der die Daten aller Artikel einer bestimmten Firma in * einen Array gespeichert werden * Wird in artikel_verwalten.php und rechnung.php gebraucht * @param $benutzer_id int $log string * @return $artikelarray array mit den Daten der Artikel(ArtikelID, Artikelnummer, * BenutzerID, Beschreibung, Einheit, Preis pro Einheit und Menge) %%*/%% function alle_a($benutzer_id, $log) { $tabelle = "artikel"; $artikelarray = array(); $db_verbindung = verbindung($log); $sql = "SELECT * FROM $tabelle WHERE benutzer_id = $benutzer_id"; sql_ausfuehren($db_verbindung, $sql, $log); if ($db_ergebnis = mysqli_query($db_verbindung, $sql)) { $i = 0; while ($zeile = mysqli_fetch_object($db_ergebnis)) { $artikelarray[$i] = array( 'art_id' => $zeile->art_id, 'art_nr' => $zeile->art_nr, 'benutzer_id' => $zeile->benutzer_id, 'beschreibung' => $zeile->beschreibung, 'einheit' => $zeile->einheit, 'preis_p_e' => $zeile->preis_p_e, 'menge' => $zeile->menge); $i++; } mysqli_free_result($db_ergebnis); } mysqli_close($db_verbindung); return $artikelarray; } %%/*%% * Funktion um Daten eines bestimmten Artikels auszulesen * Wird in artikel_verwalten.php gebraucht * @param $benutzer_id int $art_id int $log string * @return $artikelarray array mit den Daten der Artikel(ArtikelID, Artikelnummer, * BenutzerID, Beschreibung, Einheit, Preis pro Einheit und Menge) %%*/%% function einzel_a($benutzer_id, $art_id, $log) { $tabelle = "artikel"; $artikelarray = array(); $db_verbindung = verbindung($log); $sql = "SELECT * FROM $tabelle WHERE benutzer_id = $benutzer_id AND art_id = $art_id"; sql_ausfuehren($db_verbindung, $sql, $log); if ($db_ergebnis = mysqli_query($db_verbindung, $sql)) { $zeile = mysqli_fetch_object($db_ergebnis); $artikelarray[0] = array( 'art_id' => $zeile->art_id, 'art_nr' => $zeile->art_nr, 'benutzer_id' => $zeile->benutzer_id, 'beschreibung' => $zeile->beschreibung, 'einheit' => $zeile->einheit, 'preis_p_e' => $zeile->preis_p_e, 'menge' => $zeile->menge); mysqli_free_result($db_ergebnis); } mysqli_close($db_verbindung); return $artikelarray; } %%/*%% * Funktion um die Daten eines Artikels zu ändern * Wird in artikel_verwalten.php gebraucht * @param $art_nr int $benutzer_id int $beschreibung string $einheit string * $preis_p_e float $log string * @return nichts %%*/%% function a_aendern($benutzer_id, $art_id, $art_nr, $beschreibung, $einheit, $preis_p_e, $log) { $tabelle = "artikel"; $db_verbindung = verbindung($log); $sql = "UPDATE $tabelle SET art_id=$art_id, art_nr=$art_nr, benutzer_id=$benutzer_id, beschreibung='$beschreibung', einheit='$einheit', preis_p_e=$preis_p_e WHERE benutzer_id=$benutzer_id AND art_id = $art_id"; %%//%%Umlaute umwandeln damit sie in DB richtig sind $sql = utf8_decode($sql); sql_ausfuehren($db_verbindung, $sql, $log); mysqli_close($db_verbindung); } %%/*%% * Funktion um einen bestimmten Artikel zu löschen * Wird in artikel_verwalten.php gebraucht * @param $benutzer_id int $art_id int $log string * @return nichts %%*/%% function a_loeschen($benutzer_id, $art_id, $log) { $tabelle = "artikel"; $db_verbindung = verbindung($log); $sql = "DELETE FROM $tabelle WHERE benutzer_id=$benutzer_id AND art_id = $art_id"; sql_ausfuehren($db_verbindung, $sql, $log); mysqli_close($db_verbindung); } %%/*%% * Funktionen zu "Rechnung" * * Funktion um die Rechnungsnummer zu speichern * In rechnung.php wird in $rg_nr die Rechnungsnummer gespeichert anhand der * Daten aus der Tabelle firma Spalte rg_nr. Die Rechnungsnummer wird erst in die * Datenbank gespeichert, wenn die PDF-Datei erstellt wird. * Wird in druck.php und druck_orange.php gebraucht * @param $benutzer_id int $rg_nr int $log string * @return nichts %%*/%% function rg_nr_speichern($benutzer_id, $rg_nr, $log) { $tabelle = "firma"; $db_verbindung = verbindung($log); $sql = "UPDATE $tabelle SET rg_nr = $rg_nr WHERE benutzer_id = $benutzer_id"; sql_ausfuehren($db_verbindung, $sql, $log); mysqli_close($db_verbindung); } ?> db.php style.css %%/*%% * Dateiname: style.css * Style-Datei * @author Ingrid Betschart * @copyright 2016 Rafisa %%*/%% %%/*%% * #linkeseite wird in rechnung.php gebraucht. Im div mit dieser id werden alle * Artikel der Firma mit Checkboxen aufgelistet und ein Dropdown-Menü mit den * Kunden der Firma angezeigt. %%*/%% #linkeseite{ width:299px; height: 570px; overflow: scroll; background-color: #FFDEAD; float:left; border: 1px solid #000; } %%/*%% * #rechteseite wird in rechnung.php gebraucht. Im div mit dieser id wird * die Adresse des links ausgewählten Kunden und die ausgewählten Artikel angezeigt. %%*/%% #rechteseite{ width:896px; height: 570px; background-color: #FFDEAD; float:left; border: 1px solid #000; } body{ font-family: Arial,Helvetica,sans; } %%/*%% * äusserstes div %%*/%% #wrapper{ margin-left:auto; margin-right:auto; width:1200px; background-color: black; } %%/*%% * div mit der Kopfzeile %%*/%% #kopf{ background-color: #7CFC00; } %%/*%% * div mit dem Inhalt der Seite %%*/%% #inhalt{ background-color: #9370DB; height: 570px; } %%/*%% * wird bei menue_admin.php und menue.php anstelle von #inhalt verwendet. %%*/%% #inhaltStartseite{ background-color: #9370DB; height: 570px; background-image: url%%('%%../icons/geldsack.png'); background-repeat: no-repeat; background-position: 300px 100px; } %%/*%% * div mit der Fusszeile %%*/%% #fuss{ background-color: #87CEFA; font-size: 70% } %%/*%% * unbesuchter Link %%*/%% a:link { color: red; text-decoration: none; } %%/*%% * besuchter Link %%*/%% a:visited { color: green; text-decoration: none; } %%/*%% * mit Maus auf Link %%*/%% a:hover { color: hotpink; text-decoration: underline; background-color: lightgreen; } %%/*%% * ausgewählter Link %%*/%% a:active { color: blue; text-decoration: none; } %%/*%% * span wird gebraucht, um einen Text auszugeben, der angezeigt wird, wenn * ein Pflichtfeld nicht ausgefüllt wurde. %%*/%% span { color:red; } rg_mit_Testdaten.sql -- phpMyAdmin SQL Dump -- version 4.5.1 -- http://www.phpmyadmin.net -- -- Host: 127.0.0.1 -- Erstellungszeit: 09. Apr 2016 um 17:42 -- Server-Version: 10.1.10-MariaDB -- PHP-Version: 5.6.19 SET SQL_MODE = "NO_AUTO_VALUE_ON_ZERO"; SET time_zone = "+00:00"; %%/*%%!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT %%*/%%; %%/*%%!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS %%*/%%; %%/*%%!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION %%*/%%; %%/*%%!40101 SET NAMES utf8mb4 %%*/%%; -- -- Datenbank: `rg` -- -- -------------------------------------------------------- -- -- Tabellenstruktur für Tabelle `artikel` -- CREATE TABLE `artikel` ( `art_id` int(11) NOT NULL, `art_nr` int(11) NOT NULL, `benutzer_id` int(11) NOT NULL, `beschreibung` text NOT NULL, `einheit` varchar(255) NOT NULL, `preis_p_e` float NOT NULL, `menge` int(11) NOT NULL ) ENGINE=InnoDB DEFAULT CHARSET=latin1; -- -- Daten für Tabelle `artikel` -- INSERT INTO `artikel` (`art_id`, `art_nr`, `benutzer_id`, `beschreibung`, `einheit`, `preis_p_e`, `menge`) VALUES (1, 1, 2, 'Arbeitsstunden Maurer', 'h', 120.5, 0), (2, 2, 2, 'Pflastersteine', 'Stk', 10.5, 0), (3, 1, 3, 'Arbeitsstunden Maler', 'h', 70, 0), (4, 2, 3, 'Arbeitsstunden Ei', 'h', 5, 0), (5, 3, 3, 'Bemalte Ostereier', 'Stk', 5, 0), (10, 1, 5, 'Ümläüt', 'Stück', 4.5, 0), (11, 2, 5, 'neüe Ümläüte', 'Stück', 10.5, 0); -- -------------------------------------------------------- -- -- Tabellenstruktur für Tabelle `benutzer` -- CREATE TABLE `benutzer` ( `benutzer_id` int(11) NOT NULL, `i_benutzer` varchar(255) NOT NULL, `i_pw` varchar(255) NOT NULL ) ENGINE=InnoDB DEFAULT CHARSET=latin1; -- -- Daten für Tabelle `benutzer` -- INSERT INTO `benutzer` (`benutzer_id`, `i_benutzer`, `i_pw`) VALUES (1, 'admin', '202cb962ac59075b964b07152d234b70'), (2, 'maurer', '748596b6eb0bcf216908182d72cf738a'), (3, 'ei', '1ee2225a0118c6a8ff464cf2926cf352'), (5, 'umlaut', 'e4f7981a7e3b887516e863b95c969e50'); -- -------------------------------------------------------- -- -- Tabellenstruktur für Tabelle `firma` -- CREATE TABLE `firma` ( `benutzer_id` int(11) NOT NULL, `firma` varchar(255) NOT NULL, `logo` varchar(255) NOT NULL, `branche` varchar(255) NOT NULL, `strasse` varchar(255) NOT NULL, `plz` int(11) NOT NULL, `ort` varchar(255) NOT NULL, `telefon` varchar(255) NOT NULL, `mobile` varchar(255) NOT NULL, `fax` varchar(255) NOT NULL, `email` varchar(255) NOT NULL, `homepage` varchar(255) NOT NULL, `mwst_nr` varchar(255) NOT NULL, `rg_nr` int(11) NOT NULL, `konto` varchar(255) NOT NULL ) ENGINE=InnoDB DEFAULT CHARSET=latin1; -- -- Daten für Tabelle `firma` -- INSERT INTO `firma` (`benutzer_id`, `firma`, `logo`, `branche`, `strasse`, `plz`, `ort`, `telefon`, `mobile`, `fax`, `email`, `homepage`, `mwst_nr`, `rg_nr`, `konto`) VALUES (2, 'Maurerzwei', 'bild.png', 'Maurer', 'Weggassenstrasse 1', 1234, 'Hier', '041 222 33 44', '079 111 22 33', '041 222 33 40', %%''%%, %%''%%, 'CHE-098.098.098', 0, '98-876-5'), (3, 'MalerEi', 'logo.png', 'Maler', 'Dorfstrasse 123', 7777, 'Siebenhausen', '041 890 11 22', '079 890 66 55', '041 890 11 20', 'Malerei@hotmail.com', %%''%%, 'CHE-123.123.123', 0, '23-4563'), (5, 'Firma mit Ümläüten', 'öäü.png', 'Schräiner', 'Gässli 1', 6468, 'Ättighüüsä', '098 765 44 33', '078 123 44 55', '098 765 44 30', 'umlaut@firma.ch', 'http://www.php-kurs.com', 'CHE- 123.456.789', 0, '12-345-6'); -- -------------------------------------------------------- -- -- Tabellenstruktur für Tabelle `kunde` -- CREATE TABLE `kunde` ( `kunden_id` int(11) NOT NULL, `kunden_nr` int(11) NOT NULL, `benutzer_id` int(11) NOT NULL, `anrede` varchar(255) NOT NULL, `nachname` varchar(255) NOT NULL, `vorname` varchar(255) NOT NULL, `strasse` varchar(255) NOT NULL, `plz` int(11) NOT NULL, `ort` varchar(255) NOT NULL, `telefon` varchar(255) NOT NULL, `mobile` varchar(255) NOT NULL ) ENGINE=InnoDB DEFAULT CHARSET=latin1; -- -- Daten für Tabelle `kunde` -- INSERT INTO `kunde` (`kunden_id`, `kunden_nr`, `benutzer_id`, `anrede`, `nachname`, `vorname`, `strasse`, `plz`, `ort`, `telefon`, `mobile`) VALUES (1, 1, 2, 'Herr', 'Muster', 'Max', 'Musterstrasse 1', 1010, 'Musterlingen', '044 567 34 67', '089 567 45 23'), (2, 2, 2, 'Herr', 'Gronowski', 'Terence', 'Zuhause 12', 2345, 'IrgendInEinemKaff', %%''%%, %%''%%), (3, 1, 3, 'Frau', 'Informatikerin', 'keine', 'Gassenstrasse 453', 1212, 'Nirgends', %%''%%, %%''%%), (4, 2, 3, 'Herr', 'Tell', 'Wilhelm', 'Rathausplatz', 6460, 'Altdorf UR', %%''%%, %%''%%), (6, 1, 5, 'Herr', 'Löli', 'Blöödä', 'Gässli 2', 6468, 'Ättighüüsä', %%''%%, %%''%%), (7, 2, 5, 'Frau', 'Kündin', 'Neüe', 'Strasse 2', 1234, 'Hier', %%''%%, %%''%%); -- -- Indizes der exportierten Tabellen -- -- -- Indizes für die Tabelle `artikel` -- ALTER TABLE `artikel` ADD PRIMARY KEY (`art_id`), ADD KEY `benutzer_id` (`benutzer_id`); -- -- Indizes für die Tabelle `benutzer` -- ALTER TABLE `benutzer` ADD PRIMARY KEY (`benutzer_id`); -- -- Indizes für die Tabelle `firma` -- ALTER TABLE `firma` ADD PRIMARY KEY (`benutzer_id`), ADD KEY `benutzer_id` (`benutzer_id`); -- -- Indizes für die Tabelle `kunde` -- ALTER TABLE `kunde` ADD PRIMARY KEY (`kunden_id`), ADD KEY `benutzer_id` (`benutzer_id`); -- -- AUTO_INCREMENT für exportierte Tabellen -- -- -- AUTO_INCREMENT für Tabelle `artikel` -- ALTER TABLE `artikel` MODIFY `art_id` int(11) NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=12; -- -- AUTO_INCREMENT für Tabelle `benutzer` -- ALTER TABLE `benutzer` MODIFY `benutzer_id` int(11) NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=6; -- -- AUTO_INCREMENT für Tabelle `kunde` -- ALTER TABLE `kunde` MODIFY `kunden_id` int(11) NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=8; -- -- Constraints der exportierten Tabellen -- -- -- Constraints der Tabelle `artikel` -- ALTER TABLE `artikel` ADD CONSTRAINT `artikel_ibfk_1` FOREIGN KEY (`benutzer_id`) REFERENCES `firma` (`benutzer_id`) ON DELETE CASCADE ON UPDATE CASCADE; -- -- Constraints der Tabelle `firma` -- ALTER TABLE `firma` ADD CONSTRAINT `firma_ibfk_1` FOREIGN KEY (`benutzer_id`) REFERENCES `benutzer` (`benutzer_id`) ON DELETE CASCADE ON UPDATE CASCADE; -- -- Constraints der Tabelle `kunde` -- ALTER TABLE `kunde` ADD CONSTRAINT `kunde_ibfk_1` FOREIGN KEY (`benutzer_id`) REFERENCES `firma` (`benutzer_id`) ON DELETE CASCADE ON UPDATE CASCADE; %%/*%%!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT %%*/%%; %%/*%%!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS %%*/%%; %%/*%%!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION %%*/%%; 12. April 2016 Seite **9** von **115**