Files
cv-site/templates/cv-content.html
T
juanatsap e572af0771 feat: implement dynamic date calculation for projects
- Remove hardcoded startDate from La Porra project
- Add gitRepoUrl field to Project struct for dynamic date fetching
- Implement backend logic to fetch first commit date from git repositories
- Add processProjectDates function to calculate dates dynamically
- Update template to display computed dates and dynamic "Present/Presente"
- Add support for both static and git-based project start dates

When a project has a gitRepoUrl, the system automatically fetches the first
commit date from the repository. For current projects, it displays
"Present" (English) or "Presente" (Spanish) dynamically from the backend.

The La Porra project now uses git repository path for date calculation
instead of hardcoded JSON values.
2025-11-09 02:43:40 +00:00

414 lines
21 KiB
HTML

<!-- PAGE 1 -->
<div class="cv-page page-1">
<!-- Professional Title Badges - Full Width Top Bar -->
<div class="cv-title-badges-header">
<span class="title-badge">{{if eq .Lang "es"}}ANALISTA{{else}}ANALYST{{end}}</span>
<span class="badge-separator">|</span>
<span class="title-badge">{{if eq .Lang "es"}}CONSULTOR TÉCNICO{{else}}TECHNICAL CONSULTANT{{end}}</span>
<span class="badge-separator">|</span>
<span class="title-badge">NODEJS + REACTJS {{if eq .Lang "es"}}DESARROLLADOR{{else}}DEVELOPER{{end}}</span>
<span class="badge-separator">|</span>
<span class="title-badge">WEB {{if eq .Lang "es"}}DESARROLLADOR{{else}}DEVELOPER{{end}}</span>
<span class="badge-separator">|</span>
<span class="title-badge">GO + HTMX {{if eq .Lang "es"}}DESARROLLADOR{{else}}DEVELOPER{{end}}</span>
<span class="badge-separator">|</span>
<span class="title-badge">PHP {{if eq .Lang "es"}}DESARROLLADOR{{else}}DEVELOPER{{end}}</span>
</div>
<!-- Page 1 Content Grid: Left Sidebar + Main Content -->
<div class="page-content">
<!-- Left Sidebar - Skills (first half) -->
<aside class="cv-sidebar cv-sidebar-left">
{{range $index, $category := .SkillsLeft}}
<section class="sidebar-section">
<h3 class="sidebar-title">{{$category.Category}}</h3>
<div class="sidebar-content">
{{range $category.Items}}<div class="skill-item">{{.}}</div>{{end}}
</div>
</section>
{{end}}
</aside>
<!-- Main Content Area - Page 1 -->
<main class="cv-main">
<!-- Header with Name and Photo -->
<div class="cv-header">
<div class="cv-header-content">
<div class="cv-header-left">
<h1 class="cv-name">Moreno Rubio, Juan Andrés</h1>
<p class="years-experience">{{.YearsOfExperience}} {{if eq .Lang "es"}}años de experiencia{{else}}years of experience{{end}}</p>
<!-- Intro/Excerpt Text - No section heading, just the text -->
<div class="intro-text">{{.CV.Summary}}</div>
</div>
<div class="cv-photo">
<img src="/static/images/profile/dni.jpeg" alt="{{.CV.Personal.Name}}" onerror="this.src='/static/images/profile/placeholder.svg'">
</div>
</div>
</div>
<!-- Education -->
<section id="education" class="cv-section">
<h3 class="section-title">
<iconify-icon icon="mdi:school" width="24" height="24" class="section-icon"></iconify-icon>
{{if eq .Lang "es"}}Formación{{else}}Training{{end}}
</h3>
{{range .CV.Education}}
<div class="education-item">
<strong>{{.Degree}}</strong> ({{.StartDate}}-{{.EndDate}}) {{if eq $.Lang "es"}}obtenido de{{else}}obtained from the{{end}} <strong>{{.Institution}}</strong> ({{.Location}})
</div>
{{end}}
</section>
<!-- Skills Summary -->
<section id="skills" class="cv-section">
<h3 class="section-title">
<iconify-icon icon="mdi:brain" width="24" height="24" class="section-icon"></iconify-icon>
{{if eq .Lang "es"}}Competencias{{else}}Skills{{end}}
</h3>
<p class="summary-text">
{{if eq .Lang "es"}}
Amplio conocimiento en entornos web, tanto J2EE como PHP. Experto en tecnologías front-end, aunque con considerable experiencia en sistemas back-end. Receptivo al aprendizaje de nuevas tecnologías, y con una gran dosis de creatividad. Capacidad de analizar problemas y aportar soluciones específicas adaptadas a cada tipo de cliente. Me gusta trabajar tanto solo como en grupos.
{{else}}
Extensive knowledge in web environments, both J2EE and PHP. Expert in front-end technologies, although with considerable experience in back-end systems. Receptive to learning new technologies, and with a large dose of creativity. Ability to analyze problems and provide specific solutions tailored to each client type. I like to work both alone and in groups.
{{end}}
</p>
</section>
<!-- Experience -->
<section id="experience" class="cv-section">
<h3 class="section-title">
<iconify-icon icon="mdi:office-building" width="24" height="24" class="section-icon"></iconify-icon>
{{if eq .Lang "es"}}Experiencia{{else}}Experience{{end}}
</h3>
{{range .CV.Experience}}
<div class="experience-item">
<div class="company-logo">
{{if .CompanyLogo}}
<img src="/static/images/companies/{{.CompanyLogo}}" alt="{{.Company}} logo" onerror="this.parentElement.innerHTML='<iconify-icon icon=\'mdi:office-building\' width=\'60\' height=\'60\' class=\'default-company-icon\'></iconify-icon>'">
{{else}}
<iconify-icon icon="mdi:office-building" width="60" height="60" class="default-company-icon"></iconify-icon>
{{end}}
</div>
<div class="experience-content">
<div class="experience-header">
<div class="experience-title-line">
<h4 class="position">
<span class="position-title">{{.Position}}</span>
{{if .Company}}
{{if .CompanyURL}}
<a href="{{.CompanyURL}}" target="_blank" rel="noopener noreferrer" class="company-link">{{.Company}}</a>
{{else}}
<span class="company-name">{{.Company}}</span>
{{end}}
{{end}}
{{if .Current}}
<span class="current-badge">{{if eq $.Lang "es"}}ACTUAL{{else}}CURRENT{{end}}</span>
{{end}}
{{if .Expired}}
<span class="expired-badge">{{if eq $.Lang "es"}}EXPIRADO{{else}}EXPIRED{{end}}</span>
{{end}}
</h4>
<span class="experience-period">{{.StartDate}} / {{if .Current}}{{if eq $.Lang "es"}}presente{{else}}now{{end}}{{else}}{{.EndDate}}{{end}}</span>
{{if .Duration}}
<span class="experience-separator">&nbsp;-&nbsp;</span>
<span class="experience-duration">{{.Duration}}</span>
{{end}}
<span class="experience-separator">&nbsp;-&nbsp;</span>
<span class="experience-location">({{.Location}})</span>
</div>
</div>
{{if .ShortDescription}}
<p class="short-desc">{{.ShortDescription | safeHTML}}</p>
{{end}}
<div class="long-only">
<ul class="responsibilities">
{{range .Responsibilities}}
<li>{{. | safeHTML}}</li>
{{end}}
</ul>
</div>
</div>
</div>
{{end}}
</section>
</main>
</div>
</div>
<!-- PAGE 2 -->
<div class="cv-page page-2">
<!-- Professional Title Badges - Same as Page 1 -->
<div class="cv-title-badges-header">
<span class="title-badge">{{if eq .Lang "es"}}ANALISTA PROGRAMADOR{{else}}ANALYST PROGRAMMER{{end}}</span>
<span class="badge-separator">|</span>
<span class="title-badge">NODEJS + REACTJS {{if eq .Lang "es"}}DESARROLLADOR{{else}}DEVELOPER{{end}}</span>
<span class="badge-separator">|</span>
<span class="title-badge">WEB {{if eq .Lang "es"}}DESARROLLADOR{{else}}DEVELOPER{{end}}</span>
<span class="badge-separator">|</span>
<span class="title-badge">GO + HTMX {{if eq .Lang "es"}}DESARROLLADOR{{else}}DEVELOPER{{end}}</span>
<span class="badge-separator">|</span>
<span class="title-badge">PHP {{if eq .Lang "es"}}DESARROLLADOR{{else}}DEVELOPER{{end}}</span>
</div>
<!-- Page 2 Content Grid: Main Content + Right Sidebar -->
<div class="page-content">
<!-- Main Content Area - Page 2 -->
<main class="cv-main">
<!-- Awards Section -->
{{if .CV.Awards}}
<section id="awards" class="cv-section">
<h3 class="section-title">
<iconify-icon icon="mdi:trophy" width="24" height="24" class="section-icon"></iconify-icon>
{{if eq .Lang "es"}}Premios y Reconocimientos{{else}}Awards{{end}}
</h3>
{{range .CV.Awards}}
<div class="award-item">
{{if .AwardLogo}}
<div class="award-logo">
<img src="/static/images/companies/{{.AwardLogo}}" alt="{{.Title}} logo" onerror="this.parentElement.innerHTML='<iconify-icon icon=\'mdi:trophy\' width=\'60\' height=\'60\' class=\'default-award-icon\'></iconify-icon>'">
</div>
{{end}}
<div class="award-content">
<strong>{{.Title}}</strong><br>
<small>{{.Issuer}} - {{.Date}}</small>
{{if .ShortDescription}}
<p class="award-desc short-desc">{{.ShortDescription | safeHTML}}</p>
{{end}}
{{if .Responsibilities}}
<ul class="responsibilities long-only">
{{range .Responsibilities}}
<li>{{. | safeHTML}}</li>
{{end}}
</ul>
{{end}}
</div>
</div>
{{end}}
</section>
{{end}}
<!-- Projects Section -->
{{if .CV.Projects}}
<section id="projects" class="cv-section">
<h3 class="section-title">
<iconify-icon icon="mdi:web" width="24" height="24" class="section-icon"></iconify-icon>
{{if eq .Lang "es"}}Proyectos Personales / Freelance{{else}}Personal / Freelance Projects{{end}}
</h3>
{{range .CV.Projects}}
<div class="project-item">
{{if .ProjectLogo}}
<div class="project-icon">
<img src="/static/images/projects/{{.ProjectLogo}}" alt="{{.Title}} logo" onerror="this.parentElement.innerHTML='<iconify-icon icon=\'mdi:web\' width=\'80\' height=\'80\' class=\'default-project-icon\'></iconify-icon>'">
</div>
{{else}}
<div class="project-icon">
<iconify-icon icon="mdi:web" width="80" height="80" class="default-project-icon"></iconify-icon>
</div>
{{end}}
<div class="project-content">
<div class="project-header">
<h4 class="project-title">
<span class="project-title-text">
{{if .URL}}
<a href="{{.URL}}" target="_blank" rel="noopener noreferrer">{{.Title}}</a>
{{else}}
{{.Title}}
{{end}}
</span>
{{if .Current}}
<span class="current-badge">{{if eq $.Lang "es"}}ACTUAL{{else}}CURRENT{{end}}</span>
{{end}}
{{if .MaintainedBy}}
<span class="maintained-badge">{{if eq $.Lang "es"}}MANTENIDO POR{{else}}MAINTAINED BY{{end}} {{.MaintainedBy}}</span>
{{end}}
</h4>
<span class="project-period">
{{if .StartDate}}{{.StartDate}}{{end}}
{{if .Current}}
{{if .DynamicDate}}
/ {{.DynamicDate}}
{{else}}
/ {{if eq $.Lang "es"}}presente{{else}}now{{end}}
{{end}}
{{end}}
</span>
<span class="project-separator">&nbsp;-&nbsp;</span>
<span class="project-location">({{.Location}})</span>
</div>
{{if .ShortDescription}}
<p class="project-desc short-desc">{{.ShortDescription | safeHTML}}</p>
{{end}}
{{if .Responsibilities}}
<ul class="responsibilities long-only">
{{range .Responsibilities}}
<li>{{. | safeHTML}}</li>
{{end}}
</ul>
{{end}}
{{if .Technologies}}
<div class="project-technologies long-only">
<strong>{{if eq $.Lang "es"}}Tecnologías:{{else}}Technologies:{{end}}</strong>
{{range $index, $tech := .Technologies}}{{if $index}}, {{end}}{{$tech}}{{end}}
</div>
{{end}}
</div>
</div>
{{end}}
<!-- Link to full portfolio -->
<div class="projects-footer">
<p>{{if eq .Lang "es"}}Ver todos los proyectos en mi{{else}}See all projects on my{{end}}
<a href="{{.CV.Personal.Domestika}}" target="_blank" rel="noopener noreferrer"><strong>{{if eq .Lang "es"}}portfolio de Domestika{{else}}Domestika portfolio{{end}}</strong></a></p>
</div>
</section>
{{end}}
<!-- Courses Section -->
{{if .CV.Courses}}
<section id="courses" class="cv-section">
<h3 class="section-title">
<iconify-icon icon="mdi:school" width="24" height="24" class="section-icon"></iconify-icon>
{{if eq .Lang "es"}}Cursos Realizados{{else}}Courses{{end}}
</h3>
{{range .CV.Courses}}
<div class="course-item">
<div class="course-icon">
<iconify-icon icon="mdi:school" width="80" height="80" class="default-course-icon"></iconify-icon>
</div>
<div class="course-content">
<div class="course-header">
<h4 class="course-title">
<span class="course-title-text">{{.Title}}</span>
<span class="course-institution">{{.Institution}}</span>
</h4>
<span class="course-period">{{.Date}}</span>
{{if .Duration}}
<span class="course-separator">&nbsp;-&nbsp;</span>
<span class="course-duration">{{.Duration}}</span>
{{end}}
<span class="course-separator">&nbsp;-&nbsp;</span>
<span class="course-location">({{.Location}})</span>
</div>
{{if .ShortDescription}}
<p class="course-desc short-desc">{{.ShortDescription | safeHTML}}</p>
{{end}}
{{if .Responsibilities}}
<ul class="responsibilities long-only">
{{range .Responsibilities}}
<li>{{. | safeHTML}}</li>
{{end}}
</ul>
{{end}}
</div>
</div>
{{end}}
</section>
{{end}}
<!-- Languages Section -->
<section id="languages" class="cv-section">
<h3 class="section-title">
<iconify-icon icon="mdi:translate" width="24" height="24" class="section-icon"></iconify-icon>
{{if eq .Lang "es"}}Idiomas{{else}}Languages{{end}}
</h3>
{{range .CV.Languages}}
<div class="language-item">
<strong>{{.Language}}:</strong> {{.Proficiency}}{{if .Detail}} {{.Detail}}{{end}}
</div>
{{end}}
</section>
<!-- References Section -->
{{if .CV.References}}
<section id="references" class="cv-section">
<h3 class="section-title">
<iconify-icon icon="mdi:link-variant" width="24" height="24" class="section-icon"></iconify-icon>
{{if eq .Lang "es"}}Referencias{{else}}References{{end}}
</h3>
{{range .CV.References}}
<div class="reference-item">
{{if .TextBefore}}{{.TextBefore}} {{end}}<a href="{{.URL}}" target="_blank" rel="noopener noreferrer"><strong>{{if .LinkText}}{{.LinkText}}{{else}}{{.Title}}{{end}}</strong></a>{{if .TextAfter}} {{.TextAfter}}{{end}}
</div>
{{end}}
</section>
{{end}}
<!-- Other Section (Driver's License) -->
{{if .CV.Other.DriverLicense}}
<section id="other" class="cv-section">
<h3 class="section-title">
<iconify-icon icon="mdi:information" width="24" height="24" class="section-icon"></iconify-icon>
{{if eq .Lang "es"}}Otros{{else}}Other{{end}}
</h3>
<div class="other-content">
{{if eq .Lang "es"}}Carnet de conducir tipo {{.CV.Other.DriverLicense}}{{else}}Driving License type {{.CV.Other.DriverLicense}}{{end}}
</div>
</section>
{{end}}
</main>
<!-- Right Sidebar - Skills (second half) -->
<aside class="cv-sidebar cv-sidebar-right">
{{range $index, $category := .SkillsRight}}
<section class="sidebar-section">
<h3 class="sidebar-title">{{$category.Category}}</h3>
<div class="sidebar-content">
{{range $category.Items}}<div class="skill-item">{{.}}</div>{{end}}
</div>
</section>
{{end}}
</aside>
</div>
<!-- Footer - Only on Page 2 -->
<footer class="cv-footer">
<ul class="footer-content">
<li>
<div class="footer-label">linkedin_</div>
<div class="footer-separator"><i class="fa fa-circle"></i></div>
<div class="footer-value">
<a href="{{.CV.Personal.LinkedIn}}" target="_blank" rel="noopener noreferrer">{{.CV.Personal.LinkedIn}}</a>
</div>
</li>
<li>
<div class="footer-label">github_</div>
<div class="footer-separator"><i class="fa fa-circle"></i></div>
<div class="footer-value">
<a href="{{.CV.Personal.GitHub}}" target="_blank" rel="noopener noreferrer">{{.CV.Personal.GitHub}}</a>
</div>
</li>
<li>
<div class="footer-label">domestika_</div>
<div class="footer-separator"><i class="fa fa-circle"></i></div>
<div class="footer-value">
<a href="{{.CV.Personal.Domestika}}" target="_blank" rel="noopener noreferrer">{{.CV.Personal.Domestika}}</a>
</div>
</li>
<li>
<div class="footer-label">email@</div>
<div class="footer-separator"><i class="fa fa-circle"></i></div>
<div class="footer-value">
<a href="mailto:{{.CV.Personal.Email}}" target="_blank" rel="noopener noreferrer">{{.CV.Personal.Email}}</a>
</div>
</li>
<li>
<div class="footer-label">phone#</div>
<div class="footer-separator"><i class="fa fa-circle"></i></div>
<div class="footer-value">
<a href="tel:+34676875420" target="_blank" rel="noopener noreferrer">+34 676 875 420</a>
</div>
</li>
</ul>
</footer>
</div>