S'ha produït un error mentre es processava la plantilla.
The following has evaluated to null or missing:
==> webContentData.titleMap.ca_ES [in template "20097#20123#BLOG_DETALLE" at line 351, column 41]
----
Tip: It's the step after the last dot that caused this error, not those before it.
----
Tip: If the failing expression is known to legally refer to something that's sometimes null or missing, either specify a default value like myOptionalVar!myDefault, or use <#if myOptionalVar??>when-present<#else>when-missing</#if>. (These only cover the last step of the expression; to cover the whole expression, use parenthesis: (myOptionalVar.foo)!myDefault, (myOptionalVar.foo)??
----
----
FTL stack trace ("~" means nesting-related):
- Failed at: ${webContentData.titleMap.ca_ES} [in template "20097#20123#BLOG_DETALLE" at line 351, column 39]
----
1<#-- Parseo de la fecha de publicación y días -->
2<#assign publishDate = .vars['reserved-article-display-date'].data>
3<#assign originalLocale = .locale>
4<#setting locale = localeUtil.getDefault()>
5<#assign publishDate = publishDate?datetime("EEE, d MMM yyyy HH:mm:ss Z")>
6<#assign publishDateIso8601 = publishDate?string("yyyy-MM-dd'T'HH:mm:ssXXX")>
7<#assign locale = originalLocale>
8<#assign localeCurrent = themeDisplay.getLocale() />
9
10<#assign numberOfSlides = GrupoImagenVideo.getSiblings()?size>
11
12<#-- Obtención de categorías del publicador de contenidos -->
13<#assign journalArticleResourceLocalService = serviceLocator.findService("com.liferay.journal.service.JournalArticleResourceLocalService")>
14<#assign assetEntryLocalService = serviceLocator.findService("com.liferay.asset.kernel.service.AssetEntryLocalService")>
15<#assign journalArticleId = .vars['reserved-article-id'].data>
16<#assign articleResourcePrimaryKey = journalArticleResourceLocalService.getArticleResourcePrimKey(groupId, journalArticleId)>
17<#assign assetEntry = assetEntryLocalService.getEntry("com.liferay.journal.model.JournalArticle", articleResourcePrimaryKey)>
18<#assign assetCategories = assetEntry.getCategories()>
19
20<#assign portalURL = themeDisplay.getPortalURL() />
21<#assign currentUrl = themeDisplay.getPortalURL() + themeDisplay.getURLCurrent() />
22<#assign metaTagUrlAutor = "${themeDisplay.getPortalURL()}/conocenos" />
23<#assign metaTagNameAutor = "Mutual Medica" />
24
25<#-- Obtención de otras noticias relacionadas -->
26<#assign GroupLocalService = serviceLocator.findService("com.liferay.portal.kernel.service.GroupLocalService")>
27<#assign assetEntryQuery = objectUtil('com.liferay.asset.kernel.service.persistence.AssetEntryQuery')>
28<#assign void = assetEntryQuery.setOrderByCol1("publishDate")>
29<#assign void = assetEntryQuery.setOrderByCol2("title")>
30<#assign relatedNews = assetEntryLocalService.getEntries(assetEntryQuery)>
31
32<div id="${randomNamespace}detallePost"
33 class="mm__content__detail">
34
35 <div class="container">
36
37 <#-- Título -->
38 <h1 id="titulo_post">
39 <#if (TitularPost.getData())??>
40 ${TitularPost.getData()}
41 </#if>
42 </h1>
43
44 <#-- Subtítulo -->
45 <h2 id="descripcion_post" class="col-md-10 px-0">
46 <#if (SubtituloPost.getData())??>
47 ${SubtituloPost.getData()}
48 </#if>
49 </h2>
50
51 <div class="mm__share">
52 <div class="dropdown">
53 <a class="dropdown-toggle"
54 href="#"
55 id="mm__social-network"
56 data-toggle="dropdown"
57 aria-haspopup="true"
58 aria-expanded="false">
59 <svg xmlns="http://www.w3.org/2000/svg"
60 width="50"
61 height="50"
62 viewBox="0 0 63 63"
63 fill="none">
64 <circle cx="31.5"
65 cy="31.5"
66 r="30"
67 stroke="#007BC2"
68 stroke-width="3" />
69 <path d="M41 44.8003L22 31.5003L41 18.2003"
70 stroke="#007BC2"
71 stroke-width="3" />
72 <circle cx="39.1008"
73 cy="20.1003"
74 r="5.3"
75 fill="white"
76 stroke="#007BC2"
77 stroke-width="3" />
78 <circle cx="39.1008"
79 cy="42.9001"
80 r="5.3"
81 fill="white"
82 stroke="#007BC2"
83 stroke-width="3" />
84 <circle cx="20.1008"
85 cy="31.5002"
86 r="5.3"
87 fill="white"
88 stroke="#007BC2"
89 stroke-width="3" />
90 </svg>
91 </a>
92 <div class="mm__social-network dropdown-menu dropdown-menu-right"
93 aria-labelledby="mm__social-network"
94 style="position: absolute; will-change: transform; top: 0px; transform: translate3d(25px, 30px, 0px); min-width: 0;">
95 <ul>
96 <li>
97 <a target="_blank"
98 class="share"
99 href="https://twitter.com/intent/tweet?original_referer=${TitularPost.getData()}&text=${TitularPost.getData()}&tw_p=tweetbutton&url=${currentUrl}&hashtags=MutualMedica">
100 <svg xmlns="http://www.w3.org/2000/svg"
101 width="35"
102 height="35"
103 fill="currentColor"
104 class="bi bi-twitter"
105 viewBox="0 0 16 16">
106 <path d="M5.026 15c6.038 0 9.341-5.003 9.341-9.334 0-.14 0-.282-.006-.422A6.685 6.685 0 0 0 16 3.542a6.658 6.658 0 0 1-1.889.518 3.301 3.301 0 0 0 1.447-1.817 6.533 6.533 0 0 1-2.087.793A3.286 3.286 0 0 0 7.875 6.03a9.325 9.325 0 0 1-6.767-3.429 3.289 3.289 0 0 0 1.018 4.382A3.323 3.323 0 0 1 .64 6.575v.045a3.288 3.288 0 0 0 2.632 3.218 3.203 3.203 0 0 1-.865.115 3.23 3.23 0 0 1-.614-.057 3.283 3.283 0 0 0 3.067 2.277A6.588 6.588 0 0 1 .78 13.58a6.32 6.32 0 0 1-.78-.045A9.344 9.344 0 0 0 5.026 15z" />
107 </svg>
108 </a>
109 </li>
110 <li>
111 <a target="_blank"
112 class="share"
113 href="https://wa.me/?text=${currentUrl}">
114 <svg xmlns="http://www.w3.org/2000/svg"
115 width="35"
116 height="35"
117 fill="currentColor"
118 class="bi bi-whatsapp"
119 viewBox="0 0 16 16">
120 <path d="M13.601 2.326A7.854 7.854 0 0 0 7.994 0C3.627 0 .068 3.558.064 7.926c0 1.399.366 2.76 1.057 3.965L0 16l4.204-1.102a7.933 7.933 0 0 0 3.79.965h.004c4.368 0 7.926-3.558 7.93-7.93A7.898 7.898 0 0 0 13.6 2.326zM7.994 14.521a6.573 6.573 0 0 1-3.356-.92l-.24-.144-2.494.654.666-2.433-.156-.251a6.56 6.56 0 0 1-1.007-3.505c0-3.626 2.957-6.584 6.591-6.584a6.56 6.56 0 0 1 4.66 1.931 6.557 6.557 0 0 1 1.928 4.66c-.004 3.639-2.961 6.592-6.592 6.592zm3.615-4.934c-.197-.099-1.17-.578-1.353-.646-.182-.065-.315-.099-.445.099-.133.197-.513.646-.627.775-.114.133-.232.148-.43.05-.197-.1-.836-.308-1.592-.985-.59-.525-.985-1.175-1.103-1.372-.114-.198-.011-.304.088-.403.087-.088.197-.232.296-.346.1-.114.133-.198.198-.33.065-.134.034-.248-.015-.347-.05-.099-.445-1.076-.612-1.47-.16-.389-.323-.335-.445-.34-.114-.007-.247-.007-.38-.007a.729.729 0 0 0-.529.247c-.182.198-.691.677-.691 1.654 0 .977.71 1.916.81 2.049.098.133 1.394 2.132 3.383 2.992.47.205.84.326 1.129.418.475.152.904.129 1.246.08.38-.058 1.171-.48 1.338-.943.164-.464.164-.86.114-.943-.049-.084-.182-.133-.38-.232z" />
121 </svg>
122 </a>
123 </li>
124 <li>
125 <a target="_blank"
126 class="share"
127 href="https://www.linkedin.com/shareArticle?mini=true&url=${currentUrl}&title=${TitularPost.getData()}&source=LinkedIn">
128 <svg xmlns="http://www.w3.org/2000/svg"
129 width="35"
130 height="35"
131 fill="currentColor"
132 class="bi bi-linkedin"
133 viewBox="0 0 16 16">
134 <path d="M0 1.146C0 .513.526 0 1.175 0h13.65C15.474 0 16 .513 16 1.146v13.708c0 .633-.526 1.146-1.175 1.146H1.175C.526 16 0 15.487 0 14.854V1.146zm4.943 12.248V6.169H2.542v7.225h2.401zm-1.2-8.212c.837 0 1.358-.554 1.358-1.248-.015-.709-.52-1.248-1.342-1.248-.822 0-1.359.54-1.359 1.248 0 .694.521 1.248 1.327 1.248h.016zm4.908 8.212V9.359c0-.216.016-.432.08-.586.173-.431.568-.878 1.232-.878.869 0 1.216.662 1.216 1.634v3.865h2.401V9.25c0-2.22-1.184-3.252-2.764-3.252-1.274 0-1.845.7-2.165 1.193v.025h-.016a5.54 5.54 0 0 1 .016-.025V6.169h-2.4c.03.678 0 7.225 0 7.225h2.4z" />
135 </svg>
136 </a>
137 </li>
138 <li>
139 <a target="_blank"
140 class="share"
141 href="mailto:?subject=${TitularPost.getData()}&body=${currentUrl}">
142 <svg xmlns="http://www.w3.org/2000/svg"
143 width="35"
144 height="35"
145 fill="currentColor"
146 class="bi bi-envelope"
147 viewBox="0 0 16 16">
148 <path d="M0 4a2 2 0 0 1 2-2h12a2 2 0 0 1 2 2v8a2 2 0 0 1-2 2H2a2 2 0 0 1-2-2V4Zm2-1a1 1 0 0 0-1 1v.217l7 4.2 7-4.2V4a1 1 0 0 0-1-1H2Zm13 2.383-4.708 2.825L15 11.105V5.383Zm-.034 6.876-5.64-3.471L8 9.583l-1.326-.795-5.64 3.47A1 1 0 0 0 2 13h12a1 1 0 0 0 .966-.741ZM1 11.105l4.708-2.897L1 5.383v5.722Z" />
149 </svg>
150 </a>
151 </li>
152 </ul>
153 </div>
154 </div>
155 </div>
156
157 <div class="mm__category" style="max-width: 30rem;">
158 <#list assetCategories as category>
159 <#if localeCurrent?contains("ca_ES")>
160 <a href="${portalURL}/ca/blog?categories=${category.getCategoryId()}"
161 class="btn">${category.getTitle(localeCurrent)}</a>
162 <#else>
163 <a href="${portalURL}/blog?categories=${category.getCategoryId()}"
164 class="btn">${category.getTitle(localeCurrent)}</a>
165 </#if>
166 </#list>
167 </div>
168
169 <div class="mm__date">
170 <p>
171 <#assign
172 webContentData = jsonFactoryUtil.createJSONObject(AutorPost.getData())
173 />
174
175 <#if webContentData?? && webContentData.title??>
176 <#if localeCurrent?contains("ca_ES")>
177 <#assign metaTagUrlAutor = portalURL + "/ca/autor?idAutor=" + webContentData.classPK />
178 <#assign metaTagNameAutor = webContentData.titleMap.ca_ES />
179 <a href="${portalURL}/ca/autor?idAutor=${webContentData.classPK}">
180 ${webContentData.titleMap.ca_ES}
181 </a>
182 <#else>
183 <#assign metaTagUrlAutor = portalURL + "/autor?idAutor=" + webContentData.classPK >
184 <#assign metaTagNameAutor = webContentData.titleMap.es_ES />
185 <a href="${portalURL}/autor?idAutor=${webContentData.classPK}">
186 ${webContentData.titleMap.es_ES}
187 </a>
188 </#if>
189 ·
190 </#if> ${publishDate?string["dd/MM/yy"]} · <#if (TiempoLecturaPost.getData())??> ${TiempoLecturaPost.getData()} </#if>
191 </p>
192 </div>
193 <#-- Carrusel de imagenes y vídeos -->
194 <#if GrupoImagenVideo.getSiblings()?has_content>
195
196 <div id="${randomNamespace}blogCarousel"
197 class="carousel slide mm-img-carousel"
198 data-ride="carousel"
199 data-interval="false"
200 data-wrap="false">
201 <div class="carousel-inner">
202 <#list GrupoImagenVideo.getSiblings() as multimedia>
203 <@printMultimedia multimedia multimedia?is_first />
204 </#list>
205 </div>
206
207 <#-- Indicadores carrusel si hay más de un elemento multimedia -->
208 <#if GrupoImagenVideo.getSiblings()?size gt 1 || TextoPost.getData()?contains('<div class="embed-responsive')>
209 <ol class="carousel-indicators">
210 <#assign contadorIndicadores = 0/>
211 <#list 0..<GrupoImagenVideo.getSiblings()?size as i>
212 <li data-target="#${randomNamespace}blogCarousel"
213 data-slide-to="${i}"
214 class="${(i == 0)?string('active','')}"
215 id="${randomNamespace}slide${i_index}"></li>
216 <#assign contadorIndicadores = contadorIndicadores + 1/>
217 </#list>
218 <#if TextoPost.getData()?contains('<div class="embed-responsive')>
219 <li data-target="#${randomNamespace}blogCarousel"
220 data-slide-to="${contadorIndicadores}"
221 class="${(contadorIndicadores == 0)?string('active','')}"
222 id="${randomNamespace}slide${contadorIndicadores}"></li>
223 </#if>
224 </ol>
225 </#if>
226
227 </div>
228 </#if>
229
230
231 <#-- Contenido principal de la post y enlaces -->
232
233 <div id="textoPost"
234 class="mm__text__notice">
235 <#if (TextoPost.getData())??>
236 ${TextoPost.getData()}
237 </#if>
238 </div>
239
240 <#if AdjuntosPost.getSiblings()?has_content>
241 <#if AdjuntosPost.getSiblings()[0].getData()?has_content>
242 <div class="mm__content__info-relacionada">
243
244 <h3><@liferay.language key="mutualmedica.blog.detalle.informacion" /></h3>
245 <#list AdjuntosPost.getSiblings() as enlaceVar>
246 <#if enlaceVar.getData()?has_content>
247 <#assign nombreDocumento = enlaceVar.getData()?split("/")>
248
249 <a class="mm__link__document"
250 href="${enlaceVar.getData()}"
251 target="_blank">${nombreDocumento[4]}</a>
252
253 </#if>
254 </#list>
255 </div>
256 </#if>
257 </#if>
258 <div class="mm__content__btn">
259 <#if localeCurrent?contains("ca_ES")>
260 <a class="mm__btn"
261 href="${portalURL}/ca/blog"><@liferay.language key="mutualmedica.blog.detalle.volver" /></a>
262 <#else>
263 <a class="mm__btn"
264 href="${portalURL}/blog"><@liferay.language key="mutualmedica.blog.detalle.volver" /></a>
265 </#if>
266 </div>
267 </div>
268
269</div>
270
271<div id="otrosPosts">
272 <#if relatedNews?has_content && (relatedNews?size > 1)>
273
274 <#assign baseUrl = themeDisplay.getScopeGroup().getPathFriendlyURL(themeDisplay.getLayout().isPrivateLayout(),themeDisplay)>
275 <#assign groupUrl = GroupLocalService.getGroup(themeDisplay.getLayout().getGroupId()).getFriendlyURL()>
276
277 <div class="mm__more__notices">
278 <div class="container">
279 <h2><@liferay.language key="mutualmedica.blog.detalle.otros" /></h2>
280 <div class="row">
281 <#assign relatedCount = 0 >
282 <#list relatedNews as related>
283 <#if relatedCount < 3>
284 <#if related.getClassName() == "com.liferay.journal.model.JournalArticle">
285 <#assign assetRenderer = related.getAssetRenderer()/>
286 <#assign journalArticle = assetRenderer.getAssetObject() />
287 <#if journalArticleId != journalArticle.articleId>
288 <#assign assetRenderer = related.getAssetRenderer()/>
289 <#assign journalArticle = assetRenderer.getAssetObject() />
290 <#assign document = saxReaderUtil.read(journalArticle.getContent())>
291 <#assign rootElement = document.getRootElement()>
292 <#assign defaultLanguageId = parseXml ("@default-locale", rootElement)>
293 <#assign layoutURL = journalArticle.urlTitle />
294 <#assign newsTitle = getField("TitularPost", localeCurrent, defaultLanguageId, rootElement)!>
295 <#assign imgPost = getField("ImagenPost", localeCurrent, defaultLanguageId, rootElement)!>
296 <#assign autPost = getField("AutorPost", localeCurrent, defaultLanguageId, rootElement)!>
297 <#assign templecPost = getField("TiempoLecturaPost", localeCurrent, defaultLanguageId, rootElement)!>
298
299
300 <#if newsTitle?has_content && newsTitle != "">
301 <#if localeCurrent?contains("ca_ES")>
302 <#assign urlDetalleOtroPost = portalURL + "/ca" + themeDisplay.getLayout().getFriendlyURL() + "/mutualmedica/" + journalArticle.getUrlTitle(localeCurrent)>
303 <#else>
304 <#assign urlDetalleOtroPost = portalURL + themeDisplay.getLayout().getFriendlyURL() + "/mutualmedica/" + journalArticle.getUrlTitle(localeCurrent)>
305 </#if>
306
307 <div class="col-12 col-md-4 col-xl-4"
308 onclick="location.href='${urlDetalleOtroPost}'">
309
310 <div class="mm__content__card"
311 tabindex="0"
312 title="${newsTitle}"
313 aria-label="${newsTitle}">
314
315
316 <#assign imgContentData = jsonFactoryUtil.createJSONObject(imgPost)/>
317 <div class="mm__content__image-list">
318 <#if imgPost?has_content && imgPost != "">
319 <#assign smallestImageURL = adaptiveMediaUtil.getAdaptiveMediaUrl(imgContentData.fileEntryId, '320') />
320 <#if (smallestImageURL?? && smallestImageURL!= "")>
321 <img loading="lazy" alt="${imgContentData.alt}"
322 src="${smallestImageURL}" />
323 <#else>
324 <img loading="lazy" alt="${imgContentData.alt}"
325 data-fileentryid="${imgContentData.fileEntryId}"
326 src="${imgContentData.url}" />
327 </#if>
328
329
330
331 </div>
332 </#if>
333
334
335
336 <#if newsTitle?has_content && newsTitle != "">
337 <h3>${newsTitle}
338 </h3>
339
340 <#assign relatedCount = relatedCount+1 >
341 <p>
342 ${journalArticle.displayDate?string["dd/MM/yy"]} <#if (templecPost)??>· ${templecPost} </#if> <#assign
343 webContentData = jsonFactoryUtil.createJSONObject(autPost)
344 />
345
346 <#if webContentData?? && webContentData.title??>
347 ·
348 <#if localeCurrent?contains("ca_ES")>
349 <a href="${portalURL}/ca/autor?idAutor=${webContentData.classPK}"
350 class="insideLink">
351 ${webContentData.titleMap.ca_ES}
352 </a>
353 <#else>
354 <a href="${portalURL}/autor?idAutor=${webContentData.classPK}"
355 class="insideLink">
356 ${webContentData.titleMap.es_ES}
357 </a>
358 </#if>
359
360 </#if>
361 </p>
362 </#if>
363
364 </div>
365 </div>
366 </#if>
367 </#if>
368 </#if>
369 </#if>
370 </#list>
371 </div>
372 </div>
373 </div>
374
375 </#if>
376
377</div>
378
379<#function getField field languageId defaultLanguageId xml>
380 <#local defaultSelector = "//dynamic-content[@language-id='" + defaultLanguageId + "' and ancestor-or-self::*[@field-reference='" + field + "']]">
381 <#local localeSelector = "//dynamic-content[@language-id='" + languageId + "' and parent::*[@field-reference='" + field + "']]">
382 <#local selector = saxReaderUtil.createXPath(localeSelector)>
383 <#local value = selector.selectSingleNode(xml)!>
384 <#if value?has_content><#return value.getText()></#if>
385 <#local selector = saxReaderUtil.createXPath(defaultSelector)>
386 <#local value = selector.selectSingleNode(xml)!>
387 <#if value?has_content><#return value.getText()></#if>
388 <#return "">
389</#function>
390
391<#function parseXml xpath xml>
392 <#local selector = saxReaderUtil.createXPath(xpath)>
393 <#local result = selector.selectSingleNode(xml)!>
394 <#if result?has_content><#return result.getStringValue()></#if>
395 <#return "">
396</#function>
397
398
399<#macro printMultimedia multimedia active>
400 <div class="carousel-item ${active?string('active','')}">
401 <#if multimedia.ImagenPost.getData()?? && multimedia.ImagenPost.getData() != "">
402 <img loading="lazy" alt="${multimedia.ImagenPost.getAttribute("alt")}"
403 src="${multimedia.ImagenPost.getData()}" />
404 <meta property='og:image' content='${multimedia.ImagenPost.getData()}'/>
405 <#elseif multimedia.VideoPost.getData()?? && multimedia.VideoPost.getData() != "">
406 <video src="${multimedia.VideoPost.getData()}"
407 controls="controls autoplay" />
408 <#else>
409 <img loading="lazy" class="mm-logo"
410 alt="Imagen por defecto"
411 src="${themeDisplay.companyLogo}" />
412 </#if>
413 </div>
414</#macro>
415
416<script type="text/javascript">
417 window.onload = function () {
418 var textoPost = document.getElementById('textoPost');
419 if (textoPost != null) {
420 if (textoPost.querySelector('.embed-responsive')) {
421 var divVideoEmbebido = document.getElementsByClassName('embed-responsive')[0];
422 const node = document.createElement('div');
423 node.classList.add('carousel-item');
424
425 divVideoEmbebido.style.width = '500px';
426
427 node.appendChild(divVideoEmbebido);
428 document.getElementsByClassName('carousel-inner')[0].appendChild(node);
429
430 }
431 }
432 };
433
434 jQuery('.insideLink').click(function (event) {
435 event.stopImmediatePropagation();
436 });
437</script>
438
439<script type="application/ld+json">
440 {
441 "@context" : "https://schema.org",
442 "@type" : "Article",
443 "headline" : "<#if (TitularPost.getData())??>${TitularPost.getData()}</#if>",
444 "author" : {
445 "@type" : "Organization",
446 "name" : "${metaTagNameAutor}",
447 "url" : "${metaTagUrlAutor}"
448 },
449 "datePublished" : "${publishDateIso8601}",
450 "image" : {
451 "@type" : "ImageObject",
452 "url" : "<#if (GrupoImagenVideo.ImagenPost.getData())?? && GrupoImagenVideo.ImagenPost.getData() != "">${GrupoImagenVideo.ImagenPost.getData()}</#if>"
453 }
454 }
455</script>