🚀 Cómo hacer deploy de CloudPages desde GitHub sin complicarte la vida (ni romper producción)

Ágil para probar. Limpio para publicar.


📝 El escenario

Estás construyendo una CloudPage compleja en Salesforce Marketing Cloud (SFMC). Quieres:

  • Mantener tu código versionado
  • Colaborar con otros developers
  • Dejar de copiar y pegar como si fuera 2007

Y claro: hacerlo sin romper nada en producción.

🧪 Todos los snippets de este post (y muchos más que iremos publicando) están disponibles en nuestro repositorio para la comunidarks:
🔗 https://github.com/jcgalindof/salesforce-cancun


🎯 La solución: cargar el código desde GitHub con SSJS

Usando un snippet como este (basado en un ejemplo de StackExchange):

<script runat="server">
  Platform.Load('Core', '1.1')

  // Variables globales
  // Cambia estas variables de acuerdo a tu configuración
  var userDetails = {
           username : "salesforcecancun",
           token    : "c0b6a550b1aaaca1292e11cbe786e56d40b98c49",
           repoName : "salesforce-cancun",
           fileName : "cloudpage.amp"
        }

  // No modificar nada debajo de esta sección
  // Función para obtener el contenido del repo privado
  function getPrivateRepoContent(obj){
      var resource = 'https://api.github.com/repos/'+ obj.username + '/' + obj.repoName + '/contents/' + obj.fileName
      var req = new Script.Util.HttpRequest(resource);
          req.emptyContentHandling = 0;
          req.retries = 2;
          req.continueOnError = true;
          req.contentType = "application/json; charset=utf-8"
          req.setHeader("Authorization","token " + obj.token);
          req.setHeader("User-Agent", obj.username + '/' + obj.repoName);
          // Este header es muy importante: permite obtener la versión RAW del archivo
          req.setHeader("Accept", "application/vnd.github.v3.raw");
          req.setHeader("Cache-Control", "");
          req.method = "GET";
      var resp = req.send();
      // Asignamos el contenido recibido a una variable de AMPscript
      Platform.Variable.SetValue("@runCode", resp.content)
  }

  // Ejecutamos la función usando la configuración
  getPrivateRepoContent(userDetails)
</script>
%%=TreatAsContent(@runCode)=%%

Este código:

  • Conecta con un repositorio privado en GitHub.
  • Descarga el archivo deseado (HTML, JS, AMPscript… lo que sea).
  • Lo ejecuta directamente en la CloudPage gracias a TreatAsContent().

🚫 Por qué no deberías usar esto en producción

Aunque tentador, este enfoque tiene riesgos críticos si se usa sin cuidado:

❌ Token hardcodeado

  • Está visible en el código.
  • Puede ser explotado si alguien accede a la CloudPage o el entorno de edición.

⚡ TreatAsContent ejecuta TODO

  • Si el archivo remoto está comprometido, el servidor ejecuta código sin control.

⌛ Dependencia de GitHub

  • Si GitHub está caído o tu token expira, la página se rompe.

👩‍💻 Nuestra recomendación: entornos de prueba sí, producción no

Este método es altamente útil para desarrollo y QA:

  • Puedes iterar rápido sin tocar el builder.
  • Puedes versionar y trabajar en ramas.
  • Puedes integrar snippets y layouts desde repos compartidos.

Y cuando todo está listo…

✅ Copias el contenido verificado desde GitHub y lo pegas limpio en la CloudPage de producción.


🛡️ Tips de seguridad

  • Usa tokens con acceso limitado.
  • Rota el token cada 30 días (o menos).
  • Usa un entorno de prueba que no reciba tráfico de usuarios reales.
  • Nunca expongas el token en un entorno accesible por terceros.

🏆 Conclusión

Esta técnica es poderosa, pero no está diseñada para vivir en producción.

Usála como herramienta de iteración rápida, no como estructura de despliegue final.

Y recuerda:

Ágil para probar. Limpio para publicar.

Leave a Comment

Your email address will not be published. Required fields are marked *

Scroll to Top