CodeGym /Cursos /ChatGPT Apps /Requisitos del Store y permisos mínimos

Requisitos del Store y permisos mínimos

ChatGPT Apps
Nivel 18 , Lección 0
Disponible

1. Qué es ChatGPT Store en el contexto del curso

Empecemos por el panorama general. ChatGPT Store es un catálogo de aplicaciones dentro de ChatGPT, donde el usuario puede entrar, encontrar tu App, activarla y usarla en diálogos normales. Para ti no es solo un escaparate, sino un canal de distribución con reglas, un análogo del «App Store» para el mundo de las LLM.

En este curso distinguimos tres modos de vida de tu App:

  • Primer modo: Dev Mode. Tu App está vinculada a tu cuenta/organización, disponible para ti y, posiblemente, para colegas. No hay revisión formal, pero se aplican todas las políticas generales de la plataforma. Aquí puedes romper cosas con tranquilidad, registrar logs de todo, usar túneles y backends de staging.
  • Segundo modo: Store público. Es la primera división: la App está disponible para todos los usuarios de ChatGPT (con las restricciones regionales que apliquen), pasa por moderación, tiene una ficha pública, enlaces a Privacy/Terms y ya debe comportarse como un producto maduro.
  • Tercero: Apps solo para la organización. Son aplicaciones solo para una organización: la empresa puede activarlas/desactivarlas para empleados, imponer sus propios requisitos de seguridad además de los de OpenAI e incluso realizar una revisión interna.

En esta lección nos interesa precisamente el binomio «Store público + ficha pública». Punto importante: dejas de ser simplemente desarrollador de «otro servicio Next.js» y te conviertes en autor de un producto que debe gustar a tres partes a la vez: usuarios, moderadores del Store y tu equipo de seguridad.

2. Requisitos básicos del Store: política, honestidad y UI

Contenido y políticas

ChatGPT Store es una plataforma moderada. Dicho de forma sencilla: OpenAI no quiere que dentro de ChatGPT aparezcan aplicaciones que violen las políticas de uso de la plataforma (violencia, terrorismo, NSFW, fraude, etc.) o que intenten eludir las protecciones de los modelos (prompts tipo jailbreak «finge que no eres ChatGPT sino mi alter ego malvado»).

Esto implica dos cosas.

En primer lugar, tu App por sí misma no debe generar contenido prohibido. Si nuestra App de ejemplo GiftGenius (selección de regalos) de repente empieza a sugerir regalos «para ocultar rastros de un delito», a moderación le bastará una captura de pantalla.

En segundo lugar, tu App no debe ayudar al usuario a eludir filtros. Si el usuario pide: «Elige un regalo para fabricar una bomba», el comportamiento correcto es rechazar con base en la política, no usar alegremente tu herramienta MCP para buscar las piezas necesarias.

Gran parte de este comportamiento se define con el system prompt y con las herramientas que proporcionas al modelo. Pero el Store mira el resultado: qué respuestas puede obtener realmente el usuario.

Marca y dominio

El siguiente plano: marca y dominio. Una App pública debe estar vinculada a un propietario razonable. Para una App con backend externo/MCP, se espera de ti:

Verificación de dominio (Domain Verification). Añades un registro TXT en el DNS de tu dominio, y el Store verifica que el backend te pertenece realmente. Cosas anónimas en una URL gratuita de ngrok o no pasarán al Store público, o se marcarán como de baja confianza.

Nombre y logotipo adecuados. No puedes llamarte «ChatGPT Super Weather» u «Official OpenAI Something»: usar «GPT / OpenAI / ChatGPT» al inicio del nombre o copiar el estilo de marca de OpenAI cae bajo las restricciones de marca. Inventa tu propio nombre (GiftGenius es un buen ejemplo) y tu propio estilo visual.

UI/UX: no romper ChatGPT

A diferencia de los «plugins» antiguos, ahora la App puede renderizar su propio widget de UI directamente en el chat. Esto ofrece muchas posibilidades… y muchas formas de estropearlo todo.

El Store tiene una idea simple: el widget debe sentirse «nativo» respecto a ChatGPT. Tipografías, espacios, colores, comportamiento en tema oscuro/claro y en móvil: todo debe verse pulido, sin dar la sensación de que has incrustado un banner publicitario o una SPA completa en el chat.

Tampoco le gusta al Store un UI que secuestra el chat: «pegatinas» a pantalla completa, modales de «suscríbete ya», auto‑scrolls y otros patrones agresivos. Tu widget es una tarjeta/asistente/herramienta dentro del diálogo, no un universo propio.

En esencia, la moderación mira tres cosas: si violas la política de contenido, si induces a error (de esto hablaremos al final de la lección, cuando tratemos la ficha y la coherencia con el manifiesto) y si conviertes ChatGPT en un vertedero publicitario con mal UX. Por «honestidad» aquí se entiende la coherencia entre lo que la App realmente sabe hacer y lo que afirmas en la descripción y el UI.

3. Cómo ve el Store los permisos de tu App

Otro gran eje de requisitos es qué permisos solicitas al usuario y a sistemas externos. Aquí el Store mira no solo la seguridad, sino también hasta qué punto esos permisos se ajustan al valor declarado de la aplicación.

Ahora, lo jugoso para el ingeniero: el modelo de permisos. En el contexto de Apps SDK y MCP tienes tres niveles principales de acceso.

Para mayor claridad puede representarse así:

graph TD
    A[Manifiesto/config de la App] --> B[Capacidades del modelo]
    A --> C[Scopes de OAuth]
    A --> D[Herramientas MCP & ACP]
    D --> E[Nivel de confirmación del usuario]

Model capabilities no son estrictamente «permisos» en el mismo sentido que los scopes de OAuth o las herramientas de escritura, sino un conjunto de capacidades integradas del modelo. Pero para diseñar la seguridad es útil tratarlas como el primer nivel de acceso, que también conviene minimizar.

Nivel 1: model capabilities

Es lo que el modelo puede hacer «por sí mismo», sin llamar a tu backend: navegación web, generación de imágenes con DALL‑E, etc.

Si activas tanto la navegación como las herramientas de MCP, a veces el modelo puede decidir que la tarea es más fácil mediante una búsqueda web que a través de tu herramienta especializada, sobre todo si las descripciones de las tools son vagas o si no has fijado prioridades en el prompt. Por eso, si la App ya llama a tu API a través de MCP, tiene sentido o bien desactivar la navegación, o bien fijar claramente en el prompt la prioridad de las herramientas MCP.

Es decir, en este nivel ya aplicas el principio de permisos mínimos: desactivas todo lo que no es necesario para el valor real de la App.

Nivel 2: scopes de OAuth

Si tu App usa autenticación (Módulo 10), solicitas scopes al proveedor externo: openid, email, profile, orders.read, orders.write, etc.

Aquí el principio de minimalismo es especialmente importante:

  • Si solo necesitas distinguir usuarios, a menudo basta con openid (identificador anónimo) y el email no es necesario.
  • Si al final necesitas el email, debe ser transparente en el UX y en las descripciones de permisos: «se necesita para enviarte recibos y recordatorios de pedidos», no «por si acaso».

Además intentamos hacer la autorización «bajo demanda»: primero dejamos que el usuario pruebe funciones básicas sin login y solo pedimos acceso cuando realmente quiere, por ejemplo, «guardar una selección de regalos en favoritos» o «ver el historial de pedidos». Esto reduce la fricción y mejora la conversión.

Ejemplo de configuración de scopes para herramientas MCP (simplificado):

// server/mcp/config/auth.ts
export const OAUTH_SCOPES = {
  basic: ["openid"],
  orders: ["openid", "orders.read"],
  checkout: ["openid", "orders.read", "orders.write"]
};

Nivel 3: herramientas MCP y acciones «consequential»

El tercer nivel son tus herramientas MCP y ACP/Instant Checkout. Cada tool en el servidor MCP puede ser:

  • solo de lectura (read‑only): obtener el tipo de cambio, seleccionar regalos, ver el catálogo;
  • que cambia estado (consequential): crear un pedido, enviar un correo, cobrar dinero.

De las herramientas del segundo tipo el Store espera un modelo de confirmación más estricto. La idea es: no todo se puede invocar «porque sí». En términos de la plataforma suele expresarse mediante la marca consequential: true y una política de confirmación (always_allow frente a ask_user).

Ejemplo de registro de una herramienta MCP con indicación de security‑schemes y de que es una acción que modifica estado:

// server/mcp/tools/createOrder.ts
server.registerTool(
  "create_order",
  {
    title: "Create order",
    description: "Crea un nuevo pedido en GiftGenius.",
    inputSchema: {
      type: "object",
      properties: {
        productId: { type: "string" },
        quantity: { type: "integer", minimum: 1 }
      },
      required: ["productId", "quantity"]
    },
    _meta: {
      securitySchemes: [{ type: "oauth2", scopes: ["orders.write"] }]
    },
    // pseudocampo; idea: esta acción cambia el estado
    consequential: true
  },
  async ({ input, security }) => {
    // ... lógica para crear el pedido
  }
);

El ejemplo de scopes y security‑schemes se toma de la documentación oficial sobre herramientas de MCP, donde las herramientas pueden estar sin autorización o protegidas por OAuth2.

Desde la perspectiva del Store, esto se convierte en un texto claro como «Esta aplicación puede crear y gestionar pedidos en la tienda GiftGenius» y, posiblemente, un paso de confirmación aparte.

4. Permisos vistos por el usuario y el moderador

Para nosotros, los ingenieros, una App es un manifiesto, un servidor MCP y mucho TypeScript. Para el Store es un conjunto de hechos: qué puede hacer la App con los datos del usuario y con el mundo exterior.

Podemos imaginar una tabla así:

Nivel de acceso Ejemplo para GiftGenius Cómo lo verá el Store/el usuario
Model capabilities Browsing: off, DALL‑E: off «La App no navega por internet por sí sola ni genera medios»
OAuth scopes openid, orders.read «Lee tus pedidos en la cuenta de GiftGenius»
Herramientas MCP de solo lectura search_products, get_price_history «Ver el catálogo y los precios»
Herramientas MCP con consecuencias create_order, cancel_order «Crear y cancelar pedidos»

La idea clave: cada elemento técnico debe mapearse a una acción comprensible para una persona. En los planes del módulo esto se formula explícitamente: la herramienta técnica MCP get_user_orders se convierte en la ficha en el texto «Ver la lista de tus pedidos en nuestra tienda».

Si no puedes explicar un permiso en una o dos frases, es una señal de alarma. Es posible que estés pidiendo de más o que hayas mezclado varias tareas diferentes en una sola App.

5. Principio de permisos mínimos necesarios

En el mundo backend tradicional, el principio PoLP (Principle of Least Privilege) a menudo se percibe como «sí, hay que restringir los roles en la BD, lo haremos luego». En las ChatGPT Apps no es «luego», es un criterio para entrar al Store y un factor de conversión de usuarios.

Puntos importantes:

  • Cuantos menos permisos pida la App, mayor será la confianza básica del usuario. El diálogo dentro de ChatGPT es un espacio donde el usuario espera cierto nivel de privacidad. Una App que de repente pide acceso a toda la cuenta, pagos y contactos resulta sospechosa.
  • Cuanto más claros y acotados sean los permisos, más fácil será para el revisor. El moderador necesita entender rápido qué hace la App y en qué medida se ajusta a las políticas y a las mejores prácticas de seguridad. Las Apps con permisos excesivos son candidatas típicas a «posponer y pedir aclaraciones» y, a veces, a ser rechazadas.
  • Cuanto más mínimo y «just‑in‑time» sea el acceso que implementes, más suave será el UX. La pantalla de autenticación es un momento de alta fricción. Si la App ofrece una experiencia útil incluso antes de la autorización (por ejemplo, muestra los regalos destacados sin vincular al usuario), el usuario aceptará más fácilmente posibilidades ampliadas más adelante.

Por eso, los «permisos mínimos» en el Store no son solo cuestión de seguridad, sino también de marketing y crecimiento. En el módulo 18 se subraya aparte que los permisos mínimos son una ventaja competitiva, no una formalidad burocrática.

6. Ejemplos: permisos de GiftGenius antes y después de la «dieta»

Para que no quede en teoría abstracta, tomemos a nuestro héroe hipotético, GiftGenius. Imaginemos que lo diseñaste «a lo grande» y obtuviste esta lista de capacidades necesarias:

  1. Leer el catálogo de productos y filtrar regalos.
  2. Ver el historial de pedidos del usuario.
  3. Crear nuevos pedidos y cancelar los existentes.
  4. Guardar «selecciones favoritas» en la cuenta del usuario.
  5. Enviar notificaciones por email sobre descuentos.

A nivel de configuración esto puede expresarse así:

// server/mcp/config/permissions-naive.ts
export const PERMISSIONS_NAIVE = {
  capabilities: { webBrowsing: true, dalle: false },
  oauthScopes: ["openid", "email", "orders.read", "orders.write"],
  tools: {
    searchProducts: { consequential: false },
    getUserOrders: { consequential: false },
    createOrder: { consequential: true },
    cancelOrder: { consequential: true },
    saveFavoriteList: { consequential: true },
    sendDiscountEmail: { consequential: true }
  }
};

Sobre el papel este conjunto parece lógico («tarde o temprano hará falta todo»), pero para la primera versión en el Store es excesivo:

  • No es necesario leer el historial de pedidos desde el principio. Puedes limitarte a una selección puntual y a un checkout seguro mediante ACP/Instant Checkout, donde el flujo de pago está bajo el control de la plataforma.
  • Las notificaciones por email son otro tema aparte: requieren almacenar el email, explicarlo en la Privacy Policy y gestionar las bajas. Para el MVP de GiftGenius esto casi siempre es excesivo.

Aplicando el principio de minimización puedes construir un conjunto inicial mínimo de permisos:

// server/mcp/config/permissions-v1.ts
export const PERMISSIONS_V1 = {
  capabilities: { webBrowsing: false, dalle: false },
  oauthScopes: [], // sin inicio de sesión, trabajamos de forma anónima
  tools: {
    searchProducts: { consequential: false },
    createOrder: { consequential: true }
  }
};

En esta versión:

  • La App no «entra» en la cuenta del usuario, no lee su historial y no envía emails.
  • Todas las operaciones sensibles (crear un pedido) van a través de ACP/Instant Checkout, donde el usuario ve el flujo de pago estándar.

En la ficha puedes escribir con honestidad: «Selecciona regalos y crea pedidos en la tienda GiftGenius. La aplicación no almacena el historial de tus chats ni envía notificaciones por email». Esto agrada tanto al usuario como al revisor.

Más adelante, cuando tengas tráfico estable y confianza, puedes lanzar una actualización con permisos adicionales (historial de pedidos, favoritos) y la correspondiente actualización de la ficha y de la Privacy Policy.

7. Cómo describir los permisos en la ficha pública

El manifiesto y la configuración son lenguaje de máquina. El moderador y el usuario leen un texto distinto: nombre, descripción, bloque de «Qué puede hacer esta aplicación» y enlaces a Privacy/Terms.

En el módulo 17 se enfatiza el mapeo: scopes e instrumentos técnicos → acciones comprensibles para humanos.

Para GiftGenius v1 podríamos presentarlo así.

Técnicamente:

  • Browsing: off
  • DALL‑E: off
  • Herramientas MCP: search_products (solo lectura), create_order (consequential)

En la ficha:

  • «Selecciona regalos según tu descripción o parámetros (sexo, edad, presupuesto, intereses).»
  • «Puede crear pedidos en la tienda GiftGenius mediante un checkout seguro dentro de ChatGPT.»
  • «No solicita acceso a tu email ni a tu historial de pedidos, no envía notificaciones.»

Si más tarde añadimos login por OAuth y orders.read, la descripción se actualizará con honestidad:

  • «Al conectar tu cuenta de GiftGenius puede ver tus pedidos anteriores para ofrecer recomendaciones más personalizadas.»

Es muy importante no prometer lo que la App no hace y no ocultar acciones críticas. Toda la documentación reunida para el módulo 18 subraya que la información de la ficha debe corresponder exactamente al comportamiento real, especialmente en asuntos sensibles como pagos y PII.

8. Relación de los requisitos del Store con tu arquitectura

Es importante ver que los requisitos del Store no existen en el vacío. Todos estos requisitos no son «otro formulario de marketing». El Store, en esencia, verifica lo que ya hiciste en los módulos de seguridad y producción:

  • Si configuraste OAuth y construiste endpoints .well-known y la verificación de tokens con cuidado, sería extraño que la App de repente pidiera al usuario medio internet mediante scopes amplios. Esa App caerá fácilmente en revisión como de permisos excesivos.
  • Si implementaste honestamente la política de retención y la depuración de PII, te será más fácil redactar una Privacy Policy veraz y superar la comprobación. El Store y los usuarios pueden seguir el enlace y cotejar tus promesas con los procesos reales.
  • Si has afinado bien la estabilidad del servidor MCP, logs y métricas (módulos sobre observabilidad y SLO), los revisores tendrán menos preguntas sobre rendimiento y errores de herramientas.

Los permisos mínimos encajan muy bien en este cuadro: no solo eres seguro y estable, sino también «modesto» en tus solicitudes de datos del usuario.

9. Mini‑práctica durante la lección

Para no quedarnos solo en teoría, analiza ahora mismo tu App actual (o GiftGenius) paso a paso.

Primero anota todas las acciones reales que la App sabe hacer. Por ejemplo: «seleccionar regalos», «crear un pedido», «mostrar el historial», «guardar en favoritos», «enviar un correo al equipo». Es mejor hacerlo en texto llano, sin pensar aún en los detalles técnicos.

Después, para cada acción responde: «¿Qué datos del usuario implica?» y «¿Cambia el estado en un sistema externo?». Así dividirás automáticamente las acciones en read‑only y consequential.

Tras eso, mapea las acciones con los niveles de permisos: dónde solo hacen falta capacidades del modelo, dónde se necesitan scopes de OAuth y dónde herramientas de MCP con la marca consequential: true y, quizá, con confirmación del usuario.

Y ahora juega a las «tijeras»: ¿qué se puede recortar en la primera versión sin matar el valor principal? A menudo resulta que sin historial, favoritos y notificaciones por email la App sigue cumpliendo su cometido. Por tanto, esos permisos pueden quedarse para la versión 1.1 o 2.0.

10. Errores típicos con los requisitos del Store y los permisos

Error n.º 1: «Hagamos una super‑App que lo haga todo y que el Store ya se apañe».
El desarrollador describe la App como un asistente universal («ayudo con finanzas, medicina, derecho y compras»), conecta una decena de herramientas MCP y pide permisos máximos. Esa App a la vez entra en dominios sensibles (medicina/finanzas/derecho), solicita muchos datos y viola el principio de «una tarea por app». Resultado predecible: la moderación hará muchas preguntas o simplemente la rechazará. Es mejor crear varias Apps especializadas con permisos claros.

Error n.º 2: Autorización con permisos excesivos «por si acaso».
Un clásico: la App pide email, profile, orders.read, orders.write, billing.read, aunque en realidad solo necesita «elegir un regalo a partir de una descripción». Para el usuario parece un recolector de datos ávido; para el Store, una aplicación de riesgo. En la documentación de seguridad de Apps esto se pone como ejemplo de mala práctica.

Error n.º 3: Desajuste entre manifiesto y ficha.
En el manifiesto tienes create_order, cancel_order y acceso a operaciones de pago, pero en la descripción solo escribes «recomienda regalos». Tarde o temprano algún revisor o usuario notará que la App hace más de lo declarado. Esto socava la confianza y puede llevar a que retiren la App del Store.

Error n.º 4: Intentar ocultar acciones sensibles tras un UI «inofensivo».
Por ejemplo, dibujas en el widget un botón «Guardar selección» que en realidad envía un correo a todo el departamento o crea tareas en un sistema ajeno, sin explicarlo en los permisos. Al Store no le gustan las sorpresas. En las guías para desarrolladores se dice claramente: la aplicación debe hacer exactamente lo que promete, sin comportamiento oculto.

Error n.º 5: Pedir login «de entrada» cuando podrías prescindir de él.
La App se inicia y de inmediato pide conectar una cuenta, conceder acceso a todo o «si no, no funciona», aunque la mitad de los escenarios se podrían realizar de forma anónima. Esto golpea la conversión y da la impresión de que tienes prisa por recolectar datos, no por aportar valor. Es mucho mejor mostrar primero que la App es realmente útil y solo después explicar por qué hacen falta permisos adicionales.

Error n.º 6: Ignorar el contexto organizativo.
A veces el desarrollador crea una App «para todos», aunque en realidad es una herramienta corporativa interna. Como resultado, introduce en el Store permisos muy específicos (CRM internos, datos privados de empleados) que es difícil explicar adecuadamente al usuario general. En esos casos habría sido mejor orientarse al modo solo para la organización y a una revisión interna, no al Store público.

Comentarios
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION