adminHeader.ftl

 1   <#--
 2   Macro: adminHeader
 3   Description: Generates a header section for an administrative page, including a navigation menu and user account menu.
 4   Parameters:
 5   - site_name (string, required): the name of the website or application.
 6   -->
 7   <#macro adminHeader site_name=site_name!'Lutece' admin_url=admin_url >
 8   <#local userReadMode><#attempt>${dskey('portal.site.site_property.layout.user.readmode.show.checkbox')?number}<#recover>0</#attempt></#local>
 9   <#local userDarkMode><#attempt>${dskey('portal.site.site_property.layout.user.darkmode.show.checkbox')?number}<#recover>0</#attempt></#local>
 10   <#local userMenuMode><#attempt>${dskey('portal.site.site_property.layout.user.menumode.show.checkbox')?number}<#recover>0</#attempt></#local>
 11   <#local readMode><#attempt><#if dskey('portal.site.site_property.layout.readmode.checkbox')?number = 1> dir="rtl"</#if><#recover></#attempt></#local>
 12   <#local darkMode><#attempt><#if dskey('portal.site.site_property.layout.darkmode.checkbox')?number==1> theme-dark</#if><#recover></#attempt></#local>
 13   <#local layout><#attempt><#if dskey('portal.site.site_property.layout.menu.checkbox')?number==1>aside<#else>header</#if><#recover>header</#attempt></#local>
 14   <#local logoUrl = (dskey('portal.site.site_property.logo_url')!)?has_content?then(dskey('portal.site.site_property.logo_url'), 'themes/admin/shared/images/logo-header-icon.svg')>
 15   </head>
 16   <body class="antialiased"${readMode}>
 17   <@adminSkipNav />
 18   <div id="lutece-layout-wrapper" class="${layout!}" data-userdarkmode="${userDarkMode}" data-usermenu="${userMenuMode}">
 19   <header class="lutece-header" > 
 20   	<nav class="lutece-nav navbar navbar-expand-lg d-print-none" data-bs-theme="dark">
 21   		<div class="container-fluid">
 22   			<a class="lutece-brand navbar-brand navbar-brand-autodark d-none-navbar-horizontal pe-0" href="${dskey('portal.site.site_property.home_url')}" title="#i18n{portal.users.admin_header.title.viewSite} ${site_name}" target="_blank" title="#i18n{portal.site.portal_footer.newWindow}">
 23   				<img src="${logoUrl}" height="30" alt="Logo ${site_name}" aria-hidden="true">
 24   				<span class="ml-2 ms-2">${site_name}</span>
 25   			</a>
 26   			<button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target="#navbar-menu">
 27   				<span class="navbar-toggler-icon"></span>
 28   				<span class="visually-hidden">#i18n{portal.util.labelShow} / #i18n{portal.util.labelHide}</span>
 29   			</button>
 30   			<div class="lutece-collapse collapse navbar-collapse" id="navbar-menu">
 31   				<ul class="navbar-nav">
 32   					<#list feature_group_list as feature_group>
 33   						<#if feature_group.icon?length < 1>
 34   							<#assign icon_class = "ti ti-mood-empty">
 35   						<#else>
 36   							<#assign icon_class = feature_group.icon>
 37   						</#if>
 38   						<#if feature_group.features?size &gt; 1>
 39   							<li class="nav-item dropdown">
 40   								<a class="nav-link dropdown-toggle" id="dLabel${feature_group.id}Header" role="button" data-bs-toggle="dropdown" role="button" aria-expanded="false" href="${admin_url}#${feature_group.id}">
 41   									<i class="${icon_class} me-1"></i> <span>${feature_group.label}</span>
 42   								</a>
 43   								<div class="dropdown-menu" aria-labelledby="dLabel${feature_group.id}Header">
 44   									<div class="dropdown-menu-columns">
 45   										<div class="dropdown-menu-column">
 46   										<#list feature_group.features as feature>
 47   											<#if !feature.externalFeature>
 48   												<a class="dropdown-item" href="${feature.url}?plugin_name=${feature.pluginName}" title="${feature.name}">
 49   													<i class="${feature.iconUrl} me-1"></i> 
 50   													<span>${feature.name} </span>
 51   												</a>
 52   											<#else>
 53   												<a class="dropdown-item" href="${feature.url}" title="${feature.name}">
 54   													<#if feature.iconUrl?has_content><i class="${feature.iconUrl} me-1"></i></#if> 
 55   													<span>${feature.name}</span>
 56   												</a>
 57   											</#if>
 58   										</#list>
 59   										</div>
 60   									</div>
 61   								</div>
 62   							</li>
 63   						<#else>
 64   							<#list feature_group.features as feature>
 65   								<li class="nav-item">
 66   								<#if !feature.externalFeature>
 67   									<a class="nav-link" href="${feature.url}?plugin_name=${feature.pluginName}"><#if feature.iconUrl?has_content>
 68   										<i class="${feature.iconUrl} me-1"></i></#if> 
 69   										<span>${feature.name}</span>
 70   									</a>
 71   								<#else>
 72   									<a class="nav-link" href="${feature.url}"><#if feature.iconUrl?has_content><i class="${feature.iconUrl} me-1"></i></#if> 
 73   										<span>${feature.name}</span>
 74   									</a>
 75   								</#if>
 76   								</li>
 77   							</#list>
 78   						</#if>
 79   					</#list>
 80   					<li class="nav-item d-none d-lg-flex ms-auto">
 81   						<a class="nav-link"  href="${admin_url}" title="#i18n{portal.users.admin_header.homePage}" id="go-home">
 82   							<i class="ti ti-home"></i><span class="visually-hidden">#i18n{portal.users.admin_header.homePage}</span>
 83   						</a>
 84   					</li>
 85   					<li class="nav-item d-flex d-lg-none mt-2">
 86   						<a class="nav-link"  href="${admin_url}" title="#i18n{portal.users.admin_header.homePage}" id="go-home">
 87   							<i class="ti ti-home me-2"></i> <span>#i18n{portal.users.admin_header.homePage}</span>
 88   						</a>
 89   					</li>
 90   					<#if userMenuMode?number = 1>
 91   					<li class="nav-item d-none d-lg-flex">
 92   						<div class="nav-link" title="#i18n{portal.users.admin_header.labelMenuV} / #i18n{portal.users.admin_header.labelMenuH}" id="switch-menu" tabindex="0" role="button" data-bs-toggle="tooltip" data-bs-animation="false" data-bs-placement="bottom" data-bs-original-title="#i18n{portal.users.admin_header.labelMenuV} / #i18n{portal.users.admin_header.labelMenuH}">
 93   							<i class="ti ti-layout-navbar-collapse menu-rotate-icon"></i><span class="visually-hidden">#i18n{portal.users.admin_header.labelMenuV} / #i18n{portal.users.admin_header.labelMenuH}</span>
 94   						</div> 
 95   					</li>
 96   					</#if>
 97   					<#if userDarkMode?number = 1>
 98   					<li class="nav-item" id="switch-darkmode">
 99   						<div class="nav-link d-none d-lg-flex" tabindex="0" role="button">
 100   							<i class="ti ti-moon"></i><span class="visually-hidden">#i18n{portal.users.admin_header.labelMode} <span>#i18n{portal.users.admin_header.labelDarkMode}</span></span>
 101   						</div>
 102   						<div class="nav-link d-flex d-lg-none" tabindex="0" role="button">
 103   							<i class="ti ti-moon me-2"></i> <span>#i18n{portal.users.admin_header.labelMode} #i18n{portal.users.admin_header.labelDarkMode}</span>
 104   						</div>
 105   					</li>
 106   					</#if>
 107   					<#if userReadMode?number = 1>
 108   						<@adminReadMode />
 109   					</#if>
 110   					<#if user.userLevel == 0>
 111   						<#if listLoggersInfo??>
 112   						<#assign listLogDebug = listLoggersInfo?filter( logInfo -> ( logInfo.level = 'DEBUG' || logInfo.level = 'TRACE' ) ) />
 113   						<#if listLogDebug?has_content>
 114   							<li class="nav-item d-none d-lg-flex">
 115   								<a href="#" class="nav-link" data-bs-toggle="dropdown" tabindex="-1" aria-label="Show notifications" aria-expanded="false">
 116   									<svg xmlns="http://www.w3.org/2000/svg" class="icon" width="24" height="24" viewBox="0 0 24 24" stroke-width="2" stroke="currentColor" fill="none" stroke-linecap="round" stroke-linejoin="round"><path stroke="none" d="M0 0h24v24H0z" fill="none"></path><path d="M10 5a2 2 0 0 1 4 0a7 7 0 0 1 4 6v3a4 4 0 0 0 2 3h-16a4 4 0 0 0 2 -3v-3a7 7 0 0 1 4 -6"></path><path d="M9 17v1a3 3 0 0 0 6 0v-1"></path></svg>
 117   									<#if listLoggersInfo?has_content><span class="badge bg-red"></span></#if>
 118   								</a>
 119   								<div class="dropdown-menu dropdown-menu-arrow dropdown-menu-end dropdown-menu-card">
 120   									<div class="card">
 121   										<div class="card-header">
 122   											<h3 class="card-title">Notifications</h3>
 123   										</div>
 124   										<div class="list-group list-group-flush list-group-hoverable">
 125   											<div class="list-group-item logger">
 126   												<div class="row align-items-start">
 127   													<div class="col-auto pt-2">
 128   														<span class="badge bg-red d-block"></span>
 129   													</div>
 130   													<div class="col text-truncate">
 131   														<h3><a href="#" class="text-body d-block">#i18n{portal.util.log.warningLevel}</a></h3>
 132   														<#list listLogDebug as logInfo>
 133   															<#if logInfo?size gt 0><div class="d-block text-truncate mt-1" title="${logInfo.path!}"><strong>${logInfo.name!}  - ${logInfo.level!}</strong> ${logInfo.path!}</div></#if>
 134   														</#list>
 135   													</div>
 136   												</div>
 137   											</div>
 138   										</div>
 139   									</div>
 140   								</div>
 141   							</li> 
 142   						</#if>
 143   					</#if>
 144   					<li class="nav-item d-none d-lg-flex">
 145   						<a class="nav-link" href="jsp/admin/ManageProperties.jsp" title="#i18n{portal.site.adminFeature.properties_management.name}" >
 146   							<i class="ti ti-home-cog"></i>
 147   							<span class="visually-hidden">#i18n{portal.site.adminFeature.properties_management.name}</span>
 148   						</a>
 149   					</li>
 150   					<li class="nav-item d-flex d-lg-none">
 151   						<a class="nav-link" href="jsp/admin/ManageProperties.jsp" title="#i18n{portal.site.adminFeature.properties_management.name}" >
 152   							<i class="ti ti-home-cog me-2"></i> <span>#i18n{portal.site.adminFeature.properties_management.name}</span>
 153   						</a>
 154   					</li>
 155   					<li class="nav-item d-none d-lg-flex">
 156   						<a class="nav-link" href="jsp/admin/AdminTechnicalMenu.jsp" title="#i18n{portal.admindashboard.view_dashboards.title}">
 157   							<i class="ti ti-settings"></i>
 158   							<span class="visually-hidden">#i18n{portal.admindashboard.view_dashboards.title}</span>
 159   						</a>
 160   					</li>
 161   					<li class="nav-item d-flex d-lg-none">
 162   						<a class="nav-link" href="jsp/admin/AdminTechnicalMenu.jsp" title="#i18n{portal.admindashboard.view_dashboards.title}">
 163   							<i class="ti ti-settings me-2"></i> <span>#i18n{portal.admindashboard.view_dashboards.title}</span>
 164   						</a>
 165   					</li>
 166   					</#if>
 167   					<li class="nav-item dropdown d-none d-lg-flex">
 168   						<a href="#" class="nav-link nav-info nav-user-info lh-1 py-0 px-2 text-reset dropdown-toggle" data-bs-toggle="dropdown" role="button" >
 169   							<span class="visually-hidden">#i18n{portal.util.labelMore}</span>
 170   							<span class="avatar avatar-sm" style="background-image:url(<#if adminAvatar>servlet/plugins/adminavatar/avatar?id_user=${user.userId}<#else>#dskey{portal.site.site_property.avatar_default}</#if>)"></span>
 171   							<div class="ps-2 pt-3 user-infos">
 172   								<p class="mb-0 fs-5 user-login">${dashboard_zone_4!}</p>
 173   								<p class="mt-0 small user-date">${user.dateLastLogin!}</p>
 174   							</div>
 175   						</a>
 176   						<div class="dropdown-menu dropdown-menu-end dropdown-menu-arrow nav-info">
 177   						<#if userMenuItems?has_content>   
 178   							<#list userMenuItems as item>
 179   								${item.content}
 180   							</#list>
 181   						</#if>
 182   						<div class="dropdown-divider nav-info"></div>
 183   						<#if admin_logout_url?has_content>
 184   						<a class="dropdown-item dropdown-logout d-none d-lg-flex" href="${admin_logout_url}" title="#i18n{portal.users.admin_header.deconnectionLink}">
 185   							<i class="ti ti-logout me-1"></i> 
 186   							<span>#i18n{portal.users.admin_header.deconnectionLink}</span>
 187   						</a>
 188   						</#if> 
 189   						</div>
 190   					</li>
 191   					<li class="nav-item justify-content-start d-lg-none">
 192   						<a class="nav-link dropdown-toggle" id="mobile_usermenuitems" role="button" data-bs-toggle="dropdown" role="button" aria-expanded="false" href=""><i class="ti ti-user me-2"></i>${dashboard_zone_4!}</a>
 193   						<#if userMenuItems?has_content>
 194   							<ul class="dropdown-menu">
 195   								<li class="nav-item d-flex"><span class="dropdown-item"><i class="ti ti-calendar me-2"></i> #i18n{portal.users.admin_header.labelLastLogin} ${user.dateLastLogin!}</span></li>
 196   								<#list userMenuItems as item>
 197   								<li class="nav-item d-flex">${item.content}</li>
 198   								</#list>
 199   							</ul>
 200   						</#if>
 201   					</li>
 202   					<#if admin_logout_url?has_content>
 203   					<li class="nav-item d-flex d-lg-none">
 204   						<a class="nav-link" href="${admin_logout_url}" title="#i18n{portal.users.admin_header.deconnectionLink}">
 205   							<i class="ti ti-logout me-2"></i> 
 206   							<span>#i18n{portal.users.admin_header.deconnectionLink}</span>
 207   						</a>
 208   					</li>	
 209   					</#if>
 210   				</ul>
 211   				<button id="aside-header-collapse" class="btn btn-dark btn-sm mt-5" type="button" title="#i18n{portal.util.labelToggleSize}">
 212   					<span class="ti ti-switch-horizontal"></span>
 213   					<span class="visually-hidden">#i18n{portal.util.labelToggleSize}</span>
 214   				</button>
 215   			</div>
 216   		</div>
 217   	</nav>
 218   <#if user.userLevel == 0>
 219   <script>
 220   document.addEventListener( 'DOMContentLoaded', () => {	
 221   	const loggers = document.querySelector('.logger') ;
 222   	if( loggers != null && loggers.childElementCount > 0 && document.getElementById('adminModal') != null ){
 223   		if( !sessionStorage.getItem('lutece-debug-modal') ){
 224   			sessionStorage.setItem('lutece-debug-modal', false )
 225   		}
 226   		var modalContent = '<h3>#i18n{portal.util.log.warningLevel}</h3><p><strong>#i18n{portal.util.log.modalWarningMessage}</strong></p><p class="text-center"><button class="btn btn-sm btn-danger" data-toggle="collapse" data-target="#info-log" aria-expanded="false" aria-controls="info-log" type="button">#i18n{portal.util.log.modalLabelButton}</button></p><blockquote class="collapse" id="info-log">' + loggers.querySelector('.col.text-truncate').innerHTML + '</blockquote>';
 227   		var adminModal = document.getElementById('adminModal');
 228   		var adminModalLabel = document.getElementById('adminModalLabel');
 229   		var adminModalBody = document.querySelector('#adminModal .modal-body');
 230   		if( adminModalBody != null){
 231   			adminModalBody.insertAdjacentHTML( 'beforeEnd', modalContent);
 232   		}
 233   		var adminModalHeader = document.querySelector('#adminModal .modal-header');
 234   		var adminModalHeaderBtn = document.querySelector('#adminModal .modal-header button');
 235   		var myAdminModal = new bootstrap.Modal( adminModal, {} );
 236   		adminModalLabel.insertAdjacentHTML( 'beforeEnd', '#i18n{portal.util.log.modalWarningTitle}' );
 237   		adminModalHeader.classList.add('text-white');
 238   		adminModalHeaderBtn.setAttribute( 'style', 'background: transparent url("data:image/svg+xml,%3csvg xmlns=\'http://www.w3.org/2000/svg\' viewBox=\'0 0 16 16\' fill=\'%23ffffff\'%3e%3cpath d=\'M.293.293a1 1 0 011.414 0L8 6.586 14.293.293a1 1 0 111.414 1.414L9.414 8l6.293 6.293a1 1 0 01-1.414 1.414L8 9.414l-6.293 6.293a1 1 0 01-1.414-1.414L6.586 8 .293 1.707a1 1 0 010-1.414z\'/%3e%3c/svg%3e") center/.75rem auto no-repeat;');
 239   		adminModalHeader.classList.add('bg-danger');
 240   		adminModalBody.classList.add('text-danger');
 241   		adminModal.addEventListener('hide.bs.modal', function () {
 242   			sessionStorage.setItem('lutece-debug-modal',true);
 243   		})	
 244   		if( sessionStorage.getItem('lutece-debug-modal') === 'false' ){
 245   			myAdminModal.show();
 246   		}
 247   	}
 248   }); 
 249   </script>
 250   </#if>
 251   </header> 
 252   </#macro>