Impressum
Frank Seitz Industriestraße 31 22880 Wedel E-Mail: fs Telefon: +49 (0)4103 180301 Fax: +49 (0)4103 180302 Kurzprofil CPAN-Module Vuvuzela-Time KategorienAbonnieren |
Montag, 31. Mai 2010CSS: Listen portabel einrückenDie Browser benutzen unterschiedliche Wege, Listen einzurücken. Einige rücken per Padding ein, andere per Margin. Soll die Einrückung portabel verändert werden, müssen margin-left uns padding-left also zusammen gesetzt werden, und zwar eine Angabe auf die gewünschte Einrückung und die andere auf 0.
oder
Sonntag, 30. Mai 2010HTML-Konstrukte mit CSS gestaltenProblemEin aus mehreren Elementen bestehendes HTML-Konstrukt soll in seinem Aussehen frei gestaltbar sein. Wie lässt sich dies mit CSS erreichen? BeispielGegeben sei ein Inhaltsverzeichnis, bestehend aus einer Überschrift (h1) und verschachtelten Listen (ul, li) mit Links (a) auf die Dokument-Abschnitte.
Der HTML-Code wird ohne CSS vom Browser (Firefox) ungefähr so dargestellt (die Strukturelemente für den Titel (h1) und die Listen (ul) sind zur Verdeutlichung grau hinterlegt):
LösungUm ein HTML-Konstrukt aus mehreren Elementen per CSS anpassbar zu machen, gehen wir folgendermaßen vor:
Donnerstag, 20. Mai 2010Perl: POD als Programm-HilfetextDas Core-Modul Pod::Usage kann einen Programm-Hilfetext aus der eingebetteten POD-Dokumentation generieren. Es geht auch einfacher:
produziert auf STDOUT NAME
myprog - a simple program
LICENSE
This program is free software; you can redistribute it and/or modify it
under the same terms as Perl itself.
Mittwoch, 19. Mai 2010Medion Life S60003 MP3 Player unter DebianDer Medion Life S60003 ist ein einfacher Player zum Abspielen von MP3- und WMA-Dateien. Zum Datenaustausch wird dieser auf einen freien USB-Port gesteckt. Der Player wechselt in den Zustand "USB Connected". Wird gerade ein Titel gespielt, muss die Wiedergabe erst angehalten werden. Zugriff auf das Dateisystem des PlayersDer Player wird von udev erkannt und vom System automatisch auf ein Verzeichnis unter /media gemountet. Der Vorgang wird in /var/log/messages protokolliert: usb 3-1: new high speed USB device using ehci_hcd and address 18 usb 3-1: New USB device found, idVendor=066f, idProduct=8588 usb 3-1: New USB device strings: Mfr=1, Product=2, SerialNumber=5 usb 3-1: Product: MD 83366 usb 3-1: Manufacturer: Medion usb 3-1: SerialNumber: 43F9000056B398A30002D8F515A958A3 usb 3-1: configuration #1 chosen from 1 choice scsi18 : SCSI emulation for USB Mass Storage devices scsi 18:0:0:0: Direct-Access Medion MD 83366 0100 PQ: 0 ANSI: 4 scsi 18:0:0:1: Direct-Access Medion MD 83366 0100 PQ: 0 ANSI: 4 sd 18:0:0:0: [sdc] 478976 4096-byte logical blocks: (1.96 GB/1.82 GiB) sd 18:0:0:0: [sdc] Write Protect is off sd 18:0:0:0: [sdc] 478976 4096-byte logical blocks: (1.96 GB/1.82 GiB) sd 18:0:0:1: [sdd] Attached SCSI removable disk sdc: sd 18:0:0:0: [sdc] 478976 4096-byte logical blocks: (1.96 GB/1.82 GiB) sd 18:0:0:0: [sdc] Attached SCSI removable disk Der Mountpoint lässt sich mit mount(1) herausfinden: $ mount ... /dev/sdc on /media/87C9-FFD0 type vfat (rw,nosuid,nodev,uhelper=udisks, uid=1000,gid=1000,shortname=mixed,dmask=0077,utf8=1,flush) Eigentlich ist der Flash-Speicher des Players nicht direkt mountbar. Vielmehr wird der Player als MTP-Gerät (http://de.wikipedia.org/wiki/Media_Transfer_Protocol) angesprochen. Der Eintrag in /lib/udev/rules.d/45-libmtp8.rules lautet: # Medion MD8333
ATTR{idVendor}=="066f", ATTR{idProduct}=="8588", SYMLINK+="libmtp-%k",
MODE="660", GROUP="audio"
Der Player kann, wenn obiges Setup stimmt, auch per Hand gemountet werden: # mount /dev/sdX /mnt X ist der Buchstabe des SCSI-Geräts ohne eine Partitionsnummer, hier: /dev/sdc. Ist unter System/Preferences/File Management/Media (Gnome) die Option "Browse Media when inserted" aktiviert, wird von Gnome der File Browser Nautilus auf dem Verzeichnis gestartet, wenn es automatisch gemountet wird. Aber ACHTUNG: Dies alles klappt nicht, wenn der Gnome Audio-Player Rhythmbox läuft! Dieser nimmt selbst mit dem Player via MTP Kontakt auf. Offenbar kann der Player nicht gleichzeitig gemountet sein, d.h. ein etwaiger Mount - egal ob automatisch oder manuell aufgebaut - wird sofort wieder abgebaut oder anderweitig gestört. Dateien übertragenGemountet kann der Player als Datenträger für beliebige Dateien und Verzeichnisstrukturen verwendet werden. Auch die Musiksammlung kann theoretisch mittels Dateisystem-Operationen auf dem Player verwaltet werden. Dies ist allerdings nicht praktikabel, da der Player die in den MP3-Dateien enthaltenen ID3-Tags nicht auswertet. Werden MP3-Dateien einfach nur kopiert, befinden sie sich anschließend zwar auf dem Player und können gespielt werden, aber der Player "weiß" nichts über ihren Inhalt und kann dem Benutzer die zur Unterscheidung wichtigen Informationen Titel, Künstler, Album, Jahr, Genre nicht präsentieren. Daher ist es besser, die Dateien mit Rhythmbox - oder einem anderen Programm, welches Musikdateien per MTP verwaltet - zu übertragen. Der Player erhält dann auch die Meta-Information zu den Dateien. Donnerstag, 25. März 2010Perl: Plus / Minus UnendlichPerl kennt mehrere Zeichenketten, die - numerisch interpretiert - plus und minus Unendlich bedeuten.
Beispiel: Maximum ermitteln
Aber Achtung: Diese besonderen Werte sind nicht sonderlich gut dokumentiert und scheinen bei einigen Windows-Ports nicht zu funktionieren. Siehe: http://reneeb-perlblog.blogspot.com/2010/03/unendliches-perl.html Donnerstag, 18. März 2010Perl: Dirhandles objektorientiertAnalog zu lexikalischen Filehandles besitzt Perl lexikalische Dirhandles. Eine Dirhandle ist ein Iterator über einem Verzeichnis. Die Operationen auf Dirhandles lassen sich objektorientiert kapseln. Hier eine entsprechende Klasse Dirhandle mit drei Methoden: new() (Directory öffnen), close() (Directory schließen) und next() (nächster Directory-Eintrag): Beispiel: Gib alle Einträge des Verzeichnisses $dir auf STDOUT aus 1 use Dirhandle; 2 3 my $dh = Dirhandle->new($dir); 4 while (my $entry = $dh->next) { 5 say $entry; 6 } 7 $dh->close; Das Dirhandle-Objekt $dh kann wie jede normale Dirhandle an die Perl-Builtins readdir(), telldir(), seekdir(), rewinddir(), closedir() übergeben werden. Dienstag, 16. März 2010Perl: Filehandles objektorientiertMit lexikalischen Filehandles ist es in Perl leicht möglich, File-I/O objektorientiert zu kapseln. Hier zur Veranschaulichung eine Klasse Filehandle mit drei Methoden: new() (Datei öffnen), close() (Datei schließen) und slurp() (Datei komplett einlesen): Beispiel: Lies eine Datei komplett ein und gib sie auf STDOUT aus 1 use Filehandle; 2 3 my $fh = Filehandle->new('<',$file); 4 print $fh->slurp; 5 $fh->close; Der Clou: Die Filehandle $fh kann unabhängig von der Klasse wie jede andere Perl-Filehandle benutzt werden, z.B. mit dem Diamant-Operator <> oder jeder anderen Filehandle-Operation wie read(), write() usw. Obiges Programm lässt sich also auch so implementieren: 1 use Filehandle; 2 3 my $fh = Filehandle->new('<',$file); 4 while (<$fh>) { 5 print; 6 } 7 $fh->close; Freitag, 5. März 2010Perl: Crash bei Umleitung von STDERR auf Skalare VariableIch weiß nicht, wann Perl mir mal abgestürzt ist, aber jetzt bin ich auf einen Fall gestoßen:
$ ./test.pl Segmentation fault Perl-Version (andere habe ich nicht probiert): $ perl -v This is perl, v5.10.1 (*) built for i686-linux VariationenWenn $s kein In-Memory File ist, geht es. Bei $s =~ s/./xx/; geht es (ohne g Modifier). Bei $s =~ s/./x/g; geht es (der String wird nicht länger). Schließen von STDERR vor dem s/// ändert nichts. Mittwoch, 10. Februar 2010Perl und UnicodeEine sehr gute, knappe Einführung in Perl und Unicode von Moritz Lenz: http://perlgeek.de/de/artikel/charsets-unicode Dienstag, 9. Februar 2010GNU Makefile zum Konvertieren von DateienMitunter soll eine Menge von Dateien, die man erstellt und bearbeitet, systematisch in etwas anderes, z.B. ein anderes Format, konvertiert werden. Die Konvertierung lässt sich mit dem Utilty make organisieren, so dass überflüssige Konvertierungen vermieden werden. Wie sieht ein GNU Makefile für diese Aufgabe aus? Das folgende (fiktive) Beispiel geht davon aus, dass wir .in-Dateien in .out-Dateien konvertieren wollen. Die Konvertierung übernimmt das (fiktive) Programm in2out.
Montag, 8. Februar 2010Syntax-Highlighting mit highlightHighlight stellt die Syntax von zahlreichen Programmiersprachen farbig und mit Fontattributen wie kursiv und fett dar: $ highlight --syntax=LANG --fragment <CODE >CODE.html Die Option --syntax=LANG stellt die Programmiersprache ein, --fragment sorgt dafür, dass keine vollständige HTML-Seite, sondern einbettbarer HTML-Code generiert wird. Die zugehörigen CSS-Klassen liefert folgendes Kommando nach stdout: $ highlight --print-style --style-outfile=stdout | grep '^\.' >CODE.css Das nachgeschaltete grep sorgt dafür, dass der Output auf die relevanten Klassen für eine Einbettung eingeschränkt wird. Freitag, 5. Februar 2010Syntax-Highlighting mit perltidyPerltidy stellt die Syntax von Perl-Code farbig und mit Fontattributen wie kursiv und fett dar, wenn man den Code mit Option -html nach HTML wandelt. Ich nutze dieses Feature, um lesbareren Perl-Code für mein Blog zu generieren. Für die Einbettung des generierten HTML-Codes in eigene HTML-Seiten sind allerdings kleinere Sonderbehandlungen nötig. Anpassung der Stylesheet-DefinitionenPerltidy generiert mit $ perltidy -html -ss >FILE.css eine Stylesheet-Datei, die die Definitionen der CSS-Klassen für die Syntaxelemente enthält und in die eigenen HTML-Seiten eingebunden werden kann: /* default style sheet generated by perltidy */ body {background: #FFFFFF; color: #000000} pre { color: #000000; background: #FFFFFF; font-family: courier; } .c { color: #228B22;} /* comment */ .cm { color: #000000;} /* comma */ .co { color: #000000;} /* colon */ .h { color: #CD5555; font-weight:bold;} /* here-doc-target */ .hh { color: #CD5555; font-style:italic;} /* here-doc-text */ .i { color: #00688B;} /* identifier */ .j { color: #CD5555; font-weight:bold;} /* label */ .k { color: #8B008B; font-weight:bold;} /* keyword */ .m { color: #FF0000; font-weight:bold;} /* subroutine */ .n { color: #B452CD;} /* numeric */ .p { color: #000000;} /* paren */ .pd { color: #228B22; font-style:italic;} /* pod-text */ .pu { color: #000000;} /* punctuation */ .q { color: #CD5555;} /* quote */ .s { color: #000000;} /* structure */ .sc { color: #000000;} /* semicolon */ .v { color: #B452CD;} /* v-string */ .w { color: #000000;} /* bareword */ Anpassung 1Die CSS-Definitionen für <body> und <pre> am Anfang sollten im Falle einer Einbettung nicht vorkommen, da diese an anderer Stelle definiert sind. Sie lassen sich mit grep wegfiltern. $ perltidy -html -ss | grep '^\.' Anpassung 2Die Namen der CSS-Klassen bestehen aus ein oder zwei Buchstaben, was zu Nameclashes führen kann. Dies verbessere ich, indem ich dem Klassennamen einen Präfix voranstelle. Ich wähle "pt-". $ perltidy -html -ss | grep '^\.' | sed -e 's/^\./.pt-/' Resultierende CSS-Datei.pt-c { color: #228B22;} /* comment */ .pt-cm { color: #000000;} /* comma */ .pt-co { color: #000000;} /* colon */ .pt-h { color: #CD5555; font-weight:bold;} /* here-doc-target */ .pt-hh { color: #CD5555; font-style:italic;} /* here-doc-text */ .pt-i { color: #00688B;} /* identifier */ .pt-j { color: #CD5555; font-weight:bold;} /* label */ .pt-k { color: #8B008B; font-weight:bold;} /* keyword */ .pt-m { color: #FF0000; font-weight:bold;} /* subroutine */ .pt-n { color: #B452CD;} /* numeric */ .pt-p { color: #000000;} /* paren */ .pt-pd { color: #228B22; font-style:italic;} /* pod-text */ .pt-pu { color: #000000;} /* punctuation */ .pt-q { color: #CD5555;} /* quote */ .pt-s { color: #000000;} /* structure */ .pt-sc { color: #000000;} /* semicolon */ .pt-v { color: #B452CD;} /* v-string */ .pt-w { color: #000000;} /* bareword */ Anpassung des HTML-CodesPerltidy erzeugt mit $ perltidy -html -pre <FILE >FILE.html eine Quelltext-Darstellung in HTML. Diese kann in die eigene Seite eingebunden werden. Anpassung 1Der HTML-Code ist in ein <pre> ohne Klassenanabe eingefasst. Das CSS-Layout dieses <pre> lässt sich also nicht gezielt anpassen. Am besten filtert man es weg und setzt den HTML-Code in ein eigenes <pre>. $ perltidy -html -pre <FILE | egrep -v '^</?pre>' Anpassung 2Die CSS-Klassennamen müssen an die oben gewählten Namen in der Stylesheet-Datei angepasst werden. $ perltidy -html -pre | egrep -v '^</?pre>' | sed -e 's/class="/class="pt-/g' Resultierender HTML-CodeAus print "Hello world!\n"; wird im HTML-Output (Umbruch hinzugefügt) <span class="pt-k">print</span> <span class="pt-q"> "Hello world!\n"</span><span class="pt-sc">;</span> und im Browser print "Hello world!\n"; Perl: Effizient Zeichen zählenIst eine FAQ (s. perldoc -q occurrences), aber ich vergesse immer die genaue Syntax, da ich tr/// selten nutze und es mehrere Funktionen in sich vereint: $n = $str =~ tr/\n//; $n ist in diesem Fall die Anzahl der Zeilenumbrüche in $str. Mittwoch, 3. Februar 2010Apache: Redirection auf SubdirectoryMit der Direktive Redirect kann ein Seitenzugriff auf eine andere Seite umgeleitet werden. Die Umleitung schließt alle Subpfade ein, also Seiten mit gleichem Pfadanfang. Möchte man ein Directory auf ein Subdirectory umleiten, klappt dies mit Redirect nicht, weil das zu einer Endlos-Rekursion führt. Die Redirect-Regel Redirect /a /a/b führt bei Aufruf von /a zu der endlosen Kette von HTTP-Aufrufen /a /a/b /a/b/b /a/b/b/b ... bis der Browser dies erkennt und mit einer Meldung wie Redirect Loop: Redirection limit for this URL exceeded. abbricht. Die Lösung liefert die (leistungsfähigere) Direktive RedirectMatch. Mit dieser lässt sich der umzulenkende Pfad per Regex präzise eingrenzen: RedirectMatch /a$ /a/b Das Dollarzeichen verankert den Pfad /a am Ende des URL, so dass Subpfade nicht mehr matchen und die Rekursion unterbleibt. Da durch die Regel keine Subpfade weitergeleitet werden, müssen die Zugriffe innerhalb von /a/b relativ sein. Ist das Ausgangsdirectory das Root-Directory, muss auch der Anfang verankert werden, da jedes Verzeichnis auf / endet: RedirectMatch ^/$ /a Freitag, 29. Januar 2010Rsync: Abweichende Rechte einstellenMit der Option -a führt rsync den Abgleich im Archive Mode durch, d.h. Symlinks, Devices, Permissions, Ownerschaft usw. werden auf die Zielmaschine transferiert. Was aber, wenn gewisse Unterschiede erforderlich sind, z.B. die Ownerschaft einiger Dateien verschieden sein muss, weil der Owner oder die Group auf der Zielmaschine anders heißen? Beispiel: Die Group des HTTP-Servers heißt auf der einen Maschine www-data während sie auf der anderen Maschine apache heißt. Über die Group bekommt der HTTP-Server Rechte auf bestimmten Dateien eingeräumt, sie muss also passend zur Maschine gesetzt sein. Solche Differenzen kann rsync nicht auflösen und bietet auch keine Option hierfür. Es lässt sich aber mit einem nachgeschalteten Shell-Skript erreichen, das via ssh auf der Zielmaschine ausgeführt wird: rsync -az --delete -e ssh DIR1/ USER@HOST:DIR2 ssh USER@HOST CMD Wird CMD in DIR1 abgelegt, wird es durch den rsync-Aufruf mit verwaltet, also automatisch auf dem neusten Stand gehalten. Donnerstag, 28. Januar 2010Overlays in Google Earth einbindenOverlays sind Bilder, die von Google Earth auf einen Bereich der Erdoberfläche (GroundOverlays) oder statisch ins Anwendungsfenster (ScreenOverlays) projeziert werden. Zu den Bildern gehört eine Spezifikation in KML (Keyhole Markup Language), die die Bilder beschreibt und festlegt, wie Google Earth mit ihnen verfahren soll. KML ist XML-basiert und wird in einer Datei mit der Extension .kml gespeichert. Die kml-Datei und die Bild-Dateien können zusammen in Form einer einzelnen kmz-Datei an Google Earth übergeben werden. Die kmz-Datei ist eine ZIP-Datei, die die genannten Dateien enthält. Die kmz-Datei wird entweder über "File/Open" geladen oder als Parameter beim Aufruf von Google Earth angegeben. Beispiel
KML-Datei
Obige KML-Spezifiktion beschreibt ein Bild, das auf die Erdoberfläche projeziert wird (Element GroundOverlay) und ein Bild, das statisch in der oberen linken Ecke des Fensters dargestellt wird (Element ScreenOverlay). Die beteiligten Hauptelemente sind: Document, GroundOverlay, ScreenOverlay. Für die Platzhalter __NAME__, __DESCRIPTION__ usw. müssen konkrete Werte eingesetzt werden.
MIME TypeWird die kmz-Datei von einem HTTP-Server ausgeliefert, sollte dieser den MIME-Type kennen: application/vnd.google-earth.kmz kmz Im Browser kann Google-Earth als Helper-Applikation vereinbart werden. Beim Eintreffen einer kmz-Datei wird Google Earth dann automatisch gestartet und positioniert an den betreffenden Ort. Die Angaben für den Browser sind:
ApplikationMittwoch, 27. Januar 2010Perl: Gleitkomma-Zahlen ausgeben wie sie sindVielleicht trivial, aber mir war die Antwort bislang nicht klar: Wie gebe ich eine Gleitkomma-Zahl aus, ohne dass Stellen wegfallen oder überflüssige Nullen am Ende erscheinen? Bei der Ausgabe von Gleitkommazahlen habe ich bislang automatisch zu printf/sprintf und %f gegriffen, aber das Format-Element %f formatiert die Zahlen ja immer auf eine feste Anzahl an Stellen und rundet auf die letzte Stelle. Z.B. my $x = 0.123456789; printf "%f",$x; ergibt 0.123457 (%f formatiert/rundet per Default auf 6 Nachkommastellen) Natürlich kann ich die Anzahl der Stellen groß wählen, aber dann bekomme ich u.U. zusätzliche Stellen, wenn die betreffende Zahl binär nur näherungsweise dargestellt werden kann: my $x = 0.123456789; printf "%.20f",$x; ergibt 0.12345678899999999734 Andererseits erhalte ich am Ende überflüssige Nullen bei Zahlen, die dezimal weniger als die vorgegebenen Stellen besitzen: my $x = 0.5; printf "%.20f",$x; ergibt 0.50000000000000000000 Was tun? Die Lösung ist (anscheinend) einfach: Ich gebe die Zahl nicht als Zahl sondern als String aus! D.h. im Falle von printf/sprintf mit Format-Element %s! Damit erhalte ich, was ich will. Die Zahl mit allen Stellen und nicht mehr my $x = 0.123456789; printf "%s",$x; 0.123456789 und ohne überflüssige Nullen my $x = 0.5; printf "%s",$x; 0.5 Bei näherer Überlegung leuchtet das ein, da Perl intern neben der (binären) numerischen Repräsentation eine Stringrepräsentation des Werts speichert, welche anfänglich genau der Zeichenfolge bei der Zuweisung entspricht. Schlussfolgerung: Programme, die nicht rechnen, sondern Gleitkommazahlen nur einlesen und wieder ausgeben, sollten, um Verfälschungen auszuschließen, diese bei der Ausgabe grundsätzlich als Strings und nicht als Zahlen behandeln. Dienstag, 26. Januar 2010Email-Adressen in HTML vor Spammern schützenIn Mailto-URLsStatt den Mailto-URL per href zu setzen, wird der mailto-URL zum Zeitpunkt des Klicks via JavaScript generiert. Nicht gut:
<a href="mailto:rudi.ratlos@host.dom">...</a>
Besser:
<a href="#" onclick="this.href = 'mailto:rudi.ratlos'+'@'+'host.dom'">...<a/>
Dies setzt natürlich JavaScript voraus. Aber schreibt heutzutage noch jemand Web-Anwendungen ohne JavaScript? Im Text
Statt die Email-Adresse im Klartext hinzuschreiben, wird das Nicht gut:
rudi.ratlos@host.dom
Besser:
rudi.ratlos@host.dom
Noch besser, mit Text:
rudi.ratlos<AT>host.dom
Mit Grafik:
rudi.ratlos<img src="at.png" alt="AT" ... />host.dom
Bei einer Grafik besteht das Problem, dass diese vom Aussehen statisch ist, das Aussehen des umgebenden Textes u.U. nicht immer gleich ist, z.B. in unterschiedlichen Browsern oder durch Farbänderung beim Überfahren eines Links. HTML: String in Entity-Schreibweise wandelnEine einfache (eventuell nicht besonders wirksame) Methode, um Email-Adressen in HTML-Seiten unkenntlich zu machen, um sie vor Spammern zu verbergen, ist, sie in Entity-Schreibweise zu wandeln. Das folgende Perl-Skript wandelt einen beliebigen String in Entity-Schreibweise:
Beispiel: $ ./str-to-entity 'rudi.ratlos@...' rudi.ratlos@... Montag, 25. Januar 2010SSH: Timeout unterbindenClientseitig$ echo "ServerAliveInterval 120" >> /etc/ssh/ssh_config Wenn der Server 120 Sekunden kein Paket gesendet hat, sendet der Client ein Dummy-Paket zum Server. Serverseitig$ echo "ClientAliveInterval 120" >> /etc/ssh/sshd_config $ /etc/init.d/ssh reload Wenn der Client 120 Sekunden kein Paket gesendet hat, sendet der Server ein Dummy-Paket zum Client. SSH: Automatisch einloggenEin automatisches Login führt SSH durch, wenn auf der Zielmaschine der Öffentliche Schlüssel des eigenen Accounts hinterlegt ist. Der Öffentliche Schlüssel wird auf der Zielmaschine zum Zielaccount hinzugefügt mittels: $ cat id_rsa.pub >>.ssh/authorized_keys2 Information zur Schlüsselgenerierung: http://www.supportnet.de/faqsthread/806 Freitag, 22. Januar 2010PostgreSQL: TIMESTAMP nach EPOCH wandeln und zurückTIMESTAMP WITHOUT TIME ZONE nach EPOCH
Umwandlung eines sql> SELECT EXTRACT(EPOCH FROM TIMESTAMP '1970-01-01 00:00:00' AT TIME ZONE 'UTC') AS t; t --- 0
Entscheidend ist hier der Zusatz " sql> SELECT EXTRACT(EPOCH FROM TIMESTAMP '1970-01-01 00:00:00') AS t; t ------- -3600 Erläuterungen
EPOCH nach TIMESTAMP WITHOUT TIMEZONE
Umwandlung von Epoch-Sekunden in einen
sql> gkss=# SELECT TIMESTAMP 'epoch' + 0 * INTERVAL '1 second' AS t;
t
---------------------
1970-01-01 00:00:00
Erläuterungen
Donnerstag, 21. Januar 2010Verzeichnisse via rsync abgleichenVerzeichnisbaum spiegeln (local => remote)$ rsync -avz --delete dir1/ user@host:dir2
Der trailing Slash bei
Bei Angabe der Option Via ssh$ rsync -e ssh -avz --delete dir1/ user@host:dir2 Via ssh mit speziellem Port$ rsync --rsh='ssh -p port' -avz --delete dir1/ user@host:dir2 Mittwoch, 20. Januar 2010Perl-Operationen auf SymlinksFür den Umgang mit Symlinks stellt Perl eine Reihe von Builtins zur Verfügung, die nicht unbedingt offensichtlich sind. Hier eine kurze Übersicht:
Dienstag, 19. Januar 2010Liste der zusätzlich installierten Perl-ModuleWie ermittele ich, welche Perl-Module über das Grundsystem hinaus installiert wurden? Die Antwort liefert das Kommando: $ perldoc perllocal Das Ergebnis ist ein formatiertes POD-Dokument, das die Installationshistorie aller per make install oder ./Build install installierten Module aufführt. Das Dokument wird mit der Installation des ersten Moduls angelegt. Unmittelbar nach Installation des Core-Systems ist es noch nicht vorhanden, da noch kein zusätzliches Modul installiert wurde. Mit jeder Modul-Installation wird ein Eintrag am Ende hinzugefügt. Wird ein Modul mehrfach installiert, taucht es mehrfach auf. ProgrammLiefere die Namen der zusätzlich installierten Module, alphabetisch sortiert, ohne Doubletten: 1 #!/usr/bin/env perl 2 3 use strict; 4 use warnings; 5 6 my %mod; 7 my $cmd = 'perldoc -u perllocal'; 8 open(my $fh,'-|',$cmd) or die "ERROR: open failed ($!)"; 9 while (<$fh>) { 10 if (/^=head2.*\|(.*)>/) { 11 $mod{$1} = 1; 12 } 13 } 14 close($fh) or die qq|ERROR: Command failed: "$cmd" (Exit Code: $?)\n|; 15 16 for my $mod (sort keys %mod) { 17 print "$mod\n"; 18 } 19 20 # eof Mittwoch, 13. Januar 2010IconsSammlung von mehreren tausend qualitativ hochwertigen Desktop- und Web-Icons: http://www.iconarchive.com/ Fugue Icons: http://p.yusukekamiyamane.com/ Dienstag, 12. Januar 2010GIMP OperationenFarbe transparent machen
Menüpunkt: " ISO-8859-1 nach UTF-8 konvertieren$ tcs -f 8859-1 INPUT >OUTPUT Speicherbedarf von Perl-VariablenDer Speicherbedarf von einzelnen Perl-Variablen und komplexeren Datenstrukturen lässt sich mit Devel::Size ermitteln. Hier die Werte für Perl 5.10 auf einem 32-Bit System. (Eine andere Betrachtung - Messung des verbrauchten virtuellen Speichers bei großen Datenstrukturen - hat Peter J. Holzer angestellt: http://www.hjp.at/programming/perl/memory/) Skalare
Perl alloziert bei Strings jeweils 4 Bytes im Voraus, vermutlich um jedes UTF-8 Zeichen speichern zu können. Obige Berechnung geht von 1-Byte-Zeichen aus. Enthält der String UTF-8 Zeichen mit 2, 3 oder 4 Byte, vergrößert sich der Platzbedarf entsprechend. Arrays
Perl vergrößert ein Array schrittweise auf 4, 8, 16, 32, 64, ... Elemente. D.h. wird das 4. Element zugewiesen, vergößert Perl intern schon auf 8 Elemente usw. Für jedes Element alloziert Perl einen Pointer (4 Bytes). Die angegebene Größe ist der Netto-Speicherbedarf des Array, d.h. der Speicherbedarf der (skalaren) Werte kommt noch hinzu. Hashes
Perl vergrößert einen Hash schrittweise auf 8, 16, 32, 64, ... Elemente. D.h. wird das 8. Element zugewiesen, vergößert Perl intern auf 16 Elemente usw. Für jeden Key alloziert Perl vorab einen Pointer (4 Bytes). Zusätzlich kommt mit zunehmender Anzahl Buckets ein wachsender Overhead von 9, 10, 11, ... Bytes je Key hinzu. Die Größe des Key geht auch mit ein. Bei der Messung unten ist der Key der String "EintragNNNN", also 11 Zeichen lang. Die angegebene Größe ist der Netto-Speicherbedarf des Hash, d.h. der Speicherbedarf der Werte kommt noch hinzu. MessungPerl Version: 5.010000 Skalar ohne Wert: 16 Bytes Referenz: 16 Bytes Integer: 16 Bytes Float: 24 Bytes String - leer: 36 Bytes String - 1 1-Byte Zeichen: 36 Bytes (Diff: 0) String - 2 1-Byte Zeichen: 36 Bytes (Diff: 0) String - 3 1-Byte Zeichen: 36 Bytes (Diff: 0) String - 4 1-Byte Zeichen: 40 Bytes (Diff: 4) String - 5 1-Byte Zeichen: 40 Bytes (Diff: 0) String - 6 1-Byte Zeichen: 40 Bytes (Diff: 0) String - 7 1-Byte Zeichen: 40 Bytes (Diff: 0) String - 8 1-Byte Zeichen: 44 Bytes (Diff: 4) String - 9 1-Byte Zeichen: 44 Bytes (Diff: 0) String - 10 1-Byte Zeichen: 44 Bytes (Diff: 0) String - 11 1-Byte Zeichen: 44 Bytes (Diff: 0) String - 12 1-Byte Zeichen: 48 Bytes (Diff: 4) String - 16 1-Byte Zeichen: 52 Bytes (Diff: 4) String - 20 1-Byte Zeichen: 56 Bytes (Diff: 4) Array - leer: 100 Bytes Array - 4 Elemente: 116 Bytes (Diff: 16) - 29.0 Bytes/Key Array - 8 Elemente: 148 Bytes (Diff: 32) - 18.5 Bytes/Key Array - 16 Elemente: 212 Bytes (Diff: 64) - 13.2 Bytes/Key Array - 32 Elemente: 340 Bytes (Diff: 128) - 10.6 Bytes/Key Array - 64 Elemente: 596 Bytes (Diff: 256) - 9.3 Bytes/Key Hash - leer: 76 Bytes Hash - 4 Keys: 208 Bytes (Diff: 132) - 52.0 Bytes/Key Hash - 8 Keys: 372 Bytes (Diff: 164) - 46.5 Bytes/Key Hash - 16 Keys: 636 Bytes (Diff: 264) - 39.8 Bytes/Key Hash - 32 Keys: 1228 Bytes (Diff: 592) - 38.4 Bytes/Key Hash - 64 Keys: 2412 Bytes (Diff: 1184) - 37.7 Bytes/Key Hash - 128 Keys: 4780 Bytes (Diff: 2368) - 37.3 Bytes/Key Hash - 256 Keys: 10540 Bytes (Diff: 5760) - 41.2 Bytes/Key Hash - 512 Keys: 18988 Bytes (Diff: 8448) - 37.1 Bytes/Key Hash - 1024 Keys: 42028 Bytes (Diff: 23040) - 41.0 Bytes/Key Programm1 #!/usr/bin/env perl 2 3 use strict; 4 use warnings; 5 6 use Devel::Size; 7 8 print "Perl Version: $]\n"; 9 10 my $s1; 11 print 'Skalar ohne Wert: ',Devel::Size::size(\$s1)," Bytes\n"; 12 13 my $s2 = \$s1; 14 print 'Referenz: ',Devel::Size::size(\$s2)," Bytes\n"; 15 16 my $s3 = 4711; 17 print 'Integer: ',Devel::Size::size(\$s3)," Bytes\n"; 18 19 my $s4 = 1234.567; 20 print 'Float: ',Devel::Size::size(\$s4)," Bytes\n"; 21 22 my $s5 = ''; 23 my $nLast = Devel::Size::size(\$s5); 24 print "String - leer: $nLast Bytes\n"; 25 26 for my $i (1..12,16,20) { 27 $s5 = 'x'x$i; 28 my $n = Devel::Size::size(\$s5); 29 print "String - $i 1-Byte Zeichen: $n Bytes (Diff: ",$n-$nLast,")\n"; 30 $nLast = $n; 31 } 32 33 my @a1; 34 $nLast = Devel::Size::size(\@a1); 35 print "Array - leer: $nLast Bytes\n"; 36 37 for my $i (4,8,16,32,64) { 38 my @a2 = (1..$i); 39 my $n = Devel::Size::size(\@a2); 40 my $diff = $n-$nLast; 41 my $avg = $n/$i; 42 printf "Array - $i Elemente: $n Bytes (Diff: $diff) - %.1f Bytes/Key\n",$avg; 43 $nLast = $n; 44 } 45 46 my %h1; 47 $nLast = Devel::Size::size(\%h1); 48 print "Hash - leer: $nLast Bytes\n"; 49 50 for my $i (4,8,16,32,64,128,256,512,1024) { 51 my %h2; 52 for (my $j = 1; $j <= $i; $j++) { 53 $h2{sprintf 'Eintrag%04d',$j} = $j; 54 } 55 # @h2{(1..$i)} = (1..$i); 56 my $n = Devel::Size::size(\%h2); 57 my $diff = $n-$nLast; 58 my $avg = $n/$i; 59 printf "Hash - $i Keys: $n Bytes (Diff: $diff) - %.1f Bytes/Key\n",$avg; 60 $nLast = $n; 61 } 62 63 # eof Montag, 11. Januar 2010Text-Eingabefelder per CSS gestalten<input type="text" id="e" name="text" size="20" /> Text: UmrahmungRahmen von 1px Breite statt der normalen Dekoration.
#e {
border: 1px #999 solid;
}
Hintergrundfarbe
Die Hintergrundfarbe des Eingabefeldes ändern, wenn es mit der Maus überfahren wird
(
#e:hover, #e:focus {
background-color: #eee;
}
FontEin Text-Eingabefeld sollte m.E. normalerweise einen monospaced Font eingestellt haben, nur dann entspricht die optische Feldbreite exakt der Anzahl der Zeichen, die in das Feld passen.
#e {
font-family: monospace;
}
Samstag, 9. Januar 2010Cellspacing per CSS unterdrückenIn HTML: <table cellspacing="0"> Per CSS (
#t {
border-collapse: collapse;
}
#t > td {
padding: 0;
}
Dreispaltiges Seitenlayout mit CSSLayout mit Kopf, Fuss und drei Spalten: ![]() Der HTML- und CSS-Code, der dies realisiert: <div id="header"> Header </div> <div id="left"> Left </div> <div id="right"> Right </div> <div id="middle"> Middle </div> <div id="footer"> Footer </div> #header { clear: both; } #left { float: left; width: 80px; } #right { float: right; width: 80px; } #middle { padding: 0 80px 0 80px; } #footer { clear: both; } Anmerkungen
Validierung von HTML- und CSS-CodeDas W3C stellt zwei Services zur Validierung von HTML- und CSS-Code zur Verfügung:
HTML-Validator: http://validator.w3.org/ Um den HTML- bzw. CSS-Code einer Seite direkt zu validieren, können folgende Links in die Seite eingebaut werden. Aus dem Referer-Header ermittelt der Validator die Ausgangsseite und ruft diese ab. Das geht natürlich nur, wenn die Seite öffentlich zugreifbar ist. Validierung von XHTML-Code<a href="http://validator.w3.org/check/referer?ss=1"> <img src="valid-xhtml10.png" width="88" height="31" alt="Valid XHTML 1.0!" /> </a>
Der URL-Parameter Validierung von CSS2-Code
<a href="http://jigsaw.w3.org/css-validator/check/referer">
<img src="valid-css2.png" width="88" height="31" alt="Valid CSS!" />
</a>
Freitag, 8. Januar 2010Grundlegende PostgreSQL-AdministrationPostgreSQL ist meiner Meinung nach das beste frei erhältliche Relationale Datenbanksystem. Hier die wichtigsten Kommandos, um damit an den Start gehen zu können. PostgreSQL RDBMS installieren (Debian)# apt-get install postgresql Zum DB-Admin machen# su - postgres Nur von diesem Unix-Account aus kann nach der Installation eine Connection zum DBMS aufgebaut werden. Liste der existierenden Datenbanken$ psql -l [Liste] Nach der Installation existiert zunächst nur die Datenbank postgres. Datenbank erzeugen/zerstören$ createdb DB ... $ dropdb DB</pre> Liste der existierenden Benutzer$ psql postgres=# \du oder postgres=# SELECT rolname FROM pg_roles; Benutzer anlegen/entfernen$ createuser USER Shall the new role be a superuser? (y/n) y ... $ dropuser USER Benutzer sind global für alle Datenbanken einer Installation. Zunächst existiert nur der Benutzer postgres. Soll der User USER von einem anderen Account als dem entsprechenden Unix-Account connecten können, muss ein Passwort vergeben werden. Option -P. DatenbankzugriffIst ein DB-User erzeugt, kann dieser vom gleichnamigen Unix-Account oder per Passwort, falls eins vergeben wurde, von einem anderen Account per psql auf die Datenbank zugreifen. USER$ psql DB Welcome to psql 8.3.6, the PostgreSQL interactive terminal. ... DB=# Liste der existierenden Objekte
Exportieren/Importieren
Session-EinstellungenDatumsformatDatumsangaben im Format YYYY-MM-DD SET datestyle TO iso, ymd select localtimestamp(0); liefert die Zeit im Format: 2009-03-12 17:38:20 ZeichensatzClient arbeitet mit ISO-8859-1: SET client_encoding TO iso88591 Client arbeitet mit UTF-8: SET client_encoding TO utf8 Siehe: http://www.postgresql.org/docs/8.3/static/multibyte.html#AEN27449 Der clientseitige Zeichensatz kann jederzeit umgeschaltet werden. Wenn Daten mit unterschiedlichem Encoding verarbeitet werden, besteht die Möglichkeit, vor dem Schreiben auf die Datenbank das clientseitige Encoding umzuschalten. Die Konvertierung wird dann vom Server übernommen. \-Escapes in Stringliteralen verbietenSET standard_conforming_strings TO on Server-Zugriff von externen HostsDie folgenden Einträge ermöglichen den Zugriff von allen Hosts für alle User und alle Datenbanken. In pg_hba.conf oberhalb der anderen Einträge hinzufügen: # TYPE DATABASE USER CIDR-ADDRESS METHOD host all all 0.0.0.0/0 md5 In postgresql.conf eintragen: listen_addresses = '*' Server neu starten# /etc/init.d/postgresql-X.Y restart Upgrade auf eine neue VersionSiehe Kapitel "Upgrading" in der Doku. Donnerstag, 7. Januar 2010YouTube Video in HTML-Seite einbettenHier der Code, wie er von YouTube vorgeschlagen wird:
<object width="$WIDTH" height="$HEIGHT">
<param name="movie" value="$URL"></param>
<param name="allowFullScreen" value="$FS"></param>
<param name="allowscriptaccess" value="always"></param>
<embed src="$URL"
type="application/x-shockwave-flash"
allowscriptaccess="always"
allowfullscreen="$FS"
width="$WIDTH"
height="$HEIGHT">
</embed>
</object>
Im Falle eine Standard-Definition Films - wie oben - im Steitenverhältnis 4:3, errechnen sich z.B. folgende Playergrößen: 120 x 115 (klein oben - es wird keine Zeit und kein Slider angezeigt) 160 x 145 (mittel oben - es wird keine Zeit angezeigt) 240 x 205 (groß oben - Fullscreen-Button ist explizit abgeschaltet) 320 x 265 (1. YouTube-Vorschlag) 425 x 344 (2. YouTube-Vorschlag) 480 x 385 (3. YouTube-Vorschlag) 640 x 505 (4. YouTube-Vorschlag) Änderungen an SerendipityFavicon hinzugefügtZu Datei: templates/default/index.tpl Homelink2 auf Artikelübersicht geändertZu index.php?/archives/summary.html in Datei: templates/default/index.tpl Style der Serendipity Admin-Oberfläche ändernDie Admin-Oberfläche bietet keine getrennte Einstellung für den eigenen Style - entweder der Haupt-Style ändert den Style der Admin-Oberfläche mit oder es bleibt bei dem (für meinen Geschmack) nicht sonderlich schönen Default. Die Admin-Styles sind in den Verzeichnissen der Haupt-Styles in $ find templates -type d | grep admin$ ./carl_contest/admin ./competition/admin ./contest/admin ./bulletproof/admin ./default-rtl/admin ./default/admin Ein Style, der keinen Admin-Style definiert, kann mit einem fremden Admin-Style ausgestattet werden, indem ein fremdes admin Verzeichnis (eines anderen Style) dorthin kopiert wird oder ein Symlink auf dieses angelegt wird: $ cd templates/MYSTYLE $ ln -s ../OTHERSTYLE/admin . Perl-Interpreter über Shebang-Zeile suchen#!/usr/bin/env perl Mit dieser Shebang-Zeile wird der Perl-Interpreter über die Environment-Variable
Installation von SerendipityMeine Wahl der Blog-Software ist auf Serendipity gefallen, da ich es neulich positiv erwähnt gefunden habe und meine anschließende Recherche ergeben hat, dass es wohl tatsächlich gut ist. Als ersten technischen Eintrag schreibe ich auf, wie ich Serendipity from scratch auf meinem Debian Web-Host installiert habe. Zwar gibt es Serendipity auch fix und fertig als Debian-Paket, aber das ist in Debian/Stable schon älter. Außerdem ist diese Anwendung für mich wichtig genug, dass ich alles im Detail kontrollieren möchte, einschließlich programmierung, und keinesfalls will, dass die Debian-Paketverwaltung mir mit Updates dazwischen kommt. Homepage von Serendipity: http://www.s9y.org/ Schritt 1: Herunterladen der Software Auf der Homepage bekommt man die aktuelle Version als Tarball und auch eine Beschreibung für die manuelle Installation. Diese hat den Titel Fresh Installation. Sie ist gut, aber in einigen Punkten nicht ausführlich genug. Ich beschreibe hier die Dinge, die ich bei meiner Installation dort nicht gefunden habe. Schritt 2: Auspacken des Pakets Das Paket, in meinen Fall Schritt 3: Benötigte Debian-Pakete installieren # deb-install php5 # apt-get install postgresql # apt-get install php5-pgsql # apt-get install imagemagick Serendipity ist in PHP5 programmiert. Als DBMS verwende ich PostgreSQL. Imagemagick wird von Serendipity zur Bildbearbeitung gebraucht. Schritt 4: Apache Konfiguration Im Serendipity-Paket scheint keine Apache-Config dabei zu sein. Ich habe diese
von der Debian-Version übernommen, mit der ich zuvor herumgespielt habe. Lediglich
die Pfade brauchte ich anpassen. Der URL des Blog wird
Alias /blog /opt/serendipity/1.5.1
<Directory /opt/serendipity/1.5.1>
Options -Indexes +FollowSymlinks
DirectoryIndex index.php
<IfModule mod_php5.c>
php_flag session.use_trans_sid off
php_flag register_globals off
</IfModule>
AllowOverride All
order allow,deny
allow from all
<Files *.tpl.php>
deny from all
</Files>
<Files *.tpl>
deny from all
</Files>
<Files *.sql>
deny from all
</Files>
<Files *.inc.php>
deny from all
</Files>
<Files *.db>
deny from all
</Files>
</Directory>
Die Datei wird als # apache2ctl restart Schritt 5: PostgreSQL-Datenbank einrichten Für die Datenbank-Einrichtung sind drei Dinge zu tun:
Datenbank und User erzeugen: # su - postgres $ createdb serendipity $ createuser -P serendipity Password: Wichtig ist bei Schritt 6: Konfiguration und Administration von Serendipity Anschließend auf Bei Anmeldeaufforderung per "John Doe" mit Passwort "john" anmelden. Benutzername und Passwort sollten nach der Anmeldung als erstes geändert werden. Danach kann Serendipity im Detail den persönlichen Wünschen angepasst werden. Eröffnung des Developer LogbuchsIch habe beschlossen, ein Technik Logbuch zu führen, in welchem ich meine Erkenntnisse aufschreibe. Primär als Nachschlagewerk zur eigenen Erinnerung, aber auch als mögliche Hilfe für andere. Ich selbst schlage meist zuerst im Web nach, wenn ich auf eine Fragestellung oder ein Problem stoße und oft ist etwas darunter, was mir schnell weiter hilft. Dies soll mein bescheidener Beitrag zur Wissensweitergabe im Zeitalter des Internet sein.
(Seite 1 von 1, insgesamt 40 Einträge)
|
Kalender
SucheStatistikenLetzter Artikel:
31.05.2010 16:41 40 Artikel insgesamt
|
|||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||