Beiträge der Kategorie TYPO3

Letzen Login anzeigen

Das hier ist ein Konzept, das ich umgesetzt habe, den Quellcode darf/möchte ich (noch) nicht veröffentlichen.
Aufgabenstellung: im Extranet dem Benutzer das Datum seines letzen Logins anzeigen. Problem: Sobald sich ein Benutzer in Typo einloggt, wird automatisch das Datum neu gesetzt, so dass der Benutzer immer den Zeitpunkt vor ein paar Minuten zu sehen bekommt.
Egal wie der Benutzer sich einloggt – newloginbox oder felogin (neu als Systemextension in 4.2), das Einloggen und das Setzen des Wertes findet immer auf Core-Ebene statt. Die felogin bietet zwar eine Möglichkeit für einen Hook an, da ist das Setzen des Wertes aber schon passiert und auf den alten Wert kann man nicht mehr zugreifen.
Um das Problem zu lösen, braucht man in der fe_users Tabelle zwei weitere Felder – ein Backup-Feld für lastlogin und ein Feld mit dem tatsächlichen letzen Login, nennen wir sie mal ll_bkp und real_ll.
Bei Login-Vorgang passiert folgendes: Ganz am Anfang auf Core-Ebene wird der Benutzer eingeloggt, der Wert lastlogin wird gesetzt. Wenn die Extension aufgerufen wird, wird aus dem Backup (der ist noch der alte) der Wert ins Real-Last-Login übertragen, und das Backup mit dem neuen lastlogin-Wert (der aktuelle Zeitpunkt) überschrieben. Warum braucht man das Backup-Feld? Weil man keine Möglichkeit hat, das lastlogin vor dem Überschreiben irgendwie zu sichern. Und das macht man „manuell“ in der Extension.
Natürlich muss sich der Benutzer mindestens zweimal einloggen, damit im real_ll ein vernünftiger Wert steht (ist aber auch so logisch).
Wann kann man das einbauen? Man kann den Hook in der newloginbox oder felogin nutzen, um den eben beschriebenen Kopiervorgang auszuführen. Das wird dann beim Einloggen einmal ausgeführt. Das mit dem Hook klappt leider nicht, wenn die Login-Seite die Eigenschaft gesetzt hat, beim Einloggen ausgeblendet zu werden und stattdessen die Logout-Seite angezeigt wird. Da kommt es nach dem Einloggen gar nicht erst zur Ausführung des felogin/newloginbox Codes und des dazugehörigen Hooks.
Da besteht die Möglichkeit, die Extension auf jeder Seite einzubinden und die Werte nur dann zu kopieren, wenn ein Benutzer eingeloggt ist und das Backup sich vom lastlogin-Wert unterscheidet. Sobald man es einmal kopiert hat, ist es nicht mehr der Fall. Die Werte, die man zum Vergleichen benötigt stehen praktischerweise direkt im GLOBALS Objekt, das beim Einloggen mit allen in der Datenbank verfügbaren Daten des Benutzerdatensatzes geladen wird.

Flexforms (Part 1)

Bei der Entwicklung von eigenen Extensions arbeite ich im BE fast nur noch mit Flexforms – es ist wirklich toll, dass man damit fast alles an Eingaben realisieren kann. Ich wollte mal ein paar sinnvolle Schnipsel zusammenstellen, wie man bestimmte Sachen definiert, ansonsten muss man in tt_news nachschauen (wunderbares Beispiel) und in anderen Extensions, wenn man was bestimmtest benötigt.
Wenn man den Kickstarter nutzt, dann wird gleich das richtige Grundgerüst definiert, aber hier ist es nochmal:




1






Die Sheets werden in Typo3 in Form von Reitern dargestellt. Ein Sheet kann einen beliebigen Namen haben (würd ich behaupten), der Kickstarter erzeugt eines, das sDEF heißt. Darin befindet sich ein Element namens ROOT und darin wird in TCEforms der Inhalt des Sheets definiert.




LLL:EXT:np_content_slideshow/locallang_db.xml:ff.settings

array






Innerhalb des el-Elements (ist vom Typ Array) können nun unterschiedliche Felder definiert werden. Der Name dieser Felder ist beliebig (darf keine Leer- und Sonderzeichen enthalten), darüber kann der Wert der Felder im Plugin in der PHP-Klasse ausgelesen werden.
Hier ist z.B. eine Checkbox:



1


check




Der Wert heißt „random“ und kann im BE (MVC-Style) wie folgt ausgelesen werden:

$random = intval($this->configurations->get(‚random‘));

Ich habe mit das irgendwie so angewöhnt, die Locallang-Wert mit ff. zu versehen, damit man erkennt, dass es in den Flexforms verwendet wird.
Reicht für heute 🙂

Geschrieben in TYPO3 | Kommentare deaktiviert für Flexforms (Part 1)

Templa Voila: Redakteure können keine Inhalte löschen

Problem war, dass Redakteure keine Inhalte löschen konnten, aber auch nur manchmal. Es war möglich in der Listenansicht, aber nicht über das Mülleimer-Symbol in der „normalen“ Content bearbeiten Ansicht.
Die Rechte waren auf den ersten Blick richtig gesetzt, die Zugriffsrechte auch. Beim Anlegen der Elemente war es auch komisch – innerhalb eines 2-spaltigen FCEs war es nicht möglicht, dahinter oder davor schon. Wenn man doch ein Element innerhalb des 2-spaltigen FCE anzulegen versuchte, wurde es nicht korrekt verknüft und als „nicht verwendet“ dargestellt.

Die Lösung: Templa Voila bringt ein weiteres Feld mit, das sich in der Liste der „allowed excludfields“ gut tarnt – Seite:Inhalt. Dieses Feld muss bei der Gruppe mit ACLs ausgewählt werden und schon funktioniert es.

http://www.typo3.net/forum/list/list_post//73930/

Aktuelles Datum ausgeben (Jahr in Footer)

Vergesse ich andauernd – so kann man das aktuelle Jahr in TypoScript ausgeben:

10 = TEXT
10.data = date: Y

Für weiteres in der Funktion date von php nachschauen:
d.m.Y. für aktuelles Datum
Update:
Bei vielen Seiten steht das aktuelle Jahr und das Copyright-Zeichen im Footer der Seite. Am besten kann man das mir diesem Schnipsel lösen, dann ist das Jahr immer aktuell. Wie man den Wrap gestaltet, ist jedem selbst überlassen.

10 = TEXT
10 {
data = date:U
strftime = %Y
wrap = ©| npostnik.de
}

Geschrieben in TYPO3 | Kommentare deaktiviert für Aktuelles Datum ausgeben (Jahr in Footer)

Rahmen um Bilder rendern (oder eben nicht)

Manchmal ist es notwendig, dass die Bilder, die im BE reingestellt werden, im FE ein bestimmtes Aussehen verpasst bekommen, wie z.B. einen Rahmen in 2 Farben oder abgerundete Ecken. Interessanterweise hat sich rausgestellt, dass es einfacher ist, runde Ecken ins Bild zu rendern, als einen festen Rahmen.
Hier die Anleitung zum Erweitern des Render-Mechanismus, damit alle Bilder mit runden Ecken versehen werden:
Dynamische Masken
Zu beachten dabei ist, dass die Stärke der Abrundung im Zusammenhang steht mit der Ausgangsbildgröße und der Ausgabebildgröße, d.h. alle Ecken sind unterschiedlich groß. Die Maske wird nämlich auf das ursprüngliche Bild gelegt und dann mit dem Bild zusammen kleiner skaliert, so dass es nicht möglich ist, bei allen Bildern in in jeder Eingangs- und Ausgangsgröße die Ecken gleich groß zu gestalten.
Ein gute Lösung für diese Problem ist mir bisher nicht bekannt. Was man aber machen kann, ist mit den Typo3 Variablen in borderSpace und wrap zu experimentieren, so dass man auf die Bilder einen Rand legen kann oder z.B. runde Ecken. Theoretisches Beispiel:

wrap =

… [etc.]|


Und so ein CSS:

.roundcorners {
position: relative;
}
.roundcorners .topleft {
position: absolute;
top: 0;
left: 0;
}
.roundcorners .topright {
position: absolute;
top: 0;
right: 0;
}

Geschrieben in TYPO3 | Kommentare deaktiviert für Rahmen um Bilder rendern (oder eben nicht)

Rootline Menu

Kleines hübsches Rootline-Menü in dem Stil:
Seite > Unterseite > Aktuelle Seite
Das letze ist nicht verlinkt.

lib.ROOTLINE = HMENU
lib.ROOTLINE {
special = rootline
excludeDoktypes = 6
special.range = 1|-1
1 = TMENU
1.wrap = |
1.NO.allWrap = | > |*|| > |*||
1.NO.doNotLinkIt = |*| |*| 1
}

Auf das doNotLinkIt wäre ich so nie gekommen, habs von hier.

Geschrieben in TYPO3 | Kommentare deaktiviert für Rootline Menu

indexed_search „zerstückeln“

Auf vielen Seiten gibt es eine Suchbox, die oben irgendwo in der Ecke steht. Wenn man da was eingibt und absendet, landet man auf einer Seite, auf der die Ergebnisse angezeigt werden, meistens steht da auch noch eine Suchbox darüber. Was ist aber wenn man die Suchbox über den Ergebnissen nicht haben möchte, und für die kleine Suchbox oben in der Ecke nicht gleich die Macina Searchbox verwenden möchte und der Pagebrowser trotzdem funktionieren soll.

Zunächstmal braucht man nicht gleich die Macina Searchbox, um eine Box in einer Ecke zu machen, reicht ein wenig Typoscript.

lib.search = COA_INT
lib.search {
10 = TEXT
10.value =
20 = HTML
20.value =
wrap =

|

}

Fertig ist die Box! Man kann natürlich auch Klassen hinzufügen, um das Ding zu stylen oder ein fieldset drumrum. Die searchPagePID ist eine Konstante, die man definieren muss, an diese Seite wird das Ergebnis gesendet.

Auf die Ergebnisseite wird das Plugin indexed_search gelegt. Wenn man da aber das Formular nicht haben möchte, kann man es nicht einfach entfernen. Denn der Pagebrowser verlinkt nicht einfach, da wird per JavaScript ein Wert in dem Formular geändert und das Formular anschließend gesendet. Und wenn kein Formular da ist, dann gibt es JavaScript Fehlermeldungen. Mögliche Lösung ist das Ausblenden des Formulars mit CSS oder das verstecken der ungewollten Felder mit type=“hidden“.
Zu beachten ist bei all dem, dass das Formular in der Box einen anderen Namen hat, als die Suchbox selbst. Dann falls die gleich sind, gibt es auch Probleme beim Pagebrowser.

Und noch folgende ätzende Sachen: die Ausgabe der indexed_search läßt sich nicht steuern, d.h. es wird immer die Box, danach der Pagebrowser und dann das Ergebnis augegeben. Die Reihenfolge kann man nicht geeinflussen, man kann keine Wraps um die Bereiche machen und man kann sie nicht ausblenden, um irgendwann die indexed_search nochmehr zu zerstückeln (z.B. Suchbox in Spalte 1, Ausgabe in Spalte 2 und Pagebrowser in Spalte 3).

indexed_search durchsucht Meta-Tags

Problem: indexed_search fügt zu der Ergebnisliste auch die Meta-Tags hinzu. Blöd, weil die erstens auf jeder Seite die gleichen sind und so das Ergebnis erheblich verfälschen, zweitens weil die Meta-Tags direkt hintereinander ohne Leerzeichen geschrieben werden und so in meinem Liebligsbrowser(IE6) das Layout sprengen.
Zum Glück gibt es Kollegen, die das kennen und mit einem Bugfix aushelfen können.
Hier der Link: Indexed Search Metatags ignorieren
Falls die Seite mal weg sein sollte (oder jemanden das tolle Bananenbild stört), hier die Lösung. Die folgenden zwei Zeilen in indexed_search/class.indexer.php in der Funktion splitHTMLContent suchen und auskommentieren. Prost!

if(stristr($meta[$i][’name‘],’keywords‘)) $contentArr[‚keywords‘].=‘,‘.$meta[$i][‚content‘];
if(stristr($meta[$i][’name‘],’description‘)) $contentArr[‚description‘].=‘,‘.$meta[$i][‚content‘];

Geschrieben in TYPO3 | Kommentare deaktiviert für indexed_search durchsucht Meta-Tags

Sprachumschalter mit Flaggen

(vor allem für Markus, dem besten besten Freund, den man sich vorstellen kann)

Zunächst braucht man die Extension sr_language_menu, die schon die meiste Arbeit, wie das Abfragen, ob eine Seite existiert, ob eine Übersetzung vorhanden ist und das Markieren der aktuellen Sprache übernimmt. Dann kann man die Extension über den Constant Editor konfigurieren, da ist das meiste selbsterklärend.
Es gibt ein kleines Problem damit, dass Typo3 als internationale Anwendung davon ausgeht, dass Englisch die Default Sprache ist. Aber da kann man tricksen.

Das ist ein Auszug aus dem Templates (Constants), in dem Deutsch und Englisch als Sprache definiert werden. Wenn die Language ID 1 angegeben ist, dann wird die englische Version der Seite angezeigt.

config {
sys_language_uid = 0
language = de
locale_all = de_DE.UTF-8
}
[globalVar = GP:L = 1]
config {
sys_language_uid = 1
locale_all = en_EN.UTF-8
language = en
}
[global]

Hier wird eine Liste der Sprachen neben der Default angegeben.

# list of configured languages for lang selector
languageUids = 1

Und in diesem Teil wird im Setup das Wrap um die Menüpunkte angegeben.

// setup
plugin.tx_srlanguagemenu_pi1 {
flag.NO.stdWrap.wrap = |
flag.INACT.stdWrap.wrap =
flag.CUR.stdWrap.wrap =
}

Dann muss nur noch ein Menü zum Umschalten von Sprachen generiert werden. Dieser Schnipsel erzeugt ein kleines Menü mit „Sprache“ als Label. Je nachdem was vorher in Constants definiert worden ist, werden Flaggen oder eine Liste dargestellt. Nach dem Kopieren des Plugin-Inhaltes in lib.lang.10 wird noch angegeben, dass Deutsch die Default-Sprache ist, und falls man Flaggen benutzt, muss hier der Pfad zu einer deutschen Flagge angegeben werden, die aber auch im Extension-Verzeichnis liegend kann (dann fängt der Pfad mit EXT an). Weiter darunter ist definiert, wenn die aktuelle Sprache englisch ist, soll da dementsprechend Language stehen.

lib.lang = COA
lib.lang.5 = TEXT
lib.lang.5.value = Sprache:
lib.lang.5.wrap =

|

lib.lang.10 < plugin.tx_srlanguagemenu_pi1 lib.lang.10 { defaultLanguageISOCode = DE languagesUidsList = {$languageUids} defaultLayout = 0 englishFlagFile = fileadmin/gfx/flags/de.gif } [globalVar = GP:L = 1] lib.lang.5.value = Language: [global]
Wenn alles so weit vorbereitet ist, kann man das Objekt einem Marker im Template zuweisen.

np_subversion neu mit Diff-Viewer

Ich habs zwar nicht selbst programmiert, aber die Firma bei der ich arbeite. network.publishing hat eine Extension entwickelt, mit der man Subversion in Typo3 integrieren kann. Man legt Repositories an und definiert in weiteren Datensätzen, ob es sich um eine Workingcopy handelt oder einen Export und ob das Ziel eine Extension oder einfach nur ein Ordner ist.
Die Extension gibt es seit einem halben Jahr, aber das neue ist der Diff-Viewer, der es ermöglicht, nun auch online Unterschiede zu der letzen Version anzeigen zu lassen.
Wir nutzen die Extension bei allen neuen Projekten und entwickeln so Extension und verwalten den fileadmin Ordner. Ich nutze es sehr gerne und bin begeistert und kann es nur weiterempfehlen. Hier die Links:
News bei NP: np_subversion erhält Diff-Viewer
Extension im TER: np_subversion 0.7.1