Unterthema: Weitere Artikel zum Scripting
Unterthema: Sicherheitsloch Scripting Host?
Unterthema: Listing MINI.VBS
Unterthema: Listing CLOSE.VBS
Unterthema: Listing DATUM.VBS
Unterthema: Listing WINDIR.VBS
Unterthema: Listing LOGBUCH.VBS
Unterthema: Listing FEHLER.VBS
Unterthema: Listing STARTBILD.VBS
Unterthema: Listing KONVERT.VBS
Unterthema: Listing DRUCKEN.VBS
Unterthema: Listing MSDOSSYS.VBS
Unterthema: Listing DOKU.VBS
Unterthema: Listing ICONS.VBS
Unterthema: Listing UMBENENNEN.VBS
Unterthema: Listing Benutzer.VBS
Unterthema: Listing SETUPDIR.VBS
Unterthema: Listing SAVE.VBS
Unterthema: Listing RESTORE.VBS
Unterthema: Listing Schriften
Unterthema: Listing EMAILZIP.VBS
Unterthema: Listing EMAILDAT.VBS
Bitte beachten Sie auch diese Ergänzung!
So mächtig der Windows Scripting Host ist - richtig durchgesetzt hat er sich noch nicht. Erstens bevorzugen viele Softwarefirmen ihre eigene Makrosprache, was die systemweite Verbreitung des WSH hemmt, und zweitens macht es Microsoft den Anwendern unnötig schwer, sich damit anzufreunden. Im Unterschied zu AppleScript von MacOS beispielsweise gibt es beim Scripting Host kein Recorderprogramm, das alle Arbeitsschritte aufnimmt und in Skripte oder Makros schreibt, die der Benutzer anschließend editieren und erweitern kann. Unter Windows muß man statt dessen jedes Skript `zu Fuß´ programmieren, eine für Einsteiger oft zu hohe Hürde. Im Vergleich mit AppleScript fehlt auch eine Möglichkeit herauszufinden, wie sich andere Programme fernsteuern lassen und welche Befehle sie kennen. Doch auch unter Windows kommt man schnell weiter, wenn man die nötigen Tricks kennt - die verraten wir Ihnen in diesem Heft.
Auf den kommenden 13 Seiten geht es zunächst darum, wie man den Scripting Host und damit Windows 95, 98 und NT selbst steuert. Die anschließenden Artikel zeigen an den Beispielen Internet Explorer/Netscape Communicator, Word und Corel Draw/Photo Paint, wie man auch in externen Applikationen nützliche Funktionen nachrüstet und mit Skripten oder Makros Zeit spart. Im Artikel ab Seite 134 stellen wir Ihnen überdies Makroprogramme vor, welche sozusagen die Lücke schließen, die Microsoft seit 1995 offenläßt: der Windows-Makrorecorder wurde ja mit Version 3.11 eingestellt. Wie man andere Programme mit Skriptsprachen automatisiert, zeigen wir in loser Folge in späteren Ausgaben.
Die abgedruckten Beispiele können Sie auf Anhieb einsetzen, ob Sie nun sporadisch oder regelmäßig mit den jeweiligen Programmen arbeiten. Damit Sie sie nach Ihren Bedürfnissen ergänzen oder umschreiben können, haben wir alle wesentlichen Funktionen in Kommentarzeilen erläutert. Freilich brauchen Sie die Listings nicht abzutippen, alle stehen bei heise online zum Download bereit [11].
In diesem ersten Artikel finden sich 20 Skripte für den Windows-Explorer; vom Mehrzeiler etwa für abwechselnde Startbilder oder ein Logbuch, das alle Windows-Starts samt Datum, Uhrzeit und Benutzernamen protokolliert, über recht aufwendige Programme, die zum Beispiel zeigen, wie man eine WYSIWYG-Liste aller installierten Schriften erstellt oder die komplizierte Registry fehlerfrei modifiziert, bis hin zu ausgewachsenen Applikationen. Mit zwei Skripten kann man beispielsweise alle Dateiverknüpfungen sichern und bei einem Schaden wiederherstellen - Windows selbst kennt keine derartigen Rettungsmaßnahmen; bislang mußte man im Notfall das System oder wenigstens das beschädigte Programm neu installieren.
Der Scripting Host läßt sich in unterschiedlichen Sprachen programmieren; von Haus aus versteht er JScript und VBScript. Wo erfahrene Programmierer gerne JScript bevorzugen, weil die Skripte dann auch in JavaScript-fähigen Web-Browsern laufen, ist VBScript als Verwandter des Visual-Basic-Dialekts wesentlich leichter zu erlernen. Deshalb verwenden wir es auch als Grundlage für unsere Beispiele.
Skripte lassen sich mit jedem beliebigen Texteditor eintippen und bearbeiten; das mitgelieferte Notepad reicht vollkommen aus. Freilich können Sie auch eine Textverarbeitung verwenden, allerdings müssen Sie die Dateien dann `pur´, also ohne Auszeichnungen speichern. JScripts müssen die Dateiendung `.JS´ tragen, VBScript-Skripte `.VBS´. Dann führt der Scripting Host die Programme automatisch aus, wenn man sie per Doppelklick öffnet.
Der WSH enthält jedoch keine Befehle, um etwa auf das Dateisystem zuzugreifen oder irgendwelche anderen System-Eigenschaften zu verändern (siehe auch Kasten `Sicherheitsloch Skripting Host?´ auf Seite 100). Wirklich effiziente Skriptaktionen scheinen also zunächst zu scheitern.
Glücklicherweise läßt sich aber der Sprachschatz von VBScript fast beliebig erweitern. Mit dem Befehl CreateObject kann man nämlich die Funktionsaufrufe anderer Software benutzen, indem man Instanzen ihrer Objekte anlegt - ob es sich dabei um ActiveX-Objekte von Windows, um selbstgeschriebene oder um Programme anderer Hersteller handelt. Das Prinzip ist simpel: CreateObject("Name des Objektes") liefert ein Handle auf das Objekt zurück, das man per Set einer Variablen zuweist. Anschließend benutzt man diese Variable, um auf die Eigenschaften und Methoden des Objektes zuzugreifen, nachzuvollziehen etwa in dem simplen Skript WINDIR.VBS, welches den Pfad des Windows-Ordners ausgibt.
Als Teil der WSH-Installation kommen bereits einige Objekte mit, die man prächtig `mißbrauchen´ kann, unter anderem `Scripting.FileSystem-Object´, `WScript.Shell´ und `WScript.Network´. Das erste bereichert den Scripting Host um eine Vielzahl von Dateisystem-Befehlen, das zweite liefert Kommandos, um externe Programme auszuführen, Verknüpfungen zu organisieren oder auch die Registry zu bearbeiten, und das dritte fügt Netzwerkbefehle hinzu. All diese Objekte kommen auch in unseren Beispiel-Skripts zum Einsatz.
Trotzdem kann man mit den beiden Tools viele Juwelen ausgraben. Wer damit zum Beispiel die Microsoft Internet Controls öffnet, die mit dem Internet Explorer 4 installiert werden, findet das Objekt `Shell´, das vielfältige Befehle mitbringt, um die Windows-Oberfläche fernzusteuern. Man spricht es über CreateObject("Shell.Application") an und kann so in wenigen Zeilen beispielsweise das Skript MINI.VBS programmieren, das alle Fenster des Explorers per MinimizeAll-Aufruf minimiert und den Blick auf den Desktop freigibt. Ist die Arbeit darauf erledigt, klickt man einfach auf den OK-Button des zugehörigen Fensters, um die Fenster wieder sichtbar zu machen (UndoMinimizeAll).
Wer etwas tiefer in dieses System einsteigt und sich die Objekte und deren Zusammenspiel näher anschaut, kann sogar Automationsskripte wie CLOSE.VBS erstellen: Es schließt automatisch alle geöffneten Explorer-Fenster.
Um komplette Applikationen, wie etwa Excel, fernzusteuern, muß man sich natürlich zunächst einen Überblick darüber verschaffen, welche Applikationen überhaupt Automatisierungsschnittstellen bereitstellen und wie diese aussehen. Die dazu nötigen Werkzeuge bringt VisualBasic selbst in der kostenlosen Control Creation Edition mit. Eine Liste aller im System registrierten Klassenbibliotheken fördert der Befehl `Project - References´ zutage. Um die gewünschten in das aktuelle Projekt einzufügen und damit auch für den Object Browser zugänglich zu machen, markiert man das Kästchen vor dem jeweiligen Eintrag. Öffnet man danach den Object Browser (über das View-Menü oder einen Druck auf F2), so kann man sie in der Liste links oben auswählen und bekommt in der Liste `Classes´ alle Objekte angezeigt, die sich für eine Automatisierung eignen. Die Eigenschaften, Methoden und Ereignisse eines Objektes offenbaren sich rechts unten, nachdem man eine Klasse anklickt.
Nun sind die reinen Namen der Elemente oft nicht ausreichend. Programme, die eine offizielle Automatisierungsschnittstelle zur Verfügung stellen - dazu gehören unter anderem alle Microsoft-Office-Anwendungen - installieren daher neben der Klassenbibliothek auch eine Hilfe-Datei, deren Einträge der Object Browser durch einen Druck auf F1 oder das entsprechende Symbol zur Anzeige bringt.
Der Grund für diesen unverhofften Softwaresegen liegt in einer recht unbekannten Verwandtschaft: Der Windows Scripting Host ist im Grunde nichts anderes als die lokale Version der Active Server Pages, einem Mechanismus, der im Internet-Information-Server von Windows NT zum Einsatz kommt. Active Server Pages, die man an der Extension .ASP erkennt, benutzen serverseitige VBScript- und JScript-Programme, um die Webseiten dynamisch zu generieren, sobald der Anwender sie abruft.
Dabei handelt es sich um exakt dieselbe Programmiersprache, die auch der WSH verwendet. Erweiterungsmodule für ASP funktionieren deshalb in aller Regel auch mit dem Windows Scripting Host und liefern so eine schier unüberschaubare Vielfalt von Zusatzbefehlen für eigene WSH-Skripte. Und umgekehrt können Sie Ihre WSH-Skripte auch direkt zur ASP-Programmierung benutzen, doch beachten Sie die Sicherheitslücken, die sich da auftun.
Auch wenn die Erfinder des Scripting Hosts zunächst aus Sicherheitsgründen jeglichen Dateizugriff aus dem Sprachschatz gestrichen hatten, sind alle wichtigen Befehle quasi durch die Hintertür wieder eingewandert. Über das FileSystemObject läßt sich das gesamte Dateisystem des Rechners steuern. Erster Einsatz: ein Anmeldeprotokoll für Windows.
Eine entscheidende Rolle spielt der Befehl OpenTextFile, der Textdateien zum Lesen oder Schreiben öffnet. Per I/O-Modus 8 teilt man ihm mit, daß man neue Zeilen ans Textende anfügen möchte (Append). Im I/O-Modus 1 dagegen, dem Standardwert, läßt sich eine Datei mit OpenTextFile nur lesen, aber nicht verändern. Der dritte Parameter, den das Logbuch verwendet, vbTrue, sorgt dafür, daß die Datei neu angelegt wird, falls sie noch nicht existiert. Über WriteLine schließlich schreibt das Skript seine Textzeilen in die Datei.
WSH-Skripte, die man häufiger benötigt, sollte man als Kontextmenü-Eintrag definieren; dann stehen sie stets auf Mausklick parat. Um etwa das Fehlerskript auf die rechte Maustaste zu legen, muß man es mit dem Dateityp von VB-Skripten verknüpfen. Den zuständigen Dialog `Ordneroptionen´ erreicht man vom Ansicht-Menü eines beliebigen Explorer-Fensters aus; bei Windows 98 zusätzlich über `Einstellungen´ im Startmenü. Öffnen Sie das Register `Dateitypen´ und wählen Sie aus der Liste den Eintrag `Skriptdatei für VBScript´. Klicken Sie auf Bearbeiten, anschließend auf Neu. Ins obere Feld des Fensters `Neuer Vorgang´ gehört der Name, unter dem Sie später den neuen Kontextmenü-Befehl sehen möchten - etwa `Fehler suchen´. Im unteren Feld folgt der Befehlsaufruf, zum Beispiel WSCRIPT.EXE C:\SCRIPTS\FEHLER.VBS "%L". Hinter WSCRIPT.EXE verbirgt sich der eigentliche Scripting Host. Das Programm muß dem Skriptnamen vorangestellt werden, weil VBS-Dateien für sich allein genommen nicht ausführbar sind. Die Systemvariable "%L" enthält später den langen Namen der Datei, über deren Kontextmenü der Anwender den Befehl aufgerufen hat. Diese Variable kann das VBS-Programm über WScript.Arguments abfragen. Fortan steht in jedem Menü, das sich per Klick auf eine Skriptdatei über die rechte Maustaste öffnet, der neue Eintrag `Fehler suchen´.
Das Skript STARTBILD.VBS aktiviert bei jedem Windows-Start ein anderes Bild und kopiert es in die Datei C:\LOGO.SYS - die lädt Windows als Startbild, sobald es sie vorfindet. (Gibt es diese Datei nicht, bevorzugt Windows seit Version 95b die Bitmap, die in C:\IO.SYS steht.) Am besten plazieren Sie das Skript in der Autostartgruppe, so daß es nach einem Windows-Start immer gleich das Bild für den nächsten Start eintragen kann.
Legen Sie einen Ordner C:\BILDER an und kopieren Sie all Ihre Lieblingsbilder hinein - mindestens aber eines, das zu LOGO.SYS mutieren kann. Der Ordner darf keine anderen Dateien enthalten. Ein individuelles Startbild, das Sie nicht verlieren möchten, kopieren Sie einfach vor dem ersten Start des Skriptes in den BILDER-Ordner, dann nimmt es an dem zufälligen Austauschprozedere teil. Funktioniert das Ganze hingegen gar nicht, ist bei Ihnen vermutlich die Startbildoption in der MSDOS.SYS-Datei abgeschaltet. Mit dem untenstehenden Skript MSDOSSYS.VBS können Sie das kurzerhand ändern: Tragen Sie LOGO=1 anstelle von LOGO=0 ein.
Beim Austausch von Texten zwischen unterschiedlichen Betriebssystemen gehen Sonderzeichen und deutsche Umlaute verloren, weil beispielsweise DOS, Windows und MacOS unterschiedliche Zeichencodes verwenden. Die Lösung: Das Skript KONVERT.VBS konvertiert fehlerhafte Sonderzeichen und sogar ganze Wörter oder Zeichenfolgen automatisch. In der Grundform wandelt das Skript die deutschen Umlaute von DOS-ASCII nach Windows-ANSI um. Man kann es aber leicht an andere Betriebssysteme anpassen oder für ganz andere Konvertierungsaufgaben verwenden, zum Beispiel um Umlaute in HTML-Sonderzeichen umzuwandeln, etwa per text = Replace(text, "ö", "ö").
Die Bedienung ist kinderleicht, weil das Skript die offiziellen Öffnen- und Speichern-Dialogfenster von Windows nutzt. Nachdem es die Datei eingelesen hat, ersetzt es per Replace beliebige Zeichencodes oder Textstrings. Anschließend speichert es die konvertierte Datei unter dem gewünschten Namen wieder ab.
Wenn Sie gleich viele hundert Dateien in einem Aufwasch konvertieren möchten, nehmen Sie - natürlich - ein Skript. Wie so etwas im Detail funktioniert, zeigt das Skript `Fortlaufende Seriennummern als Dateinamen´ weiter unten.
Um den Kommandozeileninterpreter zu starten, benutzt das Skript den Run-Befehl des WScript.Shell-Objektes, der ein beliebiges Programm startet. Übergibt man etwa `Run command.com /c dir /on /og´, lädt der Interpreter und startet sogleich den Dir-Befehl. Die Optionen /on und /og sorgen für die alphabetisch sortierte Liste. Um weitere Funktionen kennenzulernen, können Sie per `Dir /?´ eine Übersicht aller Optionen des Dir-Kommandos anfordern.
Das Ergebnis des Dir-Befehls wird in eine Datei umgeleitet, die das Skript anschließend über OpenTextFile öffnet, liest, konvertiert und per CreateTextFile wieder in die Datei zurückschreibt. Da es sich um eine Textdatei handelt, wird diese automatisch vom gewählten Texteditor, üblicherweise Notepad, geladen - das Skript braucht dazu wiederum per Run lediglich die Textdatei aufzurufen. Auch dieses Skript bietet sich als Kontextmenü-Erweiterung an. Dazu gehen Sie vor wie beim Skript `Fehler jagen´, verknüpfen das Skript aber mit dem Dateityp `Ordner´.
Die Systemdatei MSDOS.SYS ist auch für Windows lebensnotwendig, weil sie elementare Details des Windows-Starts regelt. Da sie normalerweise mit den Attributen `Schreibgeschützt´ und `Versteckt´ vor Änderungen geschützt ist, kostet es etliche Klicks, bevor man Änderungen vornehmen kann. Das Skript MSDOSSYS.VBS zeigt, wie es einfacher geht: Es befreit die Datei von allen Schutzattributen, lädt den Inhalt im Editor und restauriert die Schutzattribute anschließend wieder.
Das Prinzip ist simpel. GetFile spricht die Datei an; Attributes liefert die augenblicklichen Attribute als Bitmaske. Wichtig: Nur vier Attribute haben Schreib/Lese-Status. Die übrigen Attribute dürfen nicht verändert werden, weil der Scripting Host sonst mit einer Zugriffsverletzung reagiert. Das Skript zeigt, wie man diese umgeht - vor dem Setzen von Attributen werden alle Read-Only-Attribute mittels And Not gelöscht. Wer Attribute setzen möchte, verwendet den Or-Operator.
Bei diesem Skript lohnt sich zudem ein Blick auf den Run-Befehl, der Notepad startet. Der dritte Parameter lautet vbTrue und sorgt dafür, daß das Skript so lange angehalten wird, bis Notepad wieder beendet ist. So ist es möglich, die Attribute nach der Änderung im Editor wieder in den Ursprungszustand zurückzuversetzen.
Seit dem Internet Explorer 4 können endlich auch Ordner individuelle Icons tragen. Leider gibt es hierfür kein benutzerfreundliches Werkzeug; Microsoft hat diese interessante Möglichkeit offenbar für die eigenen Produkte reserviert. Das stellt das Skript ICONS.VBS ab.
Als Icon-Quelle können beliebige Systembibliotheken dienen: MORICONS.DLL, PROGMAN.EXE, SHELL32.DLL ... Auch ICO-Dateien und selbstgemalte Icons kommen in Frage: Im Malprogramm die Bildgröße auf 32 x 32 Punkte begrenzen und dann das Icon als Bitmap-Grafik mit der Dateiextension .ICO speichern. Freilich funktioniert auch dieses Skript am bequemsten, wenn man es als Kontextmenü-Erweiterung für den Dateityp Ordner definiert.
Es fragt zuerst nach dem Ordnernamen und dem Dateityp, um den sich das Skript kümmern soll, zum Beispiel `JPG´. Anschließend kann man ein Prefix eingeben, also eine Zeichenfolge, die der automatischen Seriennummer vorangestellt wird (`Bild´). Ohne Prefix-Angabe erhalten die Dateien eine reine Seriennummer als neuen Dateinamen. Das Skript ermittelt alle in Frage kommenden Dateien im angegebenen Ordner und speichert die Liste der Dateinamen im Variablenfeld dateiliste.
Die Architektur ist simpel: Der Ordner wird über GetFolder geöffnet und mittels for each datei in ordner.files Datei für Datei durchsucht - in der Reihenfolge, wie das Skript die Dateien vorfindet. Das FileSystemObject liefert über GetBaseName den Dateinamen und über GetExtensionName die Dateiendung zurück.
Durch einen kleinen Trick erweitern sich die Anwendungsmöglichkeiten des Skripts zusätzlich: Es beginnt stets mit der Seriennummer 0 und ermittelt in einer do-while...loop-Schleife automatisch, ob es bereits eine Datei mit der gerade aktuellen Seriennummer gibt. Falls ja, überspringt es diese Seriennummer und geht zur nächsten über. Kommen also neue Dateien hinzu, numeriert das Skript einfach weiter. Löscht man Dateien aus dem Ordner, dann füllt das Skript die dadurch entstandenen Lücken in den Seriennummern wieder auf. So erhält man stets eine durchgehende Reihe von Seriennummern. Bereits konvertierte Dateinamen werden nicht verändert.
Weil beim Vergleich die Groß- und Kleinschreibung keine Rolle spielen soll, vereinheitlicht das Skript die Schreibweise. Mit der Variable modus haben Sie die Wahl zwischen Klein- oder Großbuchstaben. Von diesem Zusatzeffekt profitieren Web-Autoren, die ausschließlich mit Kleinbuchstaben in Dateinamen arbeiten wollen. Falls Ihr Windows übrigens Dateinamen in Großbuchstaben nicht darstellt, ist die Option `Namen in Großbuchstaben ermöglichen´ in den Explorer-Einstellungen deaktiviert (Register `Ansicht´ im Dialog `Ordneroptionen´ unter Einstellungen im Startmenü).
Da das Skript nach der Sicherheitsabfrage unter Umständen große Mengen von Dateien umbenennt, sollte man es nicht allzu sorglos einsetzen und nur Dateien in eigenen, selbst angelegten Ordnern umbenennen. Daß EXE-Programme oder DLL-Bibliotheken umbenannt werden, verhindert das Skript von selbst.
Das Skript BENUTZER.VBS ändert die Benutzerdaten einer Windows-Installation. Wer sich zum Beispiel bei der Installation vertippt hat, kann den Fehler so im nachhinein korrigieren - andernfalls übernehmen viele Programme bei ihrer Installation immer wieder die alten Angaben aus der Registry.
Ähnlich wichtig ist das Skript SETUPDIR.VBS. Es gibt Ihnen die Freiheit, selbst zu entscheiden, wo die Windows-Installationsdateien liegen. Sobald man beispielsweise ein Laufwerk nachrüstet, kann die Installations-CD-ROM einen anderen Laufwerksbuchstaben tragen. Dann stellt Windows jedesmal, wenn Komponenten nachzuinstallieren sind, wieder das falsche Laufwerk ein. Noch praktischer wird das Skript, wenn Sie die CAB-Dateien der Windows-CD auf die lokale Festplatte kopieren, um auch später ohne Windows-CD nach- oder umkonfigurieren zu können.
Weil der Scripting Host keine Möglichkeit enthält, die Namen von Registry-Schlüsseln abzufragen, geht das Programm einen Umweg: Es exportiert den gesamten Registry-Inhalt per REGEDIT in eine Textdatei und wertet diese aus.
Möchten Sie künftig eine zerbrochene Datei-Programm-Zuordnung reparieren oder eine veränderte rückgängig machen, würde es genügen, die passende REG-Datei aus dem Ordner C:\BACKUPS aufzurufen. Dies wäre allerdings nur eine Notlösung, denn erstens können REG-Dateien nur Einträge in die Registry hineinschreiben, aber keine vorhandenen Einträge löschen. Zweitens hätten Sie auf diese Weise keine Möglichkeit, die bestehende Datei-Programm-Zuordnung zu sichern, bevor sie durch die REG-Datei verändert würde.
Der Sicherheit halber speichert es die aktuelle Registry-Information als eigenständige Sicherungskopie unter einem frei wählbaren Namen, so daß man sie jederzeit und risikolos wiederherstellen kann. Damit dieses Skript das vorangegangene ansprechen kann, um die aktuelle Datei-Programm-Verknüpfung zu sichern, müssen beide Skripte im selben Ordner liegen. Vor dem Einlesen der REG-Informationen über REGEDIT löscht das Skript die vorhandenen Schlüssel und sorgt so dafür, daß die Datei-Programm-Zuordnungen exakt in der Form wiederbelebt werden, wie sie gesichert wurden.
Das Skript EMAILZIP.VBS demonstriert zunächst, wie man mit Hilfe der neuen Befehle bequem ZIP-Dateien als EMail-Attachments verschicken kann - direkt vom Explorer aus, ohne speziellen EMail-Client. Passen Sie das Skript an Ihre persönlichen Verhältnisse an: `From´ steht für Ihre EMail-Adresse, `FromName´ für Ihren Namen. Unter `Host´ sollten Sie die Adresse des SMTP-Servers bei Ihrem Provider eintragen; das Skript verwendet stellvertretend den von CompuServe.
Nach dem Start fragt das Programm nach dem Namen der ZIP-Datei, die es versenden soll, nach der EMail-Adresse des Empfängers sowie nach dem Betreff (Subject) der zugehörigen Nachricht. Richtig praktisch wird das Skript allerdings erst, wenn man es ins Kontextmenü für ZIP-Dateien integriert, um Dateien per Rechtsklick versenden zu können. Dazu geht man vor wie beim Skript FEHLER.VBS, wählt als verknüpften Dateityp entsprechend ZIP-Dateien, etwa die von WinZip. Als Namen des neuen Befehls kommt beispielsweise `als Email versenden´ in Frage, als Befehlsaufruf etwa WSCRIPT.EXE C:\SCRIPTS\EMAILZIP.VBS "%L".
Im Register `System DSN´ legen Sie per `Add´ respektive `Hinzufügen´ den Typ der Datenbank fest, eben etwa Microsoft Access. Im Feld Datenquellenname bestimmen Sie den Namen der Datenbank, über den der Scripting Host später die Datenbank ansprechen soll, zum Beispiel `Internet´. Klicken Sie zum Schluß auf Auswählen, und stellen Sie den Pfadnamen zu Ihrer Datenbank-Datei ein, die Namen und EMail-Adressen der Empfänger enthält, bei Access also eine MDB-Datei. Falls eine solche bei Ihnen bereits existiert, brauchen Sie nur die Feldnamen im Skript anzupassen. Andernfalls legt man einfach eine neue Datenbankdatei samt passender Tabelle `Emailversand´ und mindestens einem Feld für die Adressen namens `Email´ an.
Das Skript stellt zuerst eine Verbindung zu den vier ActiveX-Komponenten her, die es für seine Arbeit braucht: Datenbank, EMail, Dateisystem und Programmausführung. Anschließend bietet es die Möglichkeit, per Editor den EMail-Nachrichtentext zu verfassen. Dazu legt das Programm per CreateTextFile eine leere Textdatei an und ruft diese per Run auf - der Editor startet automatisch. Sobald die Nachricht gespeichert ist und der Editor wieder geschlossen wird, liest das Programm den Inhalt der Datei und verwendet die erste Zeile als EMail-Subject, den Rest als Nachricht.
Nun öffnet es die Systemdatenbank `Internet´ und formuliert eine Standard-SQL-Abfrage: SELECT * FROM Emailversand, um alle Felder der Tabelle Emailversand auszuwählen. Über Execute schickt es die Anweisung an die Datenbank. Zurückgeliefert wird ein Recordset mit dem Ergebnis, welches das Programm in einer Schleife ausliest und alle EMail-Adressen über AddAddress als Empfänger vermerkt. Danach füllt es die übrigen Felder des EMail-Formulars aus und schickt die EMail ab.
Natürlich ist dieses Programm nur ein einfaches Grundgerüst. Aber es läßt sich in vielfältiger Weise ausbauen. Denkbar wäre beispielsweise ein weiteres Feld in der die Datenbank-Tabelle, etwa `Privat´, das dann als Auswahlkriterium fungiert, um den Empfängerkreis der Massensendung einzuschränken. Die SQL-Anweisung müßte dann lauten: SELECT * FROM Emailversand WHERE Privat=1.
Weitere Verbesserungsmöglichkeiten: Statt die EMail per Editor zu verfassen, könnte sie auch direkt aus der Datenbank stammen. Oder die Adressen anderer Empfänger könnten für jeden einzelnen unsichtbar werden, indem anstelle von AddAddress der Befehl AddBCC verwendet würde. Dann würden die EMails als `Blind Carbon Copy´ verschickt. Oder Sie würden alle EMails einzeln versenden. Dazu böte sich der Reset-Befehl an, der die Empfängerliste nach jedem Versand leerte. Oder ...
[2] Dokumentation zu VBScript: http://msdn.microsoft.com/scripting/vbscript/download/vbsdoc.exe
[3] Dokumentation zu JScript: http://msdn.microsoft.com/scripting/jscript/download/jsdoc.exe
[4] HTML-Hilfe-Update: http://msdn.microsoft.com/isapi/gomscom.asp?Target=/workshop/author/htmlhelp/download.asp
[5] VBA Companion: http://www.apexsc.com/vbacompanion/download.html
[6] Microsoft Developer Library: http://msdn.microsoft.com/library/
[7] Visual Basic Control Creation Edition: http://msdn.microsoft.com/vbasic/downloads/cce/default.asp (als Gastentwickler registrieren)
[8] Tobias Weltner: Windows 98, Kraftpaket zum Durchstarten, Franzis-Verlag, ISBN 3-7723-5864-0
[9] http://msdn.microsoft.com/scripting/
[10] http://www.aspemail.com/
[11] http://www.heise.de/ct/ftp/listings.shtml
Browser und JavaScript | Seite 114 |
Word und VBA | Seite 118 |
Corel Draw/Photo Paint und CorelScript | Seite 126 |
Makroprogramme als Alternative | Seite 134 |
Beim Besuch solcher Seiten warnt der Internet Explorer lediglich mit einer unscheinbaren Dialogbox vor `möglicherweise unsicheren´ Inhalten. Diese Warnung sollte man nicht ignorieren, denn über diesen Schleichweg können Saboteure allen möglichen Schaden anrichten, zum Beispiel die Festplatten löschen, Paßwörter ausspionieren oder die Windows-Registry verändern.
Selbst wenn der WSH gar nicht installiert ist, bieten solche in Internetseiten eingebetteten VBScripte die Möglichkeit, Verbindung zu ActiveX-Komponenten Ihres Systems aufzunehmen und Unheil anzurichten. Das FileSystemObject beispielsweise, mit dem das gesamte Dateisystem offengelegt wird, befindet sich auch ohne WSH in jeder Windows-Installation, die den Internet Information Server (IIS) oder den Personal Webserver verwenden. Dieses gravierende Sicherheitsproblem betrifft damit sogar das vermeintlich sichere Windows NT. Um so wichtiger ist es, diese Sabotagemöglichkeiten konsequent abzuschalten und den Internet Explorer auf Normalbrowser-Niveau zu beschränken. Dazu genügt es, in der Systemsteuerung das Internet-Modul aufzurufen und auf das Register `Sicherheit´ zu klicken. Anschließend wählen Sie die Option `Angepasst´ und klicken auf Einstellungen. Deaktivieren Sie gegebenenfalls das `Initialisieren und Ausführen von ActiveX-Steuerelementen´.
set shell = CreateObject("Shell.Application") shell.MinimizeAll MsgBox "Klicken Sie auf OK, wenn Sie die Fenster zurückhaben möchten!" shell.UndoMinimizeAllKasten 4
set Shell = CreateObject("Shell.Application") for each window in shell.windows set parent = window.Application parent.Quit nextKasten 5
frage="Bitte geben Sie ein Datum ein, und ich verrate Ihnen den Wochentag!" datum=InputBox(frage) if isDate(datum) then antwort = "Der " & datum & " fällt auf einen " antwort = antwort + WeekdayName(Weekday(datum)) MsgBox antwort, vbInformation else antwort = datum & " ist kein gültiges Datum!" MsgBox antwort, vbExclamation end ifKasten 6
set WSHShell = CreateObject("WScript.Shell") windir = WSHShell.ExpandEnvironmentStrings("%WINDIR%") MsgBox "Ihr Windows-Ordner lautet: " & windirKasten 7
´ legt ein Anmeldelogbuch für Windows an set network = CreateObject("WScript.Network") ´ für UserName set fs = CreateObject("Scripting.FileSystemObject") ´ für Dateisystem logbuch = "C:\anmeldung.log" ´ Name des Logbuchs ´Logbuch im Append-Modus (8) öffnen und anlegen, falls es noch ´gar nicht existiert (vbTrue): set logfile = fs.OpenTextFile(logbuch, 8, vbTrue) ´Protokollzeile schreiben: now=Timestamp, UserName=Anmeldename logfile.WriteLine now & " Angemeldeter User: " & network.UserName logfile.closeKasten 8
´markiert fehlerhafte Zeile in einem Skript ´ Verbindung zu System-ActiveX-Modulen herstellen set WSHShell = CreateObject("WScript.Shell") ´ für Run-Befehl set fs = CreateObject("Scripting.FileSystemObject") ´ für Dateisystem set args = WScript.Arguments ´ für Argumente ´wurde der Name eines Skripts übergeben? if args.count=0 then datei=InputBox("Wie heißt die Skriptdatei, in der ein Fehler auftrat?") else datei=args(0) end if if not fs.FileExists(datei) then MsgBox datei & " existiert nicht!", vbExclamation WScript.Quit end if zeilenr=AskNumber ´ welche Zeile markieren? ´ Markierungsstring definieren markierung = string(20, "x") + " FEHLERHAFTE ZEILE " markierung = markierung + string(20, "x") ´Skriptdatei öffnen... set einlesen = fs.OpenTextFile(datei) ok=vbFalse neu = "" ´ enthält den neuen Skripttext mit Markierung ´... und zeilenweise einlesen. do until einlesen.atEndOfStream if einlesen.Line = zeilenr then ´ angegebene Zeile gefunden: Markierung einfügen neu = neu + "´" + markierung + vbNewLine neu = neu + einlesen.ReadLine + vbNewLine neu = neu + "´" + markierung + vbNewLine ok=vbTrue ´ Zeile wirklich gefunden! else ´ normale Zeile: falls alte Markierung, entfernen gelesen = einlesen.ReadLine if len(gelesen)=len(markierung)+1 then if not gelesen="´" + markierung then neu = neu + gelesen + vbNewLine end if else neu = neu + gelesen + vbNewLine end if end if loop einlesen.close if not ok and not zeilenr=0 then ´ angegebene Zeilennummer existiert nicht! MsgBox "Zeile " & zeilenr & " gibt es im Programm nicht!", vbExclamation WScript.Quit end if ´ Skriptdatei löschen und mit neuem Inhalt erneut schreiben set einlesen = fs.CreateTextFile(datei, vbTrue) einlesen.Write neu einlesen.close ´ falls Zeilen-Nr=0, dann nur alte Markierungen entfernen und Meldung if zeilenr=0 then MsgBox "Zeilenmarkierungen wurden aus Skript entfernt!", vbInformation else ´ ansonsten das Skript im Editor öffnen: WSHShell.Run "NOTEPAD.EXE " + datei end if function AskNumber ´fragt nach einer Zahl größer/gleich 0 AskNumber=-1 do while AskNumberKasten 9
´ aktiviert in zufälliger Reihenfolge neue Startbilder ´ Verbindung zu Dateisystembefehlen herstellen set fs = CreateObject("Scripting.FileSystemObject") bildarchiv = "C:\bilder" ´ hier lagern die Startbilder if not fs.FolderExists(bildarchiv) then ´ Ordner mit Startbildern existiert nicht! problem = bildarchiv + " existiert nicht. Legen Sie den Ordner an," problem = problem + "und speichern Sie darin Windows-Startbilder!" MsgBox problem, vbExclamation WScript.Quit end if set startbilder = fs.GetFolder(bildarchiv).files ´ Anzahl der vorhandenen Startbilder bestimmen: for each bild in startbilder anzahl = anzahl + 1 next if anzahl=0 then ´ gar keine Startbilder zu finden! problem=bildarchiv+" ist leer. Speichern Sie darin zuerst Startbilder!" MsgBox problem, vbExclamation WScript.Quit end if ´ neues Startbild per Zufall aussuchen zufallszahl = Zufall(1, anzahl) ´ dieses Bild heraussuchen for each bild in startbilder zufallszahl = zufallszahl - 1 if zufallszahl = 0 then ´ gefunden! Altes Startbild löschen, falls vorhanden if fs.FileExists("C:\LOGO.SYS") then fs.DeleteFile "C:\LOGO.SYS", vbTrue end if ´ neues Startbild aktivieren bild.Copy "C:\LOGO.SYS", vbTrue ´ Die nächste Zeile löschen, wenn Meldung stört! MsgBox bild.name & " wurde aktiviert!" exit for end if next function Zufall(min, max) ´ liefert eine Zufallszahl zwischen min und max randomize Zufall = Int(max * rnd) + min end functionKasten 10
´ konvertiert Textdateien von DOS-ASCII nach WIN-ANSI ´Verbindung mit Systemkomponenten aufnehmen set dialog = CreateObject("MSComDlg.CommonDialog")´Öffnen/Speichern-Dialog set fs = CreateObject("Scripting.FileSystemObject") ´Dateisystem ´Dialogfenster definieren dialog.Filter = "Alle Dateien (*.*)|*.*|txt-Dateien|*.txt|" dialog.FilterIndex = 2 ´ zweiter Filter (txt-Dateien) vorgewählt dialog.MaxFileSize = 250 ´ max. Dateinamen-Länge im Buffer dialog.CancelError = vbFalse ´ Abbrechen-Schaltfläche liefert Leerstring dialog.DialogTitle = "Zu konvertierende Datei aussuchen" dialog.InitDir = "C:\" dialog.ShowOpen dateiname = dialog.FileName if fs.FileExists(dateiname) then ´ Originaldatei einlesen MsgBox "Konversion kann je nach Dateigröße einige Minuten dauern!", _ vbInformation set datei = fs.OpenTextFile(dateiname) text = datei.ReadAll datei.close ´ Konversion der deutschen Umlaute text = Replace(text, chr(148), chr(246)) ´ö text = Replace(text, chr(132), chr(228)) ´ä text = Replace(text, chr(129), chr(252)) ´ü text = Replace(text, chr(153), chr(214)) ´Ö text = Replace(text, chr(142), chr(196)) ´Ä text = Replace(text, chr(154), chr(220)) ´Ü text = Replace(text, chr(225), chr(223)) ´ß ´ Zieldatei erfragen dialog.DialogTitle = "Konvertierte Datei speichern als" dialog.FileName = left(dateiname,InstrRev(dateiname,".")-1)+"_ANSI.txt" dialog.ShowSave dateiname = dialog.FileName if dateiname="" then MsgBox "Abbruch!", vbExclamation else ´ Konvertierten Text in Zieldatei schreiben set datei = fs.CreateTextFile(dateiname, vbTrue) datei.Write text datei.close MsgBox "Konvertierung beendet!", vbInformation end if else MsgBox "Abbruch!", vbExclamation end ifKasten 11
´druckt ein Ordnerlisting aus ´Zugriff auf ActiveX-Komponenten des Systems herstellen set WSHShell = CreateObject("WScript.Shell") ´ nötig für Run-Befehl set fs = CreateObject("Scripting.FileSystemObject") ´ Dateisystembefehle set args = WScript.Arguments ´ übergebene Argumente if args.Count=0 then ´keine Argumente übergeben? Dann Ordnernamen angeben! ordner = InputBox(_ "Geben Sie den Ordner an, dessen Inhalt gedruckt werden soll!") else ´ansonsten übergebenen Ordnernamen benutzen ordner = args(0) end if ´enthält das Ordnerlisting: tempdatei = "C:\TMP.TXT" ´per DOS-Befehl Ordner ausdrucken WSHShell.Run "command.com /c dir /on /og " + chr(34) + ordner + chr(34) _ + " > " + tempdatei, 0, vbTrue ´erfolgreich? Dann Datei lesen und ASCII-Umlaute in ANSI-Zeichen wandeln if fs.FileExists(tempdatei) then ´ Datei öffnen und komplett lesen set eingabe = fs.OpenTextFile(tempdatei) text = eingabe.ReadAll eingabe.close ´ ASCII-Zeichen ersetzen text = Replace(text, chr(148), chr(246)) text = Replace(text, chr(132), chr(228)) text = Replace(text, chr(129), chr(252)) text = Replace(text, chr(153), chr(214)) text = Replace(text, chr(142), chr(196)) text = Replace(text, chr(154), chr(220)) text = Replace(text, chr(225), chr(223)) ´ Datei mit konvertiertem Inhalt neu schreiben set ausgabe = fs.CreateTextFile(tempdatei, vbTrue) ausgabe.Write text ausgabe.close ´ Datei ausführen (startet automatisch Notepad) WSHShell.Run tempdatei end ifKasten 12
´ Demonstriert Dateiattribute am Beispiel von MSDOS.SYS: ´ Datei wird zur Bearbeitung freigegeben und im Notepad angezeigt, ´ sobald Notepad geschlossen wird, stellt Skript die Attribute wieder her ´ Zugriff auf Systemkomponenten herstellen set fs = CreateObject("Scripting.FileSystemObject") ´ Dateisystem set WSHShell = CreateObject("WScript.Shell") ´ Run-Befehl dateiname = "C:\MSDOS.SYS" Unlock dateiname ´ Schutzattribute aufheben, dann Datei öffnen WSHShell.Run "NOTEPAD " + dateiname, ,vbTrue Lock dateiname ´ Schutzattribute wiederherstellen MsgBox dateiname & " ist wieder schreibgeschützt und versteckt.", _ vbInformation sub Unlock(datei) ´entfernt die Attribute Schreibschutz/Versteckt/System if not fs.FileExists(datei) then MsgBox datei + " existiert nicht.", vbCritical WScript.Quit else set handle = fs.GetFile(datei) ´ 1=schreibgeschützt, 2=versteckt, 4=System, 32=Archiv handle.attributes = handle.attributes and not (1+2+4+8+16+64+128) end if end sub sub Lock(datei) ´setzt die Attribute wieder if not fs.FileExists(datei) then MsgBox datei + " existiert nicht.", vbCritical WScript.Quit else set handle = fs.GetFile(datei) ´ Bits 8+16+64+128 müssen vor dem Setzen gelöscht werden, weil ´ diese Bits readonly sind und bei Schreibversuch zum Fehler führen handle.attributes = handle.attributes and not (8+16+64+128) or (1+2+4) end if end subKasten 13
´ Löscht alle Einträge aus dem Dokumente-Menü, die nicht auf ´ Dateien der folgenden Typen verweisen: ´Zugriff auf ActiveX-Objekte des Systems set fs = CreateObject("Scripting.FileSystemObject") Set WshShell = Wscript.CreateObject("Wscript.Shell") ´ Erwünschte Dateiextensionen festlegen erlaubt = "doc;txt;bmp;html;htm" erlaubt = split(erlaubt, ";") ´ Variablenfeld mit Extensionen ´ Ordnername des Dokumente-Menüs herausfinden set dokumenu = fs.GetFolder(WshShell.SpecialFolders("Recent")) ´ Alle Dateien im Dokumente-Menü untersuchen... set dokumente = dokumenu.files for each link in dokumente ´... ist die Datei eine Verknüpfung? Extension = LNK? if lcase(fs.GetExtensionName(link.name)) = "lnk" then ´ ja: Verknüpfungsobjekt anlegen, um an Details zu kommen set linkobj = WshShell.CreateShortcut(link.path) ´ wie lautet die Extension der Zieldatei dieser Verknüpfung? extension = lcase(fs.GetExtensionName(linkobj.TargetPath)) ´ ist die Extension eine der "erwünschten" Extensionen? behalten = vbfalse for check = 0 to ubound(erlaubt) if extension = lcase(erlaubt(check)) then behalten=vbtrue exit for end if next if not behalten then ´ nein: also Verknüpfung aus Dokumente-Menü löschen link.delete vbtrue end if end if nextKasten 14
´ Individuelle Ordnericons (für Win98/IE4) ´ Zugang zu Systemkomponenten herstellen set args = Wscript.Arguments ´ übergebene Argumente set WSHShell = CreateObject("WScript.Shell") ´ für Run-Befehl set fs = CreateObject("Scripting.FileSystemObject") ´ Dateisystem-Befehle if args.Count=0 then ordnername = InputBox("Geben Sie den Pfadnamen des Ordners ein, " _ & "dem Sie ein neues Icon geben möchten!") else ordnername = args(0) end if ´ Windows-Ordner ermitteln win = WSHShell.ExpandEnvironmentStrings("%WINDIR%") + "\" frage1 = "Wie heißt der Pfadname der Icon-Bibliothek?" frage2 = "Wie lautet die Kennzahl des Icons?" iconfile = InputBox(frage1,,win + "PROGMAN.EXE") iconnumber = InputBox(frage2,,0) ´ speziell angepaßte DESKTOP.INI generieren und in Ordner legen OrdnerIcon ordnername, iconfile, iconnumber sub OrdnerIcon(ordner, icon, nr) ´existiert der Ordner überhaupt? if not fs.FolderExists(ordner) then MsgBox ordner & " existiert nicht.", vbExclamation exit sub end if ´ DESKTOP.INI-Datei für den Ordner anlegen ini = ordner + "\desktop.ini" set ausgabe = fs.CreateTextFile(ini, vbTrue) ´ Icon-Informationen in DESKTOP.INI schreiben: ausgabe.WriteLine "[.ShellClassInfo]" ausgabe.WriteLine "IconFile=" + iconfile ausgabe.WriteLine "IconIndex=" + iconnumber ausgabe.close ´ Attribute des Ordners setzen set ordner = fs.GetFolder(ordner) attribute = ordner.Attributes attributeoff = attribute and not (4+8+16+64+128) attributeon = attribute and not (8+16+64+128) or 4 ordner.attributes = attributeoff info = "Neue Icons werden erst nach Aktualisierung des Explorers sichtbar." _ + vbCr + "Dazu bitte eine freie Stelle des Desktops anklicken und dann" _ + vbCr + "auf [F5] drücken." MsgBox info, vbInformation ordner.attributes = attributeon end subKasten 15
´ersetzt die Dateinamen eines bestimmten Dateityps innerhalb eines Ordners ´durch fortlaufende Seriennummern ´Variablen zwingend deklarieren, um Tippfehler zu vermeiden option explicit dim dateiliste(10000) ´Liste der gefundenen zutreffenden Dateinamen dim fs ´ Referenz zum FileSystemObject dim frage ´ Fragen an den Benutzer dim ordner ´ Dateiordner, der die Dateien enthält dim prefix ´ Zeichenfolge, die vor der Seriennummer eingefügt wird dim ext ´ Extension (Dateityp), der gesucht werden soll dim counter ´ Anzahl gefundener Dateien des gewünschten Dateityps dim ordnerhandle ´ Handle auf den Ordner, der die Dateien enthält dim ordnername ´ genauer Pfadname des Ordners dim datei ´ Handle der Dateien im Ordner dim dateiname ´ Name der untersuchten Datei, ohne Pfad und Extension dim extension ´ Extension der untersuchten Datei (Dateityp) dim antwort ´ Antwort des Benutzers auf Abfragen dim zaehler ´ laufende Seriennummer dim schleife ´ Schleifenvariable dim digits ´ Anzahl der Stellen für die Seriennummer dim modus ´ 1=Dateiname in Kleinbuchstaben, 2=in Großbuchstaben counter = 0 digits = 4 modus = 2 ´Zugriff auf ActiveX-Objekte des Systems herstellen set fs = CreateObject("Scripting.FileSystemObject") ´ Angaben zur Konversion erfragen frage = "Welcher Ordner soll bearbeitet werden?" ordner = IB(frage, "Ordner", "C:\") ´ Existiert der angegebene Ordner überhaupt? if not fs.FolderExists(ordner) then MsgBox "Der Ordner " & ordner & " existiert nicht! Abbruch!", _ vbExclamation WScript.Quit end if frage = "Wie heißt die Dateiextension des Dateityps, den Sie " _ & "berücksichtigen wollen?" ext = replace(lcase(IB(frage, "Extension", "jpg")), ".", "") frage = "Bitte geben Sie das Prefix an, das als Dateiname verwendet " _ & "werden soll!" prefix = InputBox(frage, "Prefix", "datei") ´System-Dateitypen schützen if ext="exe" or ext="dll" or ext="sys" or ext="vxd" then MsgBox "Der Dateityp " & ext _ & " darf auf keinen Fall umbenannt werden!", vbCritical WScript.Quit end if ´ Ordner mit den Dateien öffnen set ordnerhandle = fs.GetFolder(ordner) ordnername = ordnerhandle.path ´ Jede Datei im Ordner untersuchen for each datei in ordnerhandle.files dateiname = fs.GetBaseName(datei.Name) extension = lcase(fs.GetExtensionName(datei.Name)) ´ richtiger Dateityp? if extension = ext then ´ noch kein Prefix zugeordnet? if not lcase(left(dateiname, len(prefix))) = lcase(prefix) _ or prefix="" then counter = counter + 1 dateiliste(counter) = datei.path end if end if next ´Ergebnis präsentieren frage = "Es wurden " & counter & " zutreffende " & ext _ & "-Dateien gefunden." + vbCr if counter = 0 then frage = frage + "Das Programm bricht ab!" MsgBox frage, vbInformation WScript.Quit else frage = frage+"Wollen Sie die Dateinamen durch Seriennummern ersetzen?" end if ´Soll wirklich konvertiert werden? antwort = MsgBox(frage, vbYesNo + vbQuestion) if antwort = vbYes then zaehler = 0 for schleife = 1 to counter dateiname = prefix & format(zaehler) & "." & ext do while fs.FileExists(ordnername + "\" + dateiname) zaehler = zaehler + 1 dateiname = prefix & format(zaehler) & "." & ext loop set datei = fs.GetFile(dateiliste(schleife)) if modus=1 then dateiname = lcase(dateiname) elseif modus=2 then dateiname = ucase(dateiname) end if datei.name = dateiname zaehler = zaehler + 1 next MsgBox "Erledigt!", vbInformation else MsgBox "Abbruch!", vbExclamation end if function IB(a, b, c) ´ entspricht der InputBox-Funktion, berücksichtigt aber die ´ Abbruch-Schaltfläche IB = InputBox(a, b, c) if IB="" then MsgBox "Abbruch!", vbInformation WScript.Quit end if end function function format(zahl) ´ formatiert eine Zahl durch vorangestellte "0" und erweitert die Zahl ´ auf diese Weise auf die in der Variablen digits festgelegten Stellen format = string(digits-len(cstr(zahl)), "0") & zahl end functionKasten 16
´ nachträglich Benutzernamen und Firma in der Registry ändern ´ ActiveX-Zugriff für Registry-Funktionen herstellen set WSHShell = CreateObject("WScript.Shell") key = "HKEY_LOCAL_MACHINE\Software\Microsoft\Windows\CurrentVersion" userkey = key + "\RegisteredOwner" firmakey = key + "\RegisteredOrganization" benutzer = InputBox("Benutzernamen ändern?", "Benutzer", _ WSHShell.RegRead(userkey)) firma = InputBox("Firmennamen ändern?", "Firma", _ WSHShell.RegRead(firmakey)) WSHShell.RegWrite userkey, benutzer WSHShell.RegWrite firmakey, firma antwort = MsgBox("Wollen Sie die Änderungen sofort kontrollieren?", _ vbYesNo + vbQuestion) if antwort = vbYes then WSHShell.Run "CONTROL.EXE sysdm.cpl"
set WSHShell = CreateObject("WScript.Shell") key = "HKEY_LOCAL_MACHINE\Software\Microsoft\Windows\CurrentVersion\" _ + "Setup\SourcePath" frage = "Windows-Installationsverzeichnis ändern?" aktuell = WSHShell.RegRead(key) neu = InputBox(frage,"Installationsverzeichnis", aktuell) if neu="" then MsgBox "Abbruch!", vbExclamation else WSHShell.RegWrite key, neu MsgBox "Aktuelles Installationsverzeichnis:" + vbCr + neu, vbInformation end ifKasten 18
set WSHShell = CreateObject("WScript.Shell") set fs = CreateObject("Scripting.FileSystemObject") set args = WScript.Arguments dir = "C:\backups" ´hier werden die Backups gelagert if not fs.FolderExists(dir) then fs.CreateFolder(dir) if args.count=0 then ´ Keine speziellen Argumente: also alle Dateiverknüpfungen sichern MsgBox "Lege Backups der Verknüpfungen an. " _ & "Das kann einige Minuten dauern!", vbInformation extensionen = ReadTypes for each dateityp in extensionen BackItup dateityp, 0 next else ´ nur die angegebene Dateiverknüpfung sichern BackItup(args(0)), 1 end if sub BackItup(ext, modus) ´sichert die angegebene Dateiverknüpfung als REG-Datei if not CheckKey("HKCR\" + ext + "\") then MsgBox "Der Schlüssel " & ext & " ist unbekannt!", vbExclamation exit sub end if on error resume next ´Dateiname für die Sicherheitskopie generieren timeStamp = date() & " " & replace(Time(),":","-") & " Uhr" name = Replace(ext,".","") + " vom " + timeStamp if modus=1 then name = _ InputBox("Geben Sie der Sicherheitskopie einen Namen!", "Name", name) regname = dir + "\" + name + ".reg" ´Informationen aus der Registry exportieren befehl = "REGEDIT.EXE /E " + chr(34) + regname + chr(34) _ + " HKEY_CLASSES_ROOT\" + ext WSHShell.Run befehl,0,vbTrue ´Programmschlüssel erfragen... prog = WSHShell.RegRead("HKCR\" + ext + "\") ´... und sichern, falls er existiert: if (not prog="") and checkKey("HKCR\" + prog + "\") then temp = "C:\tmp.txt" befehl = "REGEDIT.EXE /E " + temp + " " + chr(34) _ + "HKEY_CLASSES_ROOT\" + prog + chr(34) WSHShell.Run befehl,0,vbTrue ´aus den beiden separaten REG-Dateien eine kombinierte Datei erstellen set dateireg = fs.OpenTextFile(regname, 8) set progreg = fs.OpenTextFile(temp) progreg.SkipLine progreg.SkipLine do until progreg.atEndOfStream dateireg.WriteLine progreg.ReadLine loop dateireg.close progreg.close fs.DeleteFile temp end if end sub function CheckKey(key) ´prüft, ob ein Schlüssel in der Registry existiert on error resume next vorhanden = WSHShell.RegRead(key) if err0 then err.clear CheckKey=vbFalse else CheckKey= vbTrue end if end function function ReadTypes ´liest alle Dateitypen aus der Registry aus regexport = "C:\HKCR.HID" WSHShell.Run "REGEDIT.EXE /E "+regexport+" HKEY_CLASSES_ROOT", 0, vbTrue ´_________________________________________________________________________ set eingabe = fs.OpenTextFile(regexport) ´_________________________________________________________________________ do until eingabe.atEndOfStream gelesen = eingabe.ReadLine if len(gelesen)>20 then if left(gelesen,20) = "[HKEY_CLASSES_ROOT\." then gelesen = mid(gelesen, 20) if Instr(gelesen, "\")=0 then gelesen = left(gelesen, len(gelesen)-1) ext = ext + gelesen + ";" end if end if end if loop eingabe.close fs.DeleteFile regexport, vbTrue ext = left(ext, len(ext)-1) ReadTypes = Split(ext, ";") end functionKasten 19
set fs = CreateObject("Scripting.FileSystemObject") set WSHShell = CreateObject("WScript.Shell") dir = "C:\backups" ext = InputBox("Wie lautet die Extension der Datei, " _ + "die Sie wiederherstellen wollen?", "Extension") ext = lcase(Replace(ext, ".", "")) optionen = FindeBackups(dir) antwort = MsgBox("Möchten Sie die aktuelle Verknüpfung sichern?", _ vbQuestion + vbYesNo) if antwort = vbYes then ordner=left(WScript.ScriptFullName,inStrRev(WScript.ScriptFullName,"\")) WSHShell.Run ordner + "save.vbs ." + ext, , vbTrue end if subkey = WSHShell.RegRead("HKCR\." + ext + "\") wshShell.RegDelete("HKCR\." + ext + "\") wshShell.RegDelete("HKCR\" + subkey + "\") wshshell.Run "REGEDIT.EXE /S " + chr(34) + optionen + chr(34), 0, vbTrue MsgBox "Alte Zuordnung ist wiederhergestellt!" function FindeBackups(verzeichnis) set backups = fs.GetFolder(verzeichnis) resultat = "" optionen = "Diese Backups stehen zur Verfügung: " + vbCr zaehler = 0 for each backup in backups.files extbackup = lcase(left(backup.Name, len(ext))) if extbackup + " vom" = ext + " vom" then zaehler = zaehler + 1 resultat = resultat + backup.path + ";" optionen = optionen + "[" & zaehler & "] " _ + fs.GetBaseName(backup.Name) + vbCr end if next if len(resultat)>0 then resultat = left(resultat, len(resultat)-1) dateinamen = Split(resultat, ";") if zaehler=0 then MsgBox "Keine Backups gefunden!", vbExclamation WScript.Quit elseif zaehler=1 then FindeBackups = dateinamen(0) else optionen = optionen + "Bitte wählen Sie eine Option aus!" FindeBackups = _ dateinamen(IB(optionen, "Bitte auswählen!", "1", 1, zaehler)-1) end if end function function IB(a, b, c, d, e) ´ liefert eine Zahl zwischen d und e zurück do while eingabe<d or eingabe>e if assist then MsgBox "Ihre Antwort muß zwischen " & d _ & " und " & e & " liegen!", vbInformation assist = vbTrue antwort = InputBox(a,b,c) if antwort="" then MsgBox "Abbruch!", vbExclamation WScript.Quit end if if isNumeric(antwort) then eingabe=CInt(antwort) loop IB = eingabe end function
´ gibt Schriftprobe der installierten Schriften aus ´Kontakt zu ActiveX-Komponenten herstellen set WSHShell = CreateObject("WScript.Shell") ´ für Run-Befehl set fs = CreateObject("Scripting.FileSystemObject") ´ für Dateisystem schriftarten = GetFonts ´liefert Liste der installierten Schriften Konzentrieren ´entfernt Schriftfamilien Sortieren ´sortiert alphabetisch Schriftprobe ´generiert die HTML-Schriftprobe sub Sortieren Melde "Sortiere Schriften..." for x=0 to ubound(schriftarten) for y=x to ubound(schriftarten) if schriftarten(x)>schriftarten(y) then temp = schriftarten(x) schriftarten(x) = schriftarten(y) schriftarten(y) = temp end if next next end sub sub Konzentrieren Melde "konzentriere auf Schriftschnitte..." ´ Schriftfamilien-Attribute, die ausgeblendet sein sollen: familien = "extra bold,bolditalic,italic,bold,light,fett,kursiv," _ & "oblique,normal" familien = Split(familien,",") for x=0 to ubound(schriftarten) for y=0 to ubound(familien) if Instr(lcase(schriftarten(x)), familien(y))>0 then ´ überflüssige Font-Familie: löschen! schriftarten(x)="" exit for end if next next end sub sub Schriftprobe Melde "Schriftprobe generieren..." probe = "C:\schriften.htm" probetext = InputBox("Bitte Probetext eingeben!", "Probetext", _ "ABCDabcdÄÖÜäöüß 1234 Schriftprobe") probesize = InputBox("Bitte Schriftgröße der Probe festlegen!", _ "Größe", "25") if isNumeric(probesize) then ´ gültige Größenangabe eingegeben probesize = CInt(probesize) else ´ Vorgabe verwenden probesize=25 end if set ausgabe = fs.CreateTextFile(probe, vbTrue) for each schrift in schriftarten if schrift<>"" then if probetext="" then zusatztext = schrift else Print ausgabe, "Schriftart " + schrift + "<BR>" end if probezeile = "<p style=" + chr(34) + "font-family: " + schrift _ + "; font-size: " & probesize & "pt" + chr(34) + ">" _ + probetext + zusatztext + "</p><hr>" Print ausgabe, probezeile end if next WSHShell.Run probe end sub function GetFonts Melde "Stelle Schriften aus der Registry zusammen. Geduld..." ´ Schriftenliste aus der Registry auslesen tempdatei = "C:\SCHRIFT.TXT" key=" HKEY_LOCAL_MACHINE\Software\Microsoft\Windows\CurrentVersion\Fonts" WSHShell.Run "REGEDIT.EXE /E " + tempdatei + key, 0, vbTrue ´ Schriftenliste auswerten set eingabe = fs.OpenTextFile(tempdatei) do until eingabe.atEndOfStream gelesen = eingabe.ReadLine if len(gelesen)>1 then if left(gelesen,1) = chr(34) then ´ Zeile enthält eine Schrift... schrift = Split(gelesen, "=") name = replace(schrift(0),chr(34), "") position = InStr(name, "(") ´ Schrifttyp feststellen... if position>0 then typ = mid(name, position+1) typ = lcase(left(typ, len(typ)-1)) name = left(name, position-1) else typ="truetype" end if if typ="truetype" then GetFonts = GetFonts + name + ";" end if end if end if loop eingabe.close fs.DeleteFile tempdatei, vbTrue GetFonts = Split(left(GetFonts, len(GetFonts)-1), ";") end function function Melde(was) ´ Meldung für 1 Sekunde anzeigen: WSHShell.Popup was, 1 end function sub Print(obj, txt) obj.WriteLine txt + "<BR>" end subKasten 21
´ ZIP-Dateien per Rechtsklick versenden ´ Zugriff auf ActiveX-Module set fs = CreateObject("Scripting.FileSystemObject") ´Dateisystem Set Mail = CreateObject("Persits.MailSender") ´Email-Versand Set args = WScript.Arguments ´übergebene Argumente ´ wurden Argumente übergeben? if args.count=0 then ´ nein, also nach ZIP-Dateinamen fragen frage = "Geben Sie den kompletten Pfadnamen Ihrer ZIP-Datei an!" zipdatei = InputBox(frage, "Pfadname") ´ existiert die angegebene Datei überhaupt? if not fs.FileExists(zipdatei) then MsgBox zipdatei&" existiert nicht oder ist keine Datei!",vbExclamation WScript.Quit end if else ´ ja, also ZIP-Dateinamen aus dem Argument benutzen zipdatei = args(0) end if ´ Individuelle Email-Einstellungen: Mail.Host = "smtp.site1.csi.com" ´ SMTP-Mailserver Mail.From = "anonym@anonym.net" ´ Email-Absender Mail.FromName = "anonym" ´ Absender-Name ´ Adressinformationen abfragen frage = "Geben Sie die Empfänger-Email-Adresse ein!" email = InputBox(frage, "Empfänger") Mail.AddAddress email frage = "Geben Sie eine Überschrift für Ihre Email-Sendung an!" Mail.Subject = InputBox(frage, "Überschrift") Mail.AddAttachment zipdatei On Error Resume Next ´ Fehler beim Versenden abfangen Mail.Send ´ Email absenden If Err 0 Then ´ Fehler! Ursache ausgeben meldung = "Email konnte nicht versendet werden: " & Err.Description MsgBox meldung, vbExclamation else meldung = "Die Datei "+ fs.GetBaseName(zipdatei) + " wurde abgeschickt!" MsgBox meldung, vbInformation end if
´ automatischer Email-Massenversand aus Datenbank ´ Zugriff auf ActiveX-Objekte des Systems set db = CreateObject("ADODB.Connection") ´ Datenbank Set Mail = CreateObject("Persits.MailSender") ´ Email-Versand set fs = CreateObject("Scripting.FileSystemObject") ´ Dateisystem set WSHShell = CreateObject("WScript.Shell") ´ Run-Befehl tempdatei = "C:\TEMPEMAIL" ´ Email-Nachricht ´ neue leere Email-Datei anlegen: set emaildatei = fs.CreateTextFile(tempdatei, vbTrue) emaildatei.close ´ Email-Nachricht verfassen: hinweis = "Bitte verfassen Sie Ihre Email und speichern Sie sie ab! " _ & "Danach beenden Sie den Editor!" MsgBox hinweis, vbInformation WSHShell.Run "NOTEPAD.EXE " + tempdatei, , vbTrue if not fs.FileExists(tempdatei) then MsgBox "Sie haben keine Email gespeichert!", vbExclamation WScript.Quit end if ´ Email-Datei einlesen set emaildatei = fs.OpenTextFile(tempdatei) on error resume next ´ Fehler beim Lesen abfangen header = emaildatei.ReadLine ´ erste Zeile der Email wird zum Header body = emaildatei.ReadAll ´ Rest wird zur Nachricht emaildatei.close ´ Datei schließen und löschen fs.DeleteFile tempdatei, vbTrue ´ Fehler beim Einlesen der Email if err<>0 then hinweis = "Emaildatei konnte nicht gelesen werden und war vielleicht " _ & "leer oder enthielt weniger als 2 Zeilen!" MsgBox hinweis, vbExclamation WScript.Quit end if ´ Empfängeradressen aus der Datenbank lesen db.Open "internet" ´ Datenbank "Internet" öffnen ´ SQL-Abfrage: gesamte Tabelle "Emailversand" wählen sql = "SELECT * FROM Emailversand" set rs = db.Execute(sql) ´ und an die Datenbank schicken Mail.Host = "smtp.site1.csi.com" ´ SMTP-Server festlegen Mail.From = "anonym@anonym.net" ´ Absender-Informationen Mail.FromName = "MeinName" ´ Feld Email aus der Tabelle auslesen do while testRS(RS) ´ lesen, bis Ende der Tabelle erreicht email = RS("Email") ´ Feld "Email" auslesen if Instr(email, "@")>0 then ´ korrekte Email-Adresse? Mail.AddAddress email ´ als weitere Empfängeradresse festlegen else hinweis = email&" ist keine gültige Email-Adresse und wird ignoriert!" MsgBox hinweis, vbInformation end if RS.MoveNext ´ nächster Datensatz loop Mail.Subject = header ´ Emailheader und -text festlegen Mail.Body = body ´ Fehler beim Versenden abfangen On Error Resume Next Mail.Send ´ Email absenden If Err <> 0 Then ´ Fehler! Grund angeben hinweis = "Fehler beim Versand: " & Err.Description MsgBox hinweis, vbExclamation else MsgBox "Nachricht wurde versandt!", vbInformation end if Function testRS(RS) ´ prüft, ob letzter Datensatz erreicht ist On Error Resume Next bEOF = RS.EOF If Err Or bEOF Then testRS = False Else testRS = True End If End Function