Hello there,
we ran into a weird issue on a system we recently updated to TYPO3 10.
We use HMENU to build the language navigation, as this part was not rebuilt during the update.
The configuration looks like this:
Show typoscriptHide typoscript
lib.langNav = HMENU
lib.langNav {
special = language
special.value = {$lang.uids_for_langNav}
stdWrap.wrap = <h2 class="hidden">{$TEXT.titleLangnav}</h2><div class="langNavContainer"><ul id="langNav">|</ul></div><hr class="hidden" />
addQueryString = 1
addQueryString.method = GET
addQueryString.exclude = FE,tx_srfeuserregister_pi1,MAX_FILE_SIZE,user,pass,L
1 = TMENU
1 {
NO = 1
NO {
allWrap = <li class="first">|</li>|*|<li>|</li>|*|<li>|</li>
stdWrap.cObject = TEXT
stdWrap.cObject.value = {$lang.titles_for_langNav_new}
ATagTitle = {$TEXT.titleLang}
ATagParams = title="{$lang.titles_for_langNav_new}"
}
ACT < .NO
ACT {
allWrap = <li class="first act"><span>|</span></li>|*|<li class="act"><span>|</span></li>|*|<li class="act"><span>|</span></li>
ATagParams = class="act"
doNotLinkIt = 1
}
# Wenn es keine Übersetztung gibt
USERDEF1 < .NO
USERDEF1 {
doNotLinkIt = 1
allWrap = <li class="first noLink"><span>|</span></li class="noLink">|*|<li><span>|</span></li>|*|<li class="noLink"><span>|</span></li>
}
}
}
What happens is, that if I add any parameter to the page URL, the page would load as usally, when I then switch the language, the parameter stays. Excluding any parameter solves this but this is ignored with the L parameter. Additionally, the language navigation is cached with this parameter until the next time the cache is stale, which means lots and lots of links with a L=X parameter attached to them through the site.
Luckily, the L parameter does not affect the rendering of the content, as this is properly managed via the language that is detected in the URL (e.g. /de/
, /fr/
, ...) but other HMENU items on the page, that are also told to ignore the L parameter do not follow this rule and simply append the parameter when building the URL.
This is how the main menu is built:
Show typoscriptHide typoscript
lib.navBarMenu = HMENU
lib.navBarMenu {
wrap (
<nav><hr class="hidden" />
<h2 class="hidden">{$TEXT.titleMainnav}</h2>
<span class="stick stick-l"></span>
<span class="stick "></span>
<ul id="mainNav" class="hidden-xs hidden-sm nav navbar-nav ">|</ul></nav>
)
1 = TMENU
1 {
expAll = 1
noBlur = 1
NO = 1
NO {
typolink.addQueryString = 0
stdWrap.cObject = TEXT
stdWrap.cObject.field = title
# configure hidden navtitle-div which is used for level2 (see below)
stdWrap.postCObject = TEXT
stdWrap.postCObject {
wrap = <div class="hidden navtitle">|</div>
field = title
override.cObject = TEXT
override.cObject {
field = nav_title
if.isTrue.field = nav_title
}
}
wrapItemAndSub = <li>|</li> |*| <li>|</li> |*| <li class="ipsearch">|</li>
stdWrap.dataWrap.stdWrap.cObject = COA
stdWrap.dataWrap.stdWrap.cObject {
10 = TEXT
10.value = <span class="hidden-sm">|</span>
20 = TEXT
20.field = subtitle // title
20.wrap = <span class="hidden-md hidden-lg">|</span>
}
ATagParams = class="level1link" |*| class="level1link" |*| class="level1link"
ATagTitle {
field = title
//stdWrap.override.cObject = TEXT
//stdWrap.override.cObject.field = nav_title
//stdWrap.override.if.isTrue.field = nav_title
}
}
IFSUB = 1
IFSUB < .NO
IFSUB {
wrapItemAndSub = <li class="dropdown "><span class="nav-icon"></span>|</li> |*| <li class="dropdown "><span class="nav-icon"></span>|</li> |*| <li class="dropdown ipsearch"><span class="nav-icon"></span>|</li>
wrapItemAndSub.insertData = 1
ATagBeforeWrap = 1
ATagParams = class="dropdown-toggle" |*| class="dropdown-toggle" |*| class="dropdown-toggle"
}
# Copy properties of normal to active state, and then add a CSS class for styling
ACTIFSUB = 1
ACTIFSUB < .IFSUB
ACTIFSUB {
wrapItemAndSub = <li class="dropdown active "><span class="nav-icon"></span>|</li> |*| <li class="dropdown active "><span class="nav-icon"></span>|</li> |*| <li class="dropdown active ipsearch "><span class="nav-icon"></span>|</li>
}
CURIFSUB = 1
CURIFSUB < .IFSUB
CURIFSUB {
wrapItemAndSub = <li class="dropdown active "><span class="nav-icon"></span>|</li> |*| <li class="dropdown active "><span class="nav-icon"></span>|</li> |*| <li class="dropdown active ipsearch "><span class="nav-icon"></span>|</li>
}
# Copy properties of normal to active state, and then add a CSS class for styling
ACT = 1
ACT < .NO
ACT {
wrapItemAndSub = <li class="active">|</li> |*| <li class="active">|</li> |*| <li class="active ipsearch">|</li>
}
# Copy properties of normal to current state, and then add a CSS class for styling
CUR = 1
CUR < .NO
CUR {
wrapItemAndSub = <li class="active">|</li> |*| <li class="active">|</li> |*| <li class="active ipsearch">|</li>
}
}
2 = TMENU
2 {
wrap = <div class="megaMenu dropdown-menu"><ul class="subNav menuCol">|</ul></div>
# configure overview l1-overview link
stdWrap.preCObject = TEXT
stdWrap.preCObject.value (
<li class="overview"></li>
)
expAll = 1
noBlur = 1
NO = 1
NO {
wrapItemAndSub = <li class="level2 noSub">|</li>
ATagParams = class="level2link"
ATagTitle.field = title
}
ACT = 1
ACT {
wrapItemAndSub = <li class="level2 noSub">|</li>
ATagParams = class="level2link"
ATagTitle.field = title
}
CUR = 1
CUR {
wrapItemAndSub = <li class="level2 noSub">|</li>
ATagParams = class="level2link"
ATagTitle.field = title
}
IFSUB = 1
IFSUB {
wrapItemAndSub = <li class="level2">|</li>
ATagParams = class="level2link"
stdWrap.wrap >
}
ACTIFSUB = 1
ACTIFSUB {
wrapItemAndSub = <li class="level2">|</li>
ATagParams = class="level2link act"
stdWrap.wrap >
}
CURIFSUB = 1
CURIFSUB {
wrapItemAndSub = <li class="level2">|</li>
ATagParams = class="level2link cur"
stdWrap.wrap >
}
SPC = 1
SPC {
doNotShowLink = 1
allWrap = </ul> | <ul class="subNav menuCol">
}
}
3 < .2
3 {
stdWrap.preCObject >
wrap = <div class="sub-menu-col"><ul class="subNav ">|</ul></div>
NO = 1
NO {
wrapItemAndSub = <li class="level2"><div class="">|</div></li>
ATagParams = class="level3link"
ATagTitle.field = title
}
ACT = 1
ACT {
wrapItemAndSub = <li class="level2"><div class="">|</div></li>
ATagParams = class="level3link act"
ATagTitle.field = title
}
CUR = 1
CUR {
wrapItemAndSub = <li class="level2"><div class="">|</div></li>
ATagParams = class="level3link cur"
ATagTitle.field = title
}
IFSUB >
ACTIFSUB >
CURIFSUB >
}
}
The lib.navBarMenu.1.NO.typolink.addQueryString = 0
works for every other parameter that I can throw at the URL but the L
-parameter is always appended.
I guess this is a bug in how HMENU builds it's URLs with typolink and just does not check for typolink.addQueryString (but it should, according to the documentation).
I'll try to look into it myself and provide a patch if I come around but maybe somebody else already knows how to solve this differently, in which case I'll be happy with it, too.