Seguridad

Esta página, auditada

Aquí no hay ni una cifra escrita a mano. Todas salen del lockfile, del package.json, de la política de pnpm, de los workflows o de git, en tiempo de build.

En el build

  • Commit12a0b11
  • Firmaválida
  • Build2026-10-16 17:54 UTC
  • Node24.20.0
  • pnpm11.26.0
  • Dependencias directas11
  • Total resueltas478
  • Versiones sin fijar0
  • Cuarentena7 días
  • Scripts permitidosesbuild, lefthook, sharp, workerd
  • Actions fijadas por SHA6/6

En tu navegador, ahora

  • Hashes CSP…
  • JS externo…
  • Cabeceras…

Las cabeceras las sirve Cloudflare desde public/_headers, así que en local no aparecen. Es lo esperado, no un fallo.

Scans de Prowler

Prowler audita las dos superficies desde las que vive esta página. Los resultados de abajo son reales y sin tocar, del último scan de cada una.

71%en verde, en total
  • Controles 51
  • En verde 36
  • En rojo 15
  • Superficies 2

GitHub

Audita la configuración de este mismo repositorio: protección de rama, permisos de los workflows, escaneo de secretos y avisos de dependencias.

72%controles en verde
  • En verde 13
  • En rojo 5
  • Objetivo danibarranqueroo/portfolio
  • Prowler v5.42.0
  • Fecha 2026-10-12

Lo que falla, y por qué sigue fallando

  • altaRepository default branch dismisses stale pull request approvals
    repository_default_branch_dismisses_stale_reviews

    riesgo asumidoDepends on a pull-request review workflow, which a solo repository does not run.

  • altaRepository default branch requires code owner approval for changes to owned code
    repository_default_branch_requires_codeowners_review

    riesgo asumidoCode owner review means reviewing your own code on a solo repository. CODEOWNERS exists so ownership is explicit, but enforcing self-review would be theatre.

  • altaRepository default branch requires status checks
    repository_default_branch_status_checks_required

    pendienteCI already runs lint, typecheck, build, audit, gitleaks and a SHA-pin check on every push. Making them a merge gate requires moving to a pull-request workflow.

  • mediaRepository default branch requires conversation resolution before merging
    repository_default_branch_requires_conversation_resolution

    riesgo asumidoDepends on a pull-request review workflow, which a solo repository does not run.

  • mediaRepository default branch requires at least 2 approvals for code changes
    repository_default_branch_requires_multiple_approvals

    riesgo asumidoRequires two approving reviews. This is a one-person repository, so a second approver does not exist. Stated rather than hidden.

Requieren comprobación a mano

  • manualRepository deletes branches after pull request merge
    repository_branch_delete_on_merge_enabled

Prowler marca así lo que no puede determinar por sí solo. Aquí es consecuencia de acotar el token de CI al mínimo: con menos permisos hay ajustes que no puede leer. Se listan igualmente, porque un check que no aparece en ninguna lista es un check escondido.

En verde

  • Repository default branch denies force pushes
  • Repository default branch protection applies to administrators
  • Repository enforces branch protection on the default branch
  • Repository default branch requires signed commits
  • Repository grants workflows a read-only default GITHUB_TOKEN
  • Repository has package vulnerability scanning (Dependabot alerts) enabled
  • Repository has immutable releases enabled
  • Repository has secret scanning enabled to detect sensitive data
  • Repository denies default branch deletion
  • Repository has a CODEOWNERS file
  • Repository is archived or active within the configured inactivity threshold
  • Repository default branch requires linear history
  • Public repository has a SECURITY.md file

Cloudflare

Audita la cuenta y la zona DNS desde la que se sirve esta página: TLS, HSTS, DNSSEC, registros de correo y reglas del WAF.

70%controles en verde
  • En verde 23
  • En rojo 10
  • Objetivo danibarranquero.com, www.danibarranquero.com
  • Prowler v5.42.0
  • Fecha 2026-10-12

Lo que falla, y por qué sigue fallando

  • altaDNS records pointing to hostnames have valid targets without takeover risk
    dns_record_cname_target_valid

    riesgo asumidoA false positive, and acting on it would make things worse. The flagged target is the null MX from RFC 7505: an MX record pointing at "." is the standard way to declare that a domain receives no mail at all. The check reads that "." as a dangling hostname and warns about mail interception, which is precisely what the null MX prevents. Removing the record to turn this green would reopen the risk it is warning about.

  • altaDNS records do not expose internal IP addresses
    dns_record_no_internal_ip

    riesgo asumidoA false positive, and worth stating plainly. The address is 100::, the IPv6 discard prefix from RFC 6666, which is what Cloudflare writes for a record that exists only to be proxied. It is not an internal address and it never leaves the account: externally the zone answers with Cloudflare anycast addresses, and a public AAAA lookup returns 2606:4700 addresses, never this one.

  • altaDNS records do not expose internal IP addresses
    dns_record_no_internal_ip

    riesgo asumidoA false positive, and worth stating plainly. The address is 100::, the IPv6 discard prefix from RFC 6666, which is what Cloudflare writes for a record that exists only to be proxied. It is not an internal address and it never leaves the account: externally the zone answers with Cloudflare anycast addresses, and a public AAAA lookup returns 2606:4700 addresses, never this one.

  • altaRate limiting is configured for the zone
    zone_rate_limiting_enabled

    riesgo asumidoAvailable on the free plan, which allows one rule, so this is a choice rather than a limit. Rate limiting protects an origin from being overwhelmed, and there is no origin: every response is a static asset served from Cloudflare edge cache on unmetered bandwidth. The only free action is a challenge, which would put an interstitial in front of real readers to defend against nothing.

  • altaWAF is enabled
    zone_waf_enabled

    bloqueadoThe Web Application Firewall is not available on the Cloudflare free plan. Prowler says so itself in the finding. The site is static files with no origin server, no database and no user input, so the attack classes a WAF blocks have nothing here to reach.

  • altaCloudflare Zone OWASP Managed WAF Rulesets Are Enabled
    zone_waf_owasp_ruleset_enabled

    bloqueadoThe OWASP Core Ruleset cannot be deployed on the free plan; only paid plans can. Same reasoning as the WAF check above.

  • mediaBot Fight Mode is enabled
    zone_bot_fight_mode_enabled

    riesgo asumidoMutually exclusive with the Content-Security-Policy on this site. Bot Fight Mode injects an inline challenge script whose r and t parameters change on every request, so no hash and no nonce can ever match it. Turning it on would mean adding unsafe-inline to script-src. Trading a real CSP for bot noise on a static site with no login and no forms is the wrong way round.

  • mediaCloudflare Zone Firewall Rules Use Blocking Actions to Protect Against Threats
    zone_firewall_blocking_rules_configured

    riesgo asumidoCustom firewall rules are available on the free plan. Nothing here is worth blocking: the entire site is public static content meant to be read, there is no authenticated surface, and no path that changes state. A blocking rule written only to satisfy a check would be configuration theatre.

  • mediaDKIM record exists with valid public key
    zone_record_dkim_exists

    riesgo asumidoThis domain sends no mail, so there is no key to publish. The record is *._domainkey with an empty p=, which RFC 6376 defines as a revoked key, and alongside SPF -all, DMARC p=reject and a null MX it is the recommended way to say "nothing here signs mail". The check looks for a valid public key and finds none, which is correct and also the point.

  • bajaHotlink Protection is enabled
    zone_hotlink_protection_enabled

    riesgo asumidoA bandwidth control rather than a security control, and static bandwidth on Workers is unmetered, so it protects nothing here. It also blocks other sites from loading images by referer, which is how link previews on social platforms fetch the portrait. Real cost, no benefit.

En verde

  • Always Online is disabled
  • DNSSEC is enabled
  • HSTS is enabled with recommended max-age and includes subdomains
  • Minimum TLS version is set to 1.2 or higher
  • SSL/TLS encryption mode is set to Full (Strict)
  • Universal SSL is enabled
  • DNS records do not use wildcard entries
  • DNS records do not use wildcard entries
  • DNS records do not use wildcard entries
  • Cloudflare proxy is enabled for applicable DNS records
  • Cloudflare proxy is enabled for applicable DNS records
  • Automatic HTTPS Rewrites is enabled
  • Always Use HTTPS is enabled
  • DMARC record exists with enforcement policy (p=reject or p=quarantine)
  • SPF record exists with strict policy (-all)
  • TLS 1.3 is enabled
  • Cloudflare Zone Browser Integrity Check Is Enabled
  • Cloudflare Zone Challenge Passage Is Configured Between 15 and 45 Minutes
  • Development mode is disabled for production zones
  • Email Obfuscation is enabled
  • IP Geolocation is enabled
  • CAA record exists with issue or issuewild tag
  • Under Attack Mode is disabled during normal operations

Nada de esto está escrito a mano: el JSON-OCSF de Prowler se normaliza en el build. Los fallos se muestran tal cual, con su motivo; esconderlos dejaría la página sin sentido.

Encuentra la mala configuración

Tres configuraciones reales. Haz clic en la línea peligrosa de cada una.0/3

Política de bucket S3

Política IAM

Grupo de seguridad