# Java -------------------------------------------------------------------------------- title: "Introducción" description: "Construye una aplicación Lead Manager y alójala en AppSail. La aplicación se conecta a tu cuenta de Zoho CRM usando conectores de Catalyst, y te permite ver, crear, actualizar o eliminar leads desde el módulo de Leads en tu CRM." last_updated: "2026-10-08T06:48:03.650Z" source: "https://docs.catalyst.zoho.com/es/tutorials/leadmanager-appsail/springboot/introduction/" service: "All Services" related: - Project Directory Structure (/es/cli/v1/project-directory-structure/introduction/) - Catalyst SDK for AppSail (/es/serverless/help/appsail/key-concepts/catalyst-configurations/#implementing-catalyst-sdk-in-appsail/) -------------------------------------------------------------------------------- # Aplicación Lead Manager usando AppSail ### Introducción Este tutorial te ayudará a construir una aplicación web **Java Spring Boot** llamada **Lead Manager**. Esta aplicación web te permitirá conectarte con tu cuenta de Zoho CRM y te permitirá gestionar leads en tu organización. Podrás acceder, agregar, editar o eliminar leads en el módulo de Leads en tu cuenta de CRM directamente desde esta aplicación. La conexión a Zoho CRM se establece usando el protocolo de autenticación OAuth 2.0. Generaremos un OAuth Access Token para la aplicación *Lead Manager* y lo usaremos para autorizar la conexión para acceder a los datos del CRM. El requisito de autenticación en este tutorial se maneja usando Embedded Authentication. También implementaremos un Catalyst Connector para gestionar este acceso a la cuenta de CRM. El conector renovará el Access Token automáticamente cada vez que expire usando un Refresh Token, y mantendrá una conexión constante entre el cliente y la cuenta de CRM. Estos tokens se pueden generar después de registrar la aplicación cliente en la consola de API de Zoho y obtener las credenciales requeridas. La aplicación cliente se verá así: <br /> La aplicación Lead Manager emplea componentes de los siguientes servicios de Catalyst: - **Catalyst Serverless**: - AppSail: Para alojar la aplicación independiente *Java Spring Boot*. Construiremos el front-end de la aplicación así como la lógica del back-end, y los empaquetaremos juntos para desplegarlos en AppSail. - **Catalyst CloudScale**: - Data Store: Para almacenar el Refresh Token y el UserID del usuario de Catalyst obtenido por el recurso de función. El Refresh Token es obtenido de esta tabla por la función, cada vez que se necesita generar un nuevo Access Token. - ZCQL: Para obtener datos del *Data Store* mediante consultas. - Catalyst Authentication: Para implementar un inicio de sesión social de Zoho en la página de inicio de sesión de la aplicación cliente, además de la opción de inicio de sesión estándar, implementaremos el tipo Embedded Authentication en este tutorial. Usaremos la consola web de Catalyst y la Interfaz de Línea de Comandos (CLI) de Catalyst para construir esta aplicación. Info: Se te proporcionará el código para los archivos que se incluirán en los componentes de función y cliente en este tutorial. Solo necesitarás copiar el código proporcionado y pegarlo en los archivos apropiados según las instrucciones. ### Arquitectura de la aplicación La arquitectura de la aplicación Lead Manager se muestra a continuación: <br /> El flujo de trabajo completo de la aplicación se explicará con más detalle cuando codifiques la lógica de tu front end, lo cual te recomendamos revisar mientras sigues los pasos. -------------------------------------------------------------------------------- title: "Requisitos previos" description: "Construye una aplicación Lead Manager y alójala en AppSail. La aplicación se conecta a tu cuenta de Zoho CRM usando conectores de Catalyst, y te permite ver, crear, actualizar o eliminar leads desde el módulo de Leads en tu CRM." last_updated: "2026-10-08T06:48:03.651Z" source: "https://docs.catalyst.zoho.com/es/tutorials/leadmanager-appsail/springboot/prerequisites/" service: "All Services" related: - Catalyst Tools VS Code Plugin (/es/catalyst-extensions/vs-code-extension/introduction/) -------------------------------------------------------------------------------- # Requisitos previos Antes de comenzar a construir la aplicación, debes tener los siguientes requisitos previos instalados en tu sistema: 1. **Catalyst CLI**: Catalyst CLI contiene un conjunto de herramientas que te permiten inicializar, desarrollar, probar y desplegar los componentes de tu aplicación desde tu máquina local. Trabajaremos con Catalyst CLI en este tutorial. Debes realizar estas acciones: - Instalar Catalyst CLI: Catalyst CLI se instala a través de NPM. Por lo tanto, debes tener NPM y Node.js instalados en tu sistema antes de instalar la CLI. Consulta la página de ayuda para instalar Catalyst CLI para obtener detalles sobre los requisitos previos y los pasos para instalarlo. - Iniciar sesión en Catalyst CLI: Después de instalar Catalyst CLI, debes autenticar la CLI con tu cuenta de Catalyst antes de usarla. Consulta la página de ayuda de inicio de sesión en CLI para conocer los pasos para iniciar sesión desde Catalyst CLI y las diversas opciones disponibles. 2. **Cuenta de Zoho CRM**: Dado que el módulo de Leads está disponible en todas las ediciones de Zoho CRM, puedes tener una cuenta de Zoho CRM configurada de cualquier edición para establecer una conexión con la aplicación Lead Manager. Si no tienes una cuenta de Zoho CRM, puedes registrarte aquí. 3. **Instalar la herramienta de automatización de compilación Apache Maven**: Para completar este tutorial, necesitas instalar Maven en tu sistema local. Instala la versión compatible para tu sistema usando este enlace. 4. **Cualquier herramienta IDE para desarrollo de código Java y cliente** Puedes usar cualquier IDE para trabajar con la función y el código del cliente. Algunas opciones populares incluyen Visual Studio Code, IntelliJ IDEA, Eclipse y Sublime Text. Descarga e instala un IDE de tu elección en tu sistema. Si eres usuario del IDE Visual Studio Code, puedes instalar la extensión Catalyst Tools, y usar tu propio IDE en lugar de la CLI. Puedes encontrar más detalles sobre la extensión de Catalyst para VS Code en esta sección de ayuda. -------------------------------------------------------------------------------- title: "Crear un proyecto" description: "Construye una aplicación Lead Manager y alójala en AppSail. La aplicación se conecta a tu cuenta de Zoho CRM usando conectores de Catalyst, y te permite ver, crear, actualizar o eliminar leads desde el módulo de Leads en tu CRM." last_updated: "2026-10-08T06:48:03.651Z" source: "https://docs.catalyst.zoho.com/es/tutorials/leadmanager-appsail/springboot/create-project/" service: "All Services" related: - Project Directory Structure (/es/cli/v1/project-directory-structure/introduction/) - Catalyst SDK for AppSail (/es/serverless/help/appsail/key-concepts/catalyst-configurations/#implementing-catalyst-sdk-in-appsail/) -------------------------------------------------------------------------------- # Crear un proyecto Vamos a crear un proyecto de Catalyst desde la consola de Catalyst. 1. Inicia sesión en la consola de Catalyst y haz clic en **Create New Project**. <br /> 2. Ingresa el nombre del proyecto como "**LeadManager**" en la ventana emergente. <br /> Tu proyecto será creado. Puedes abrir el proyecto haciendo clic en **Access Project**. <br /> -------------------------------------------------------------------------------- title: "Crear una tabla" description: "Construye una aplicación Lead Manager y alójala en AppSail. La aplicación se conecta a tu cuenta de Zoho CRM usando conectores de Catalyst, y te permite ver, crear, actualizar o eliminar leads desde el módulo de Leads en tu CRM." last_updated: "2026-10-08T06:48:03.651Z" source: "https://docs.catalyst.zoho.com/es/tutorials/leadmanager-appsail/springboot/create-table/" service: "All Services" related: - Data Store (/es/cloud-scale/help/data-store/introduction/) - ZCQL (/es/cloud-scale/help/zcql/introduction) -------------------------------------------------------------------------------- # Crear una tabla A continuación, vamos a crear una tabla en el **Data Store**. Esta tabla se utiliza para almacenar los valores del *Refresh Token* y userID, que se recuperan cada vez que se necesita generar un *Access Token*. Para crear una tabla: 1. Navega a la sección del servicio Catalyst Cloud Scale en la consola y haz clic en **Start Exploring**. <br /> 2. Haz clic en **Create a new Table**. <br /> 3. Ingresa el nombre de la tabla como "Token" y haz clic en **Create**. <br /> Nota: Asegúrate de ingresar el nombre exactamente como se indica porque el código de la aplicación contiene el mismo nombre. La tabla será creada. <br /> Ahora, vamos a crear dos columnas en la tabla para almacenar el userID y el refresh token respectivamente. Info: Puedes conocer los diversos tipos de datos soportados por Catalyst y las otras propiedades de una columna en la documentación de ayuda de Data Store. 4. Haz clic en **New Column** en la sección *Schema View*. <br /> 5. Ingresa el nombre de la columna como "refresh_token". Selecciona el tipo de dato como Encrypted Text. <br /> 6. Haz clic en **Create**. <br /> 7. Ahora haz clic en el botón **New Column** nuevamente para crear la segunda columna. Nómbrala "userId", y selecciona **BigInt** como su tipo de dato. <br /> 8. Haz clic en **Create**. <br /> Las columnas requeridas han sido creadas. ### Configurar alcances y permisos Para permitir que cualquier usuario de la aplicación Lead Manager vea o gestione leads desde la aplicación cliente, debes habilitar un permiso de tabla adicional que permitirá al usuario obtener y almacenar nuevos *Refresh Tokens*, si es necesario. Para habilitar los permisos requeridos: 1. Haz clic en la pestaña **Scopes and Permissions**. <br /> 2. Habilita el permiso **Insert** para el rol **App User** en la sección *Table Permissions*. Asegúrate de no cambiar ninguna otra configuración de permisos. <br /> El componente Data Store está ahora configurado para la aplicación. -------------------------------------------------------------------------------- title: "Habilitar inicio de sesión social de Zoho" description: "Construye una aplicación Lead Manager y alójala en AppSail. La aplicación se conecta a tu cuenta de Zoho CRM usando conectores de Catalyst, y te permite ver, crear, actualizar o eliminar leads desde el módulo de Leads en tu CRM." last_updated: "2026-10-08T06:48:03.652Z" source: "https://docs.catalyst.zoho.com/es/tutorials/leadmanager-appsail/springboot/enable-auth/" service: "All Services" related: - Authentication (/es/cloud-scale/help/authentication/introduction/) - Embedded Authentication (/es/cloud-scale/help/authentication/native-catalyst-authentication/embedded-authentication/introduction/) - Enable Social Login (/es/cloud-scale/help/authentication/social-logins/configuring-social-logins/) - Public Sign Up (/es/cloud-scale/help/authentication/public-signup/) -------------------------------------------------------------------------------- # Habilitar inicio de sesión social de Zoho usando Embedded Authentication La aplicación Lead Manager contiene una página de inicio de sesión donde debes proporcionar credenciales válidas para acceder a tu cuenta de Zoho CRM. Necesitas implementar una funcionalidad de registro para esta aplicación. La funcionalidad también debe proporcionar la opción de iniciar sesión en la cuenta usando inicios de sesión sociales de Zoho. Implementaremos el tipo Embedded Authentication para completar este requisito. Para configurar el inicio de sesión social de Zoho para la aplicación Lead Manager desde la consola: 1. Navega al componente **Authentication** en la sección *Security & Identity*, y haz clic en **Setup** en la pestaña **Native Catalyst Authentication**. <br /> 2. Selecciona **Embedded Authentication**, y haz clic en **Next**. <br /> 3. Puedes copiar y usar los scripts proporcionados en el paso de **Configuration** para configurar tu funcionalidad de inicio de sesión. Sin embargo, como solo vamos a usar el *inicio de sesión social de Zoho*, necesitas habilitar primero el **toggle de Public Signup**. <br /> 4. Haz clic en **Yes, Proceed** en el cuadro de diálogo después de revisarlo. <br /> 5. Haz clic en el botón **Zoho** para habilitar el inicio de sesión social. <br /> 6. Proporciona "LeadManagerApp" como el *Client Name* y haz clic en **Enable**. <br /> 7. Haz clic en **Next**. <br /> 8. No configuraremos ninguna configuración de autenticación adicional para nuestra aplicación. Haz clic en **Finish**. <br /> **Embedded Authentication** ha sido habilitado para la aplicación, y los usuarios ahora pueden iniciar sesión en la aplicación usando el **inicio de sesión social de Zoho**. <br /> -------------------------------------------------------------------------------- title: "Generar un proyecto SpringBoot" description: "Construye una aplicación Lead Manager y alójala en AppSail. La aplicación se conecta a tu cuenta de Zoho CRM usando conectores de Catalyst, y te permite ver, crear, actualizar o eliminar leads desde el módulo de Leads en tu CRM." last_updated: "2026-10-08T06:48:03.652Z" source: "https://docs.catalyst.zoho.com/es/tutorials/leadmanager-appsail/springboot/generate-springboot/" service: "All Services" related: - AppSail Help (/es/serverless/help/appsail/introduction/) - AppSail Guide for Spring Boot Apps (/es/serverless/help/appsail/help-guides/java/spring-boot/) -------------------------------------------------------------------------------- # Generar un proyecto SpringBoot Para este tutorial, vamos a crear un proyecto **Spring Boot - JAR** usando el sitio web **Spring Initializr**. 1. Ve al sitio web de Spring Initializr. <br /> 2. Elige o ingresa los detalles requeridos de la siguiente manera: - Selecciona **Maven** como *Project*, **Java** como *Language*, y la versión más reciente de *Spring Boot*. - Ingresa "**com.catalyst.appsail**" como el *Group*, "**leadmanager**" como el *Artifact*, y proporciona una descripción adecuada. Los campos *Name* y *Package name* se completarán automáticamente. - Selecciona **Jar** como el *Packaging*, y **17** como la versión de *Java*. <br /> 3. Haz clic en el botón **ADD DEPENDENCIES**, en el lado derecho de la pantalla, y selecciona **Spring Web** en el menú desplegable y selecciona la dependencia. Este paso instalará todas las dependencias necesarias requeridas para construir una aplicación web Spring Boot cuando generes el paquete. <br /> 4. Confirma todas tus selecciones, y haz clic en **Generate**. <br /> El proyecto Spring Boot **leadmanager** se descargará en tu sistema local como un archivo zip. Descomprime el archivo descargado y este directorio, leadmanager/ será nuestro directorio local donde inicializaremos el servicio Catalyst AppSail para nuestro proyecto. Junto con todas las dependencias requeridas, también contendrá el archivo LeadManagerApplication.java. Este archivo contendrá la lógica que te permite ejecutar la aplicación en Spring Boot. El directorio **Spring Boot - JAR** leadmanager/ se verá así: <br /> Info: Este tutorial ha creado un proyecto Spring Boot para demostrar la construcción de un proyecto Spring Boot - JAR, y desplegarlo como un servicio AppSail. Puedes aprender cómo hacer lo mismo con proyectos Spring Boot - WAR en esta documentación de ayuda. Para más información sobre cómo crear un proyecto Spring Boot, puedes visitar su documentación de ayuda oficial. -------------------------------------------------------------------------------- title: "Inicializar el proyecto" description: "Construye una aplicación Lead Manager y alójala en AppSail. La aplicación se conecta a tu cuenta de Zoho CRM usando conectores de Catalyst, y te permite ver, crear, actualizar o eliminar leads desde el módulo de Leads en tu CRM." last_updated: "2026-10-08T06:48:03.652Z" source: "https://docs.catalyst.zoho.com/es/tutorials/leadmanager-appsail/springboot/init-project/" service: "All Services" related: - Catalyst CLI (/es/cli/v1/cli-command-reference/) - Initialize Resources (/es/cli/v1/initialize-resources/introduction/) - Catalyst AppSail Help (/es/serverless/help/appsail/introduction/) - Project Directory (/es/cli/v1/project-directory-structure/introduction/) -------------------------------------------------------------------------------- # Inicializar el proyecto Ahora puedes comenzar a trabajar en tu proyecto de Catalyst desde la CLI. El primer paso es inicializar el proyecto en un directorio vacío. Este será el directorio principal de tu proyecto, y todos los archivos del proyecto se guardarán en él. Puedes aprender más sobre esto en la página de ayuda de Estructura de Directorio del Proyecto. Puedes aprender sobre la inicialización de un proyecto en detalle en la documentación de ayuda de la CLI. Para esta aplicación, inicializarás únicamente el componente AppSail. El componente *AppSail* se inicializará en el stack de programación **Node.js**. 1. Crea una carpeta para el proyecto en tu máquina local y navega hasta ella desde la terminal. 2. Inicializa un proyecto ejecutando el siguiente comando desde ese directorio: catalyst init 3. Navega usando las **teclas de flecha** y selecciona tu portal preferido y haz clic en **Enter**. Si no tienes otras organizaciones asociadas con la cuenta, entonces se seleccionará la predeterminada automáticamente. <br /> Info: Puedes encontrar más información sobre la función de portal multi-org de Catalyst en este documento de ayuda. 4. La CLI ahora te pedirá que asocies un proyecto de Catalyst con el directorio. Asócialo con el proyecto que creamos anteriormente desde la consola. Selecciona **LeadManager** de la lista y haz clic en **Enter**. <br /> 5. Selecciona **AppSail** usando la barra espaciadora, luego haz clic en **Enter** para inicializar. <br /> 6. La CLI te pedirá que elijas entre Catalyst-Managed Runtime y Docker Image. Como estás creando este proyecto desde uno de los Catalyst-Managed Runtime, selecciona **Catalyst-Managed Runtime** y haz clic en **Enter**. <br/> 7. La CLI iniciará el servicio *AppSail*. - Como estás creando tu propio proyecto, ingresa "n" y haz clic en **Enter** para la solicitud que pregunta si deseas comenzar con una lista de proyectos recomendados. <br /> - Ingresa "Y" en la solicitud para inicializar el servicio *AppSail* en tu directorio actual. <br /> 8. Ingresa "LeadManagerApp" como el nombre de tu servicio AppSail, e ingresa la ruta del directorio de tu proyecto como la ruta de compilación de tu servicio AppSail. <br /> 9. Elige el runtime más reciente de **Java** como el stack de programación, y haz clic en **Enter**. <br /> 10. Elige **Java SE** como la plataforma para tu servicio AppSail. <br /> El servicio AppSail ha sido inicializado para tu aplicación Lead Manager. <br /> El directorio se creará en la estructura estándar, y contendrá el archivo app-config.json que incluye la configuración de tu servicio AppSail, junto con los archivos de configuración estándar del proyecto como el archivo catalyst.json y un archivo oculto .catalystrc. Esta es la estructura del directorio del proyecto **LeadManager** inicializado con el servicio *AppSail*. <br /> ### Desplegar la aplicación Necesitas desplegar la aplicación en la consola remota para obtener la **URL de la aplicación** requerida. Necesitamos esta URL cuando registremos el cliente en la consola de API de Zoho para obtener los valores de Client ID y Client Secret requeridos. Info: Volveremos a desplegar el servicio de la aplicación una vez que hayamos completado la codificación y agregado los valores de Client ID y Client Secret a la aplicación. Ingresa el siguiente comando de CLI para desplegar la aplicación: catalyst deploy Ahora, para obtener la URL de la aplicación: 1. Navega al componente AppSail presente en la sección *COMPUTE* de la sección **Catalyst Serverless** de la consola. <br /> Podrás ver que tu aplicación ha sido desplegada como un servicio AppSail. 2. Ahora haz clic en tu servicio AppSail, y podrás ver la URL de la aplicación. <br /> Info: Discutiremos más sobre el comando de CLI catalyst deploy y el servicio AppSail, después de que volvamos a desplegar la aplicación, hacia el final del tutorial. -------------------------------------------------------------------------------- title: "Registrar el cliente" description: "Construye una aplicación Lead Manager y alójala en AppSail. La aplicación se conecta a tu cuenta de Zoho CRM usando conectores de Catalyst, y te permite ver, crear, actualizar o eliminar leads desde el módulo de Leads en tu CRM." last_updated: "2026-10-08T06:48:03.653Z" source: "https://docs.catalyst.zoho.com/es/tutorials/leadmanager-appsail/springboot/register-client/" service: "All Services" related: - Catalyst Authentication (/es/cloud-scale/help/authentication/introduction/) - Social Logins (/es/cloud-scale/help/authentication/social-logins/introduction/) -------------------------------------------------------------------------------- # Registrar el cliente Ahora debemos registrar la aplicación cliente en la consola de API de Zoho para generar las siguientes credenciales: - **Client ID**: La clave única generada para un cliente registrado - **Client Secret**: El valor secreto generado para el Client ID de un cliente registrado El Client ID y el Client Secret se agregan al código del backend y frontend en varios lugares. Estos valores son necesarios para generar el Access Token y el Refresh Token inicialmente, y luego para renovar el Access Token usando el Refresh Token. Para registrar la aplicación cliente en la consola de API de Zoho: 1. Visita la consola de API de Zoho y haz clic en **Get Started**. <br /> 2. Selecciona **Server-based Applications** como el tipo de cliente. <br /> 3. Ingresa "LeadManagerApp" como el **Client Name**. <br /> 4. Proporciona los otros detalles en el siguiente formato: - Homepage URL: **URL de la aplicación AppSail** - Authorized Redirect URIs: **URL de la aplicación AppSail/generateToken** <br /> Reemplaza {**URL de la aplicación AppSail**} con la URL de la aplicación que obtuviste cuando desplegaste tu proyecto anteriormente en este paso. 5. Necesitarás agregar otra **Authorized Redirect URI** para el cliente. Serviremos la aplicación a través de un **localhost** para probarla después de configurar el código. Como esto será redirigido a un dominio local, debemos agregar eso como otra URI de redirección autorizada. <br /> Info: Cuando sirves una aplicación localmente desde la CLI, se aloja desde el puerto 3000 por defecto, a menos que el puerto esté ocupado. Así que asegúrate de agregar el dominio correspondiente. 6. Haz clic en **Create**. <br /> La consola de API generará y mostrará los valores de Client ID y Client Secret para el cliente registrado. Necesitarás copiar estos valores y pegarlos en el código del frontend y backend de tu aplicación. Discutiremos esto en las siguientes secciones. -------------------------------------------------------------------------------- title: "Codificar tu aplicación" description: "Construye una aplicación Lead Manager y alójala en AppSail. La aplicación se conecta a tu cuenta de Zoho CRM usando conectores de Catalyst, y te permite ver, crear, actualizar o eliminar leads desde el módulo de Leads en tu CRM." last_updated: "2026-10-08T06:48:03.654Z" source: "https://docs.catalyst.zoho.com/es/tutorials/leadmanager-appsail/springboot/code-app/" service: "All Services" related: - Web SDK for Authentication (/es/sdk/web/v4/cloud-scale/authentication/get-auth-instance/) -------------------------------------------------------------------------------- # Codificar tu aplicación En el directorio leadmanager/src/main/java/com/catalyst/appsail/leadmanager/, crea un archivo de código Java y nómbralo **LeadmanagerApplication.java**. Este archivo de código contendrá la lógica que te permitirá servir tu aplicación. Junto con este archivo, necesitas crear los siguientes archivos de código en el mismo directorio: * **LeadManager.java**: Contendrá la lógica de negocio de tu aplicación. * **AuthProviderImpl.java**: Contendrá la lógica para inicializar el SDK de Catalyst. En el directorio /src/main/resources/static, crea los siguientes archivos: * **index.html**: El archivo que contiene el código HTML para el front-end de la aplicación. * **login.html**: El archivo que contiene el código HTML para la lógica de Embedded Authentication. * **main.css**: El archivo que contiene los elementos de estilo de la aplicación. * **main.js**: El archivo que contiene el código JavaScript que conecta el front-end y el backend. La estructura final del directorio del proyecto **Spring Boot - JAR** leadmanager/ se muestra a continuación: <br /> Codificarás los archivos LeadManager.java, LeadmanagerApplication.java, AuthProviderImpl.java, index.html, login.html, main.css, main.js y pom.xml. Nota: Por favor revisa el código en esta sección para asegurarte de que lo comprendes completamente. Copia el código a continuación y pégalo en los archivos respectivos de tu proyecto usando un IDE y guarda los archivos. package com.catalyst.appsail.leadmanager; import java.util.Collections; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import jakarta.servlet.http.HttpServlet; @SpringBootApplication public class LeadmanagerApplication extends HttpServlet { public static void main(String[] args) { String port = System.getenv().getOrDefault("X_ZOHO_CATALYST_LISTEN_PORT","3000"); SpringApplication app = new SpringApplication(LeadmanagerApplication.class); app.setDefaultProperties(Collections.singletonMap("server.port",port)); app.run(args); } } package com.catalyst.appsail.leadmanager; import java.util.*; import java.util.logging.Logger; import com.zc.auth.CatalystSDK; import com.zc.auth.connectors.ZCConnection; import com.zc.component.ZCUserDetail; import com.zc.component.object.ZCObject; import com.zc.component.object.ZCRowObject; import com.zc.component.object.ZCTable; import com.zc.component.users.ZCUser; import com.zc.component.zcql.ZCQL; import org.json.simple.JSONObject; import org.json.simple.parser.JSONParser; import okhttp3.HttpUrl; import okhttp3.MediaType; import okhttp3.OkHttpClient; import okhttp3.Request; import org.springframework.web.bind.annotation.RequestBody; import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.DeleteMapping; import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.PutMapping; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.RestController; import jakarta.servlet.http.HttpServletRequest; import jakarta.servlet.http.HttpServletResponse; @RestController class LeadManager { @SuppressWarnings("unused") private static final Logger LOGGER = Logger.getLogger(LeadManager.class.getName()); private String apiUrl = "https://www.zohoapis.com/crm/v2/Leads"; private String GET = "GET"; private String POST = "POST"; private String PUT = "PUT"; private String DELETE = "DELETE"; private String CLIENT_ID = ""; //Agrega tu Client ID private String CLIENT_SECRET = ""; //Agrega tu Client Secret OkHttpClient client = new OkHttpClient(); String responseData = ""; MediaType mediaType = MediaType.parse("application/json"); org.json.simple.JSONArray reqData = new org.json.simple.JSONArray(); JSONObject data = new JSONObject(); JSONParser jsonParser = new JSONParser(); @GetMapping("/generateToken") public void generateToken(HttpServletRequest request, HttpServletResponse response) throws Exception { CatalystSDK.init(new AuthProviderImpl((HttpServletRequest) request)); String code = request.getParameter("code"); String domain = (request.getHeader("host").contains("localhost") ? ("http://" + request.getHeader("host")) : ("https://") + request.getHeader("host").split(":")[0]); ZCUserDetail details = ZCUser.getInstance().getCurrentUser(); ZCObject object = ZCObject.getInstance(); ZCRowObject row = ZCRowObject.getInstance(); row.set("refresh_token", getRefreshToken(code, domain)); row.set("userId", details.getUserId()); ZCTable tab = object.getTable(********l); //Reemplaza esto con el Table ID de tu tabla tab.insertRow(row); response.setStatus(HttpServletResponse.SC_OK); response.sendRedirect(domain + "/index.html"); } public String getRefreshToken(String code, String domain) throws Exception { HttpUrl.Builder urlBuilder = HttpUrl.parse("https://accounts.zoho.com/oauth/v2/token").newBuilder(); urlBuilder.addQueryParameter("code", code); urlBuilder.addQueryParameter("client_id", CLIENT_ID); urlBuilder.addQueryParameter("client_secret", CLIENT_SECRET); urlBuilder.addQueryParameter("grant_type", "authorization_code"); urlBuilder.addQueryParameter("redirect_uri", domain + "/generateToken"); String URL = urlBuilder.build().toString(); MediaType mediaType = MediaType.parse("text/plain"); okhttp3.RequestBody body = okhttp3.RequestBody.create(mediaType, ""); Request getResponse = new Request.Builder().url(URL).method(POST, body).build(); JSONParser jsonParser = new JSONParser(); JSONObject data = (JSONObject) jsonParser.parse(client.newCall(getResponse).execute().body().string()); return data.get("refresh_token").toString(); } @SuppressWarnings("unchecked") @GetMapping("/getUserDetails") public void getUserDetails(HttpServletRequest request, HttpServletResponse response) throws Exception { CatalystSDK.init(new AuthProviderImpl((HttpServletRequest) request)); Long userId = ZCUser.getInstance().getCurrentUser().getUserId(); String query = "SELECT * FROM Token where UserId="+userId; ArrayList&lt;ZCRowObject&gt; rowList = ZCQL.getInstance().executeQuery(query); JSONObject resp = new JSONObject(); if (rowList.isEmpty()) { resp.put("userId", null); response.setContentType("application/json"); response.getWriter().write(resp.toJSONString()); response.setStatus(200); } else { resp.put("userId", rowList.get(0).get("Token", "userId")); response.setContentType("application/json"); response.getWriter().write(resp.toJSONString()); response.setStatus(200); } } public ArrayList&lt;ZCRowObject&gt; getuserDetails(HttpServletRequest request) throws Exception { CatalystSDK.init(new AuthProviderImpl((HttpServletRequest) request)); Long userId = ZCUser.getInstance().getCurrentUser().getUserId(); String query = "SELECT * FROM Token where UserId="+userId; ArrayList&lt;ZCRowObject&gt; rowList = ZCQL.getInstance().executeQuery(query); return rowList; } @GetMapping("/crmData") public void getAllLeads(HttpServletRequest request,HttpServletResponse response) throws Exception { responseData = getResponse(GET, null,request,apiUrl); response.setContentType("application/json"); response.getWriter().write(responseData); response.setStatus(200); } @GetMapping("/crmData/{id}") public void getLead(@PathVariable Long id,HttpServletRequest request,HttpServletResponse response) throws Exception { String apiUri = apiUrl + "/" + id; responseData = getResponse(GET, null,request,apiUri); response.setContentType("application/json"); response.getWriter().write(responseData); response.setStatus(200); } @SuppressWarnings("unchecked") @PostMapping("/crmData") public void addLead(@RequestBody String leadData,HttpServletRequest request,HttpServletResponse response) throws Exception { JSONObject jsonObject = (JSONObject)jsonParser.parse(leadData); reqData.add(jsonObject); data.put("data", reqData); okhttp3.RequestBody body = okhttp3.RequestBody.create(mediaType,data.toString()); responseData = getResponse(POST, body,request,apiUrl); response.setContentType("application/json"); response.getWriter().write(responseData); response.setStatus(200); } @DeleteMapping("/crmData/{id}") public void deleteLead(@PathVariable Long id,HttpServletRequest request,HttpServletResponse response) throws Exception { String apiUri = apiUrl + "/" + id; responseData = getResponse(DELETE, null,request,apiUri); response.setContentType("application/json"); response.getWriter().write(responseData); response.setStatus(200); } @SuppressWarnings("unchecked") @PutMapping("/crmData/{id}") public void editLead(@PathVariable Long id, @RequestBody String leadData,HttpServletRequest request,HttpServletResponse response) throws Exception { String apiUri = apiUrl + "/" + id; JSONObject jsonObject = (JSONObject)jsonParser.parse(leadData); reqData.add(jsonObject); data.put("data", reqData); okhttp3.RequestBody body = okhttp3.RequestBody.create(mediaType,data.toString()); responseData = getResponse(PUT, body,request,apiUri); reqData.remove(jsonObject); response.setContentType("application/json"); response.getWriter().write(responseData); response.setStatus(200); } public String getResponse(String METHOD, okhttp3.RequestBody body,HttpServletRequest request,String apiUrl) throws Exception { CatalystSDK.init(new AuthProviderImpl((HttpServletRequest) request)); Long userId = ZCUser.getInstance().getCurrentUser().getUserId(); String accessToken = getAccessToken(userId,request); Request getResponse = new Request.Builder().url(apiUrl).method(METHOD, body) .addHeader("Authorization", "Zoho-oauthtoken " + accessToken).build(); String resp = client.newCall(getResponse).execute().body().string(); return resp; } @SuppressWarnings("unchecked") public String getAccessToken(Long userId,HttpServletRequest request) throws Exception { CatalystSDK.init(new AuthProviderImpl((HttpServletRequest) request)); JSONObject authJson = new JSONObject(); JSONObject connectorJson = new JSONObject(); String query = "SELECT refresh_token FROM Token where UserId="+userId; ArrayList&lt;ZCRowObject&gt; rowList = ZCQL.getInstance().executeQuery(query); authJson.put("client_id", CLIENT_ID); authJson.put("client_secret", CLIENT_SECRET); authJson.put("auth_url", "https://accounts.zoho.com/oauth/v2/token"); authJson.put("refresh_url", "https://accounts.zoho.com/oauth/v2/token"); authJson.put("refresh_token", rowList.get(0).get("Token", "refresh_token")); connectorJson.put(userId.toString(), authJson); return ZCConnection.getInstance(connectorJson).getConnector(userId.toString()).getAccessToken(); } } Nota:<br /> * Asegúrate de agregar los valores de Client ID y Client Secret obtenidos después de registrar el cliente en la consola de API de Zoho en las líneas 46 y 47 respectivamente, en el archivo de código anterior. * Agrega el Table ID de la tabla que creaste en el Data Store en la línea 65. package com.catalyst.appsail.leadmanager; import com.zc.auth.AuthHeaderProvider; import jakarta.servlet.http.HttpServletRequest; public class AuthProviderImpl implements AuthHeaderProvider { private HttpServletRequest request; AuthProviderImpl(HttpServletRequest request) { this.request = request; } @Override public String getHeaderValue(String s) { return request.getHeader(s); } } &lt;!DOCTYPE html&gt; &lt;html&gt; &lt;head&gt; &lt;meta charset="utf-8" /&gt; &lt;meta http-equiv="X-UA-Compatible" content="IE=edge"&gt; &lt;title&gt;CRM Lead Manager&lt;/title&gt; &lt;meta name="viewport" content="width=device-width, initial-scale=1"&gt; &lt;link rel="stylesheet" type="text/css" media="screen" href="main.css" /&gt; &lt;link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/css/bootstrap.min.css" integrity="sha384-ggOyR0iXCbMQv3Xipma34MD+dH/1fQ784/j6cY/iJTQUOhcWr7x9JvoRxT2MZw1T" crossorigin="anonymous"&gt; &lt;link href="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/4.5.0/css/bootstrap.min.css" rel="stylesheet"&gt; &lt;link href="https://cdnjs.cloudflare.com/ajax/libs/mdbootstrap/4.19.1/css/mdb.min.css" rel="stylesheet"&gt; &lt;script src="https://code.jquery.com/jquery-3.4.1.min.js" integrity="sha256-CSXorXvZcTkaix6Yvo6HppcZGetbYMGWSFlBw8HfCJo=" crossorigin="anonymous"&gt; &lt;/script&gt; &lt;script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.14.7/umd/popper.min.js" integrity="sha384-UO2eT0CpHqdSJQ6hJty5KVphtPhzWj9WO1clHTMGa3JDZwrnQq4sF86dIHNDz0W1" crossorigin="anonymous"&gt; &lt;/script&gt; &lt;script src="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/js/bootstrap.min.js" integrity="sha384-JjSmVgyd0p3pXB1rRibZUAYoIIy6OrQ6VrjIEaFf/nJGzIxFDsf4x0xIM+B07jRM" crossorigin="anonymous"&gt; &lt;/script&gt; &lt;script src="main.js"&gt; &lt;/script&gt; &lt;script src="https://static.zohocdn.com/catalyst/sdk/js/4.6.2/catalystWebSDK.js"&gt; &lt;/script&gt; &lt;script src="/__catalyst/sdk/init.js"&gt; &lt;/script&gt; &lt;link href="//maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css" rel="stylesheet" id="bootstrap-css"&gt; &lt;style&gt; #connect { height: 260px; width: 500px; position: absolute; top: 0; bottom: 0; left: 0; right: 0; margin: auto; } &lt;/style&gt; &lt;/head&gt; &lt;body onload="getUserDetails()"&gt; &lt;br&gt; &lt;center&gt; &lt;h1&gt;CRM Lead Manager&lt;/h1&gt; &lt;br&gt; &lt;/center&gt; &lt;div id="connect"&gt; &lt;center&gt; &lt;p&gt;Click here to connect to Zoho CRM&lt;/p&gt; &lt;button onclick='navigate()'&gt; &lt;img src="https://www.zohowebstatic.com/sites/default/files/styles/product-home-page/public/icon-crm_blue.png" style="width: 180px;height: 130px;"&gt; &lt;/button&gt; &lt;/center&gt; &lt;/div&gt; &lt;div style="width: 200px;float: right; margin-right: 30px;"&gt; &lt;label for="logoutbtn" class="btn btn-success btn-block btn-outlined"&gt;Logout&lt;/label&gt; &lt;button id="logoutbtn" onclick="logout()" style="display: none;"&gt; &lt;/button&gt; &lt;/div&gt; &lt;div id="main"&gt; &lt;div class="container"&gt; &lt;ul class="nav nav-tabs nav-justified mb-3" id="myTab" role="tablist"&gt; &lt;li class="nav-item"&gt; &lt;a class="nav-link active" id="check-tab" data-toggle="tab" href="#check" role="tab" aria-controls="check" aria-selected="true"&gt;Add a Lead&lt;/a&gt; &lt;/li&gt; &lt;li class="nav-item"&gt; &lt;a class="nav-link" id="report-tab" data-toggle="tab" href="#report" onclick="getLeads()" role="tab" aria-controls="report" aria-selected="false"&gt;Manage Leads&lt;/a&gt; &lt;/li&gt; &lt;/ul&gt; &lt;br&gt; &lt;div class="tab-content" id="myTabContent"&gt; &lt;div class="tab-pane fade show active" id="check" role="tabpanel" aria-labelledby="check-tab"&gt; &lt;div class="tab-pane fade show active" id="ex3-tabs-1" role="tabpanel" aria-labelledby="ex3-tab-1"&gt; &lt;div style="margin-left: 100px; margin-right:100px;"&gt; &lt;form id="leads"&gt; &lt;!-- 2 column grid layout with text inputs for the first and last names --&gt; &lt;div class="row mb-4"&gt; &lt;div class="col"&gt; &lt;div class="form-outline"&gt; &lt;label class="form-label" for="form6Example1"&gt;First name&lt;/label&gt; &lt;input type="text" id="firstName" class="form-control" /&gt; &lt;/div&gt; &lt;/div&gt; &lt;div class="col"&gt; &lt;div class="form-outline"&gt; &lt;label class="form-label" for="form6Example2"&gt;Last name&lt;/label&gt; &lt;input type="text" id="lastName" class="form-control" required /&gt; &lt;/div&gt; &lt;/div&gt; &lt;/div&gt; &lt;!-- Text input --&gt; &lt;div class="form-outline mb-4"&gt; &lt;label class="form-label" for="form6Example3"&gt;Company name&lt;/label&gt; &lt;input type="text" id="companyName" class="form-control" /&gt; &lt;/div&gt; &lt;!-- Email input --&gt; &lt;div class="form-outline mb-4"&gt; &lt;label class="form-label" for="form6Example5"&gt;Email&lt;/label&gt; &lt;input type="email" id="email" class="form-control" /&gt; &lt;/div&gt; &lt;!-- Text input --&gt; &lt;div class="form-outline mb-4"&gt; &lt;label class="form-label" for="form6Example4"&gt;State&lt;/label&gt; &lt;input type="text" id="state" class="form-control" /&gt; &lt;/div&gt; &lt;!-- Number input --&gt; &lt;div class="form-outline mb-4"&gt; &lt;label class="form-label" for="form6Example6"&gt;Phone&lt;/label&gt; &lt;input type="number" id="phone" class="form-control" /&gt; &lt;/div&gt; &lt;!-- Number input --&gt; &lt;div class="form-outline mb-4"&gt; &lt;label class="form-label" for="form6Example6"&gt;Lead Source&lt;/label&gt; &lt;input type="text" id="leadSource" class="form-control" /&gt; &lt;/div&gt; &lt;!-- Submit button --&gt; &lt;center&gt; &lt;button type="submit" onclick="createLead();return false;" class="btn btn-primary btn-block mb-4" style="width: 100px;"&gt;Add Lead&lt;/button&gt; &lt;div id="loader" style="display: none;"&gt; &lt;div class="spinner-border" role="status"&gt; &lt;span class="sr-only"&gt;Loading...&lt;/span&gt; &lt;/div&gt; &lt;/div&gt; &lt;/center&gt; &lt;/form&gt; &lt;/div&gt; &lt;/div&gt; &lt;/div&gt; &lt;div class="tab-pane fade" id="report" role="tabpanel" aria-labelledby="report-tab"&gt; &lt;center&gt; &lt;div id="loaders" style="display: none; padding-top: 200px;"&gt; &lt;div class="spinner-border" role="status"&gt; &lt;span class="sr-only"&gt;Loading...&lt;/span&gt; &lt;/div&gt; &lt;/div&gt; &lt;/center&gt; &lt;p id="showData"&gt; &lt;/p&gt; &lt;/div&gt; &lt;/div&gt; &lt;/div&gt; &lt;!-- Modal --&gt; &lt;div class="modal fade" id="myModal" tabindex="-1" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true"&gt; &lt;div class="vertical-alignment-helper"&gt; &lt;div class="modal-dialog vertical-align-center"&gt; &lt;div class="modal-content"&gt; &lt;center&gt; &lt;h4 class="modal-title" id="myModalLabel"&gt; &lt;/h4&gt; &lt;div class="modal-body" id="message"&gt; &lt;/div&gt; &lt;div class="modal-footer"&gt; &lt;button type="button" style="background-color: #007bff;color: white;" class="btn btn-default" data-dismiss="modal"&gt;Close&lt;/button&gt; &lt;/div&gt; &lt;/center&gt; &lt;/div&gt; &lt;/div&gt; &lt;/div&gt; &lt;/div&gt; &lt;div class="modal fade" id="editForm" tabindex="-1" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true"&gt; &lt;div class="vertical-alignment-helper"&gt; &lt;div class="modal-dialog vertical-align-center"&gt; &lt;div class="modal-content"&gt; &lt;div style="margin-left: 80px; margin-right:80px;"&gt; &lt;br&gt; &lt;center&gt; &lt;h2&gt;Edit Lead&lt;/h2&gt; &lt;/center&gt; &lt;br&gt; &lt;form id="editLeads"&gt; &lt;!-- 2 column grid layout with text inputs for the first and last names --&gt; &lt;div class="row mb-4"&gt; &lt;div class="col"&gt; &lt;div class="form-outline"&gt; &lt;label class="form-label" for="form6Example1"&gt;First name&lt;/label&gt; &lt;input type="text" id="editfirstName" class="form-control" /&gt; &lt;/div&gt; &lt;/div&gt; &lt;div class="col"&gt; &lt;div class="form-outline"&gt; &lt;label class="form-label" for="form6Example2"&gt;Last name&lt;/label&gt; &lt;input type="text" id="editlastName" class="form-control" required /&gt; &lt;/div&gt; &lt;/div&gt; &lt;/div&gt; &lt;!-- Text input --&gt; &lt;div class="form-outline mb-4"&gt; &lt;label class="form-label" for="form6Example3"&gt;Company name&lt;/label&gt; &lt;input type="text" id="editcompanyName" class="form-control" /&gt; &lt;/div&gt; &lt;!-- Email input --&gt; &lt;div class="form-outline mb-4"&gt; &lt;label class="form-label" for="form6Example5"&gt;Email&lt;/label&gt; &lt;input type="email" id="editemail" class="form-control" /&gt; &lt;/div&gt; &lt;!-- Text input --&gt; &lt;div class="form-outline mb-4"&gt; &lt;label class="form-label" for="form6Example4"&gt;State&lt;/label&gt; &lt;input type="text" id="editstate" class="form-control" /&gt; &lt;/div&gt; &lt;!-- Number input --&gt; &lt;div class="form-outline mb-4"&gt; &lt;label class="form-label" for="form6Example6"&gt;Phone&lt;/label&gt; &lt;input type="number" id="editphone" class="form-control" /&gt; &lt;/div&gt; &lt;!-- Submit button --&gt; &lt;center&gt; &lt;button type="submit" id="editBtn" onclick="editLead();return false;" class="btn btn-primary btn-block mb-4" style="width: 100px;"&gt;Edit&lt;/button&gt; &lt;div id="loader" style="display: none;"&gt; &lt;div class="spinner-border" role="status"&gt; &lt;span class="sr-only"&gt;Loading...&lt;/span&gt; &lt;/div&gt; &lt;/div&gt; &lt;/center&gt; &lt;/form&gt; &lt;/div&gt; &lt;/div&gt; &lt;/div&gt; &lt;/div&gt; &lt;/div&gt; &lt;div class="modal fade right" id="ModalDanger" tabindex="-1" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true"&gt; &lt;div class="modal-dialog modal-notify modal-danger modal-side modal-top-right" role="document"&gt; &lt;!--Content--&gt; &lt;div class="modal-content"&gt; &lt;!--Header--&gt; &lt;div class="modal-header"&gt; &lt;p class="heading"&gt;Lead Deletion&lt;/p&gt; &lt;button type="button" class="close" data-dismiss="modal" aria-label="Close"&gt; &lt;span aria-hidden="true" class="white-text"&gt;×&lt;/span&gt; &lt;/button&gt; &lt;/div&gt; &lt;!--Body--&gt; &lt;div class="modal-body"&gt; &lt;div class="row"&gt; &lt;div class="col-9"&gt; &lt;p&gt;Are you sure you want to delete the Lead?&lt;/p&gt; &lt;/div&gt; &lt;/div&gt; &lt;/div&gt; &lt;!--Footer--&gt; &lt;div class="modal-footer justify-content-center"&gt; &lt;a type="button" class="btn btn-danger" id="delete-btn" onclick="deleteLead()"&gt;Delete&lt;/a&gt; &lt;a type="button" class="btn btn-outline-danger waves-effect" data-dismiss="modal"&gt;Cancel&lt;/a&gt; &lt;/div&gt; &lt;/div&gt; &lt;!--/.Content--&gt; &lt;/div&gt; &lt;/div&gt; &lt;/div&gt; &lt;/body&gt; &lt;script&gt; //Agrega tu Client ID function navigate() { window.location.href = "https://accounts.zoho.com/oauth/v2/auth?scope=ZohoCRM.modules.ALL&client_id={{client_id}}&response_type=code&access_type=offline&redirect_uri=" + location.protocol + '//' + location.host + "/generateToken"; } &lt;/script&gt; &lt;/html&gt; Nota: Asegúrate de ingresar el Client ID en la línea 252 &lt;html&gt; &lt;/html&gt; &lt;meta charset="utf-8" /&gt; &lt;meta http-equiv="X-UA-Compatible" content="IE=edge"&gt; &lt;title&gt;CRM Lead Manager&lt;/title&gt; &lt;meta name="viewport" content="width=device-width, initial-scale=1"&gt; &lt;link rel="stylesheet" type="text/css" media="screen" href="main.css" /&gt; &lt;script src="main.js"&gt; &lt;/script&gt; &lt;link rel="stylesheet" type="text/css" media="screen" href="main.css" /&gt; &lt;link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/css/bootstrap.min.css" integrity="sha384-ggOyR0iXCbMQv3Xipma34MD+dH/1fQ784/j6cY/iJTQUOhcWr7x9JvoRxT2MZw1T" crossorigin="anonymous"&gt; &lt;script src="https://static.zohocdn.com/catalyst/sdk/js/4.6.2/catalystWebSDK.js"&gt; &lt;/script&gt; &lt;script src="https://code.jquery.com/jquery-3.4.1.min.js" integrity="sha256-CSXorXvZcTkaix6Yvo6HppcZGetbYMGWSFlBw8HfCJo=" crossorigin="anonymous"&gt; &lt;/script&gt; &lt;script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.14.7/umd/popper.min.js" integrity="sha384-UO2eT0CpHqdSJQ6hJty5KVphtPhzWj9WO1clHTMGa3JDZwrnQq4sF86dIHNDz0W1" crossorigin="anonymous"&gt; &lt;/script&gt; &lt;script src="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/js/bootstrap.min.js" integrity="sha384-JjSmVgyd0p3pXB1rRibZUAYoIIy6OrQ6VrjIEaFf/nJGzIxFDsf4x0xIM+B07jRM" crossorigin="anonymous"&gt; &lt;/script&gt; &lt;script src="https://static.zohocdn.com/catalyst/sdk/js/4.6.2/catalystWebSDK.js"&gt; &lt;/script&gt; &lt;script src="/__catalyst/sdk/init.js"&gt; &lt;/script&gt; &lt;script&gt; catalyst.auth.signIn("login"); &lt;/script&gt; &lt;link href="//maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css" rel="stylesheet" id="bootstrap-css"&gt; &lt;style&gt; #login { height: 100%; width: 100%; position: absolute; top: 0; bottom: 0; left: 0; right: 0; margin: auto; } &lt;/style&gt; &lt;body&gt; &lt;br&gt; &lt;center&gt; &lt;h1&gt;CRM Lead Manager&lt;/h1&gt; &lt;/center&gt; &lt;div id="login"&gt; &lt;/div&gt; &lt;/body&gt; &lt;/html&gt; #dataTable { font-family: Arial, Helvetica, sans-serif; border-collapse: collapse; width: 100%; } #dataTable td, #dataTable th { border: 1px solid #ddd; padding: 8px; } #dataTable tr:nth-child(even){background-color: #f2f2f2;} #dataTable tr:hover {background-color: #ddd;} #dataTable th { padding-top: 12px; padding-bottom: 12px; text-align: left; background-color: #007bff; color: white; } .vertical-alignment-helper { display: table; height: 100%; width: 100%; pointer-events: none; } .vertical-align-center { display: table-cell; vertical-align: middle; pointer-events: none; } .modal-content { width: inherit; max-width: inherit; height: inherit; margin: 0 auto; pointer-events: all; } function createLead() { debugger; $("#loader").show(); var firstName = $("#firstName").val(); var lastName = $("#lastName").val(); if (lastName == "") { alert("Kindly Enter the Last Name"); $("#loader").hide(); return; } var companyName = $("#companyName").val(); var email = $("#email").val(); var state = $("#state").val(); var phone = $("#phone").val(); var leadSource = $("#leadSource").val(); $.ajax({ url: "/crmData", type: "post", contentType: "application/json", data: JSON.stringify({ "First_Name": firstName, "Last_Name": lastName, "Company": companyName, "Email": email, "State": state, "Phone": phone, "Lead_Source": leadSource, }), success: function (data) { debugger; $('#leads').trigger("reset"); $("#myModalLabel").html("Success"); $("#message").html("Lead Created Successfully"); $("#loader").hide(); $('#myModal').modal('show'); }, error: function (error) { $('#leads').trigger("reset"); $("#myModalLabel").html("Failure"); $("#message").html("Please try again after Sometime"); $("#loader").hide(); $('#myModal').modal('show'); } }); } function logout() { var redirectURL = "/login.html"; //Agrega el dominio de tu aplicación var auth = catalyst.auth; auth.signOut(redirectURL); } function getUserDetails() { $("#main").hide(); $("#connect").hide(); catalyst.auth.isUserAuthenticated().then(result =&gt; { console.log(result) $("#loader").show(); $.ajax({ url: "/getUserDetails", type: "get", success: function (data) { $("#loader").hide(); if (data.userId) { $("#main").show(); $("#connect").hide(); } else { $("#connect").show(); $("#main").hide(); } }, error: function (error) { $("#myModalLabel").html("Failure"); $("#message").html("Please try again after Sometime"); $("#loader").hide(); $('#myModal').modal('show'); } }); }).catch(err =&gt; { document.body.innerHTML = 'You are not logged in. Please log in to continue. Redirecting you to the login page..'; setTimeout(function () { window.location.href = "login.html"; }, 3000); }); } function getLeads() { debugger; var tableContainer = document.getElementById("showData"); tableContainer.innerHTML = ""; $("#loaders").show(); $.ajax({ url: "/crmData", type: "get", success: function (data) { debugger; var reqData = getRequiredData(data.data); $("#loaders").hide(); renderTable(reqData); }, error: function (error) { $("#myModalLabel").html("Failure"); $("#message").html("Please try again after Sometime"); $("#loader").hide(); $('#myModal').modal('show'); } }); } function showDeletePopup(leadID) { $('#ModalDanger').modal('show'); var deleteBtn = document.getElementById("delete-btn"); deleteBtn.value = leadID; } function deleteLead() { var leadID = document.getElementById('delete-btn').value; $.ajax({ url: "/crmData/" + leadID, type: "delete", success: function (data) { debugger; $('#ModalDanger').modal('toggle'); $("#myModalLabel").html("Success"); $("#message").html("Lead Deleted Successfully"); $('#myModal').modal('show'); setTimeout(function () { location.reload(); }, 3000); }, error: function (error) { $("#myModalLabel").html("Failure"); $("#message").html("Please try again after Sometime"); $("#loader").hide(); $('#myModal').modal('show'); } }); } function showEditPopup(leadID) { $.ajax({ url: "/crmData/" + leadID, type: "get", success: function (data) { debugger; var respData = data.data; $('#editfirstName').val(respData[0].First_Name); $('#editlastName').val(respData[0].Last_Name); $('#editcompanyName').val(respData[0].Company); $('#editemail').val(respData[0].Email); $('#editstate').val(respData[0].State); $('#editphone').val(respData[0].Phone); $('#editleadSource').val(respData[0].Lead_Source); $('#editBtn').val(respData[0].id); $('#editfirstName').html(respData[0].First_Name); $('#editlastName').html(respData[0].Last_Name); $('#editcompanyName').html(respData[0].Company); $('#editemail').html(respData[0].Email); $('#editstate').html(respData[0].State); $('#editphone').html(respData[0].Phone); $('#editleadSource').html(respData[0].Lead_Source); $('#editForm').modal('show'); }, error: function (error) { $("#myModalLabel").html("Failure"); $("#message").html("Please try again after Sometime"); $("#loader").hide(); $('#myModal').modal('show'); } }); } function editLead() { var firstName = $("#editfirstName").val(); var lastName = $("#editlastName").val(); if (lastName == "") { alert("Kindly Enter the Last Name"); return; } var companyName = $("#editcompanyName").val(); var email = $("#editemail").val(); var state = $("#editstate").val(); var phone = $("#editphone").val(); var leadSource = $("#editleadSource").val(); var leadID = $("#editBtn").val(); $.ajax({ url: "/crmData/" + leadID, type: "put", contentType: "application/json", data: JSON.stringify({ "First_Name": firstName, "Last_Name": lastName, "Company": companyName, "Email": email, "State": state, "Phone": phone, "Lead_Source": leadSource }), success: function (data) { debugger; $('#editForm').modal('toggle'); $("#myModalLabel").html("Success"); $("#message").html("Lead Edited Successfully"); $('#myModal').modal('show'); setTimeout(function () { location.reload(); }, 3000); }, error: function (error) { $('#leads').trigger("reset"); $("#myModalLabel").html("Failure"); $("#message").html("Please try again after Sometime"); $("#loader").hide(); $('#myModal').modal('show'); } }); } function getRequiredData(data) { var i; var resp = []; for (i = 0; i &lt; data.length; i++) { var gulp = { "First Name": data[i].First_Name, "Last Name": data[i].Last_Name, "Phone": data[i].Phone, "Email": data[i].Email, "Company": data[i].Company, "Edit": '&lt;center&gt;&lt;a href=&quot;javascript:showEditPopup(\'' + data[i].id + '\')&quot;&gt;&#9998;︎&lt;/a&gt;&lt;/center&gt;', "Delete": '&lt;center&gt;&lt;a href=&quot;javascript:showDeletePopup(\'' + data[i].id + '\')&quot;&gt;&#128465;︎&lt;/a&gt;&lt;/center&gt;' } resp.push(gulp); } console.log(resp); return resp; } function renderTable(respData) { var col = []; for (var i = 0; i &lt; respData.length; i++) { for (var key in respData[i]) { if (col.indexOf(key) === -1) { col.push(key); } } } var table = document.createElement("table"); table.id = "dataTable"; var tr = table.insertRow(-1); for (var i = 0; i &lt; col.length; i++) { var th = document.createElement("th"); th.innerHTML = col[i]; tr.appendChild(th); } for (var i = 0; i &lt; respData.length; i++) { tr = table.insertRow(-1); for (var j = 0; j &lt; col.length; j++) { var tabCell = tr.insertCell(-1); tabCell.innerHTML = respData[i][col[j]]; } } var divContainer = document.getElementById("showData"); divContainer.innerHTML = ""; divContainer.appendChild(table); } &lt;?xml version="1.0" encoding="UTF-8"?&gt; &lt;project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd"&gt; &lt;modelVersion&gt;4.0.0&lt;/modelVersion&gt; &lt;parent&gt; &lt;groupId&gt;org.springframework.boot&lt;/groupId&gt; &lt;artifactId&gt;spring-boot-starter-parent&lt;/artifactId&gt; &lt;version&gt;3.2.12-SNAPSHOT&lt;/version&gt; &lt;relativePath/&gt; &lt;!-- lookup parent from repository --&gt; &lt;/parent&gt; &lt;groupId&gt;com.catalyst.appsail&lt;/groupId&gt; &lt;artifactId&gt;leadmanager&lt;/artifactId&gt; &lt;version&gt;0.0.1-SNAPSHOT&lt;/version&gt; &lt;name&gt;leadmanager&lt;/name&gt; &lt;description&gt;Leadmanager Tutorial&lt;/description&gt; &lt;url/&gt; &lt;licenses&gt; &lt;license/&gt; &lt;/licenses&gt; &lt;developers&gt; &lt;developer/&gt; &lt;/developers&gt; &lt;scm&gt; &lt;connection/&gt; &lt;developerConnection/&gt; &lt;tag/&gt; &lt;url/&gt; &lt;/scm&gt; &lt;properties&gt; &lt;java.version&gt;17&lt;/java.version&gt; &lt;/properties&gt; &lt;dependencies&gt; &lt;dependency&gt; &lt;groupId&gt;org.springframework.boot&lt;/groupId&gt; &lt;artifactId&gt;spring-boot-starter-web&lt;/artifactId&gt; &lt;/dependency&gt; &lt;dependency&gt; &lt;groupId&gt;org.springframework.boot&lt;/groupId&gt; &lt;artifactId&gt;spring-boot-starter-test&lt;/artifactId&gt; &lt;scope&gt;test&lt;/scope&gt; &lt;/dependency&gt; &lt;dependency&gt; &lt;groupId&gt;com.zoho.catalyst&lt;/groupId&gt; &lt;artifactId&gt;java-sdk&lt;/artifactId&gt; &lt;version&gt;2.0.0-beta04&lt;/version&gt; &lt;/dependency&gt; &lt;dependency&gt; &lt;groupId&gt;com.squareup.okhttp3&lt;/groupId&gt; &lt;artifactId&gt;okhttp&lt;/artifactId&gt; &lt;version&gt;3.9.0&lt;/version&gt; &lt;scope&gt;compile&lt;/scope&gt; &lt;/dependency&gt; &lt;/dependencies&gt; &lt;build&gt; &lt;plugins&gt; &lt;plugin&gt; &lt;groupId&gt;org.springframework.boot&lt;/groupId&gt; &lt;artifactId&gt;spring-boot-maven-plugin&lt;/artifactId&gt; &lt;/plugin&gt; &lt;/plugins&gt; &lt;/build&gt; &lt;repositories&gt; &lt;repository&gt; &lt;id&gt;spring-snapshots&lt;/id&gt; &lt;name&gt;Spring Snapshots&lt;/name&gt; &lt;url&gt;https://repo.spring.io/snapshot&lt;/url&gt; &lt;releases&gt; &lt;enabled&gt;false&lt;/enabled&gt; &lt;/releases&gt; &lt;/repository&gt; &lt;repository&gt; &lt;id&gt;java-sdk&lt;/id&gt; &lt;url&gt;https://maven.zohodl.com&lt;/url&gt; &lt;/repository&gt; &lt;/repositories&gt; &lt;pluginRepositories&gt; &lt;pluginRepository&gt; &lt;id&gt;spring-snapshots&lt;/id&gt; &lt;name&gt;Spring Snapshots&lt;/name&gt; &lt;url&gt;https://repo.spring.io/snapshot&lt;/url&gt; &lt;releases&gt; &lt;enabled&gt;false&lt;/enabled&gt; &lt;/releases&gt; &lt;/pluginRepository&gt; &lt;/pluginRepositories&gt; &lt;/project&gt; Adicionalmente, también necesitarás actualizar el archivo **app-config.json**. { "command": "java -jar leadmanager-0.0.1-SNAPSHOT.jar", "build_path": "./target", "stack": "java17", "env_variables": {}, "memory": 256, "scripts": { "preserve": "./mvnw clean package", "predeploy": "./mvnw clean package" }, "raw": {}, "platform": "javase", "catalyst_auth": true, "login_redirect": "/index.html" } <!-- Nota: Asegúrate de proporcionar el valor correcto para la clave buildpath. --> Ahora repasemos la lógica y funcionalidad del código de la aplicación. * El archivo login.html en el componente cliente habilita el inicio de sesión con Catalyst Embedded Authentication, permitiéndote iniciar sesión usando el inicio de sesión social de Zoho. * El archivo index.html contiene el código para el front-end del cliente. Define una función navigate() que habilita la conexión a la cuenta de CRM pasando la información de autorización requerida como el Client ID y el scope. * La lógica del backend de la aplicación define las siguientes APIs que realizan diversas acciones: - **/generateToken**: Obtiene el *Refresh Token* llamando a la función getRefreshToken(), y lo inserta junto con el userID del usuario actual en la tabla Token en el *Data Store*. Luego redirige a la página index del cliente. - **/getUserDetails**: Obtiene los detalles del usuario llamando a la función getUserDetails(). Si no hay un registro en la tabla, se envía una respuesta JSON con solo el userID. Si el registro existe en la tabla, se envía junto con el userID. - **/crmData**: Esta ruta define la ruta de todos los leads en el módulo de Leads. La función Node ejecuta las operaciones HTTP GET y POST para obtener todos los leads o crear un nuevo lead usando esta ruta, respectivamente. - **/crmData/:id**: Esta ruta define la ruta de un lead en particular en el módulo de Leads. El id representa el ID único del lead en CRM. La función ejecuta las operaciones HTTP PUT y DELETE para editar o eliminar un lead, respectivamente, usando esta ruta. * La lógica del backend se implementa usando las siguientes funciones que son llamadas por las APIs: - **getRefreshToken()**: Obtiene el *Refresh Token* pasando el Client ID, Client Secret, *Redirect URI* y otros valores requeridos como parámetros de cadena de consulta. - **getAccessToken()**: Obtiene el *Access Token* pasando el *Refresh Token* consultado de la tabla Token usando ZCQL, y otros parámetros requeridos. El Access Token se obtiene cada vez que se necesita realizar una operación en el módulo de CRM, como agregar un lead o editar un lead. - **getResponse()**: Pasa el *Access Token* obtenido para conseguir la autorización necesaria para realizar cada acción en el módulo de CRM. Esta función se llama con cada API /crmData y /crmData/:id para autorizar la solicitud. - **getUserDetails()**: Obtiene el registro de la tabla *Token* que contiene el *Refresh Token*, pasando el userID. * **main.js**: Es la función JavaScript en el componente cliente que analiza las respuestas JSON obtenidas de la función y las renderiza en la página index.html. Esta función define las acciones para todos los elementos de la interfaz de usuario en la aplicación cliente. Por ejemplo, getLeads() obtiene todos los leads de la respuesta de la función y los renderiza en el cliente, y showEditPopup() define las acciones para editar un lead. -------------------------------------------------------------------------------- title: "Probar la aplicación" description: "Construye una aplicación Lead Manager y alójala en AppSail. La aplicación se conecta a tu cuenta de Zoho CRM usando conectores de Catalyst, y te permite ver, crear, actualizar o eliminar leads desde el módulo de Leads en tu CRM." last_updated: "2026-10-08T06:48:03.655Z" source: "https://docs.catalyst.zoho.com/es/tutorials/leadmanager-appsail/springboot/test-app/" service: "All Services" related: - CLI Help Documentation (/es/cli/v1/cli-command-reference/) - Serve Resources (/es/cli/v1/serve-resources/introduction/) -------------------------------------------------------------------------------- # Probar la aplicación Antes de desplegar la aplicación en la consola remota, puedes probar la aplicación en un servidor local y verificar si todo funciona correctamente usando la CLI de Catalyst. Para servir el proyecto de Catalyst localmente, ejecuta el siguiente comando desde el directorio de tu proyecto: catalyst serve La aplicación Lead Manager ahora se servirá en el puerto 3000 por defecto. Se mostrarán las URLs de los endpoints locales de los componentes. Info: Cada vez que accedas a la página principal o cualquiera de las subpáginas de tu cliente o la función, la CLI mostrará un log en vivo de la URL accedida, junto con el método de solicitud HTTP. Nota: Asegúrate de haber proporcionado las Authorized Redirect URIs requeridas cuando registraste el cliente en el Paso 4. <br /> Ahora puedes abrir la aplicación en un navegador usando la URL local del cliente que se muestra en la CLI. Inicialmente serás redirigido a la página de inicio de sesión. Si configuras una acción de registro por tu cuenta, puedes registrarte primero, luego iniciar sesión en la aplicación. Alternativamente, también puedes iniciar sesión usando el *inicio de sesión social de Zoho*. <br /> Serás redirigido a la página de permisos. Acepta los permisos solicitados por la aplicación para acceder a los detalles de tu cuenta de Zoho. Luego serás redirigido de vuelta a la aplicación. Haz clic en el ícono de **Zoho CRM** en esta página para conectarte a Zoho CRM. <br /> Ahora debes **elegir la cuenta de CRM** con la que deseas conectar la aplicación Lead Manager, luego haz clic en **Submit**. <br /> Se listarán todas tus cuentas existentes de desarrollador, sandbox y producción. Haz clic en **Accept** para permitir que la aplicación *Lead Manager* acceda a tus módulos de Zoho CRM. <br /> Serás redirigido de vuelta a la aplicación. Ahora puedes crear y gestionar leads en tu cuenta de Zoho CRM configurada directamente desde esta aplicación. Para agregar un lead, ingresa los detalles del lead en la sección *Add a Lead* y haz clic en **Add Lead**. <br /> Un mensaje emergente de confirmación mostrará el estado cada vez que agregues, edites o elimines un lead. <br /> Puedes hacer clic en la pestaña **Manage Leads** para ver todos tus leads del módulo *Leads*. Puedes **editar** o **eliminar** cualquiera de ellos haciendo clic en sus respectivos íconos en la tabla. <br /> Puedes actualizar la información de un lead, luego haz clic en **Edit**. <br /> Si haces clic en el ícono de **eliminar**, debes confirmar la acción en el mensaje emergente de confirmación. <br /> También puedes verificar los valores del *Refresh Token* y userID almacenados en el **Data Store** desde tu consola de Catalyst. Navega a la sección **Data View** de la tabla *Token* para ver el registro que fue agregado. <br /> Si eliminas esta entrada, tendrás que autenticar tus credenciales en la aplicación cliente y establecer una conexión con tu cuenta de CRM nuevamente. Puedes cerrar sesión de la aplicación haciendo clic en **Logout**. Puedes salir de la sesión de serve en tu terminal ejecutando el comando para terminar un proceso en ejecución, según tu sistema operativo. Si esta configuración funciona correctamente, podemos desplegar la aplicación a producción. -------------------------------------------------------------------------------- title: "Desplegar la aplicación" description: "Construye una aplicación Lead Manager y alójala en AppSail. La aplicación se conecta a tu cuenta de Zoho CRM usando conectores de Catalyst, y te permite ver, crear, actualizar o eliminar leads desde el módulo de Leads en tu CRM." last_updated: "2026-10-08T06:48:03.656Z" source: "https://docs.catalyst.zoho.com/es/tutorials/leadmanager-appsail/springboot/deploy-app/" service: "All Services" related: - CLI Help Documentation (/es/cli/v1/cli-command-reference/) - Deploy Resources (/es/cli/v1/deploy-resources/introduction/) - AppSail Help Documentation (/es/serverless/help/appsail/introduction/) -------------------------------------------------------------------------------- # Desplegar la aplicación Ahora puedes desplegar la aplicación en la consola remota. Nota: Como ya habías iniciado sesión en la aplicación Lead Manager desde el servidor local, ya se habría generado un Refresh Token. Este token continuará autenticando tu acceso. Para desplegar tu proyecto de Catalyst desde la CLI, ejecuta el siguiente comando en tu terminal desde el directorio de tu proyecto: catalyst deploy La función se despliega primero, seguida del componente cliente. Se mostrarán las URLs de la aplicación de los componentes. <br /> La aplicación ahora está desplegada en la consola de Catalyst. Ahora, si nuevamente navegas al componente AppSail ubicado en la sección *Serverless*, podrás obtener la URL de invocación de la aplicación. <br /> En esta sección también tendrás acceso a un dashboard en vivo que indica el número de instancias que el servicio de la aplicación Lead Manager ha generado en cualquier momento dado. Usando esta sección también podrás configurar y gestionar el servicio AppSail. Puedes encontrar más información sobre esto aquí. Puedes usar la URL de invocación en un navegador para acceder a la aplicación desplegada. La aplicación Lead Manager ahora puede ser accedida desde su URL de aplicación web. <br />