Administrar pestañas

Compila tu primer administrador de pestañas.

Descripción general

En este instructivo, se compila un administrador de pestañas para organizar las pestañas de documentación de tu extensión de Chrome y Chrome Web Store.

Ventana emergente de la extensión Tabs Manager
Extensión Tabs Manager

En esta guía, explicaremos cómo hacer lo siguiente:

  • Crea una ventana emergente de extensión con la API de Action.
  • Realiza consultas sobre pestañas específicas con la API de Tabs.
  • Preserva la privacidad del usuario a través de permisos de host limitados.
  • Cambia el enfoque de la pestaña.
  • Mueve las pestañas a la misma ventana y agrúpalas.
  • Cambia el nombre de los grupos de pestañas con la API de TabGroups.

Antes de comenzar

En esta guía, se da por sentado que tienes experiencia básica en desarrollo web. Te recomendamos que consultes Hello World para obtener una introducción al flujo de trabajo de desarrollo de extensiones.

Compila la extensión

Para comenzar, crea un directorio nuevo llamado tabs-manager para alojar los archivos de la extensión. Si lo prefieres, puedes descargar el código fuente completo en GitHub.

Paso 1: Agrega los datos y los íconos de la extensión

Crea un archivo llamado manifest.json y agrega el siguiente código:

{
  "manifest_version": 3,
  "name": "Tab Manager for Chrome Dev Docs",
  "version": "1.0",
  "icons": {
    "16": "images/icon-16.png",
    "32": "images/icon-32.png",
    "48": "images/icon-48.png",
    "128": "images/icon-128.png"
  }
}

Para obtener más información sobre estas claves del manifiesto, consulta el instructivo sobre el tiempo de lectura, en el que se explican los metadatos y los íconos de la extensión con más detalle.

Crea una carpeta images y, luego, descarga los íconos en ella.

Paso 2: Crea y diseña la ventana emergente

La API de Action controla la acción de la extensión (ícono de la barra de herramientas). Cuando el usuario hace clic en la acción de la extensión, se ejecutará código o se abrirá una ventana emergente, como en este caso. Comienza por declarar la ventana emergente en manifest.json:

{
  "action": {
    "default_popup": "popup.html"
  }
}

Una ventana emergente es similar a una página web, con una excepción: no puede ejecutar JavaScript intercalado. Crea un archivo popup.html y agrega el siguiente código:

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <link rel="stylesheet" href="./popup.css" />
  </head>
  <body>
    <template id="li_template">
      <li>
        <a>
          <h3 class="title">Tab Title</h3>
          <p class="pathname">Tab Pathname</p>
        </a>
      </li>
    </template>

    <h1>Google Dev Docs</h1>
    <button>Group Tabs</button>
    <ul></ul>

    <script src="./popup.js" type="module"></script>
  </body>
</html>

A continuación, le aplicarás estilo a la ventana emergente. Crea un archivo popup.css y agrega el siguiente código:

body {
  width: 20rem;
}

ul {
  list-style-type: none;
  padding-inline-start: 0;
  margin: 1rem 0;
}

li {
  padding: 0.25rem;
}
li:nth-child(odd) {
  background: #80808030;
}
li:nth-child(even) {
  background: #ffffff;
}

h3,
p {
  margin: 0;
}

Paso 3: Administra las pestañas

La API de Tabs permite que una extensión cree, consulte, modifique y reorganice pestañas en el navegador.

Cómo solicitar un permiso

Muchos métodos de la API de Tabs se pueden usar sin solicitar ningún permiso. Sin embargo, necesitamos acceder a title y URL de las pestañas, y estas propiedades sensibles requieren permiso. Podríamos solicitar el permiso "tabs", pero esto daría acceso a las propiedades sensibles de todas las pestañas. Como solo administramos pestañas de un sitio específico, solicitaremos permisos de host restringidos.

Los permisos de host específicos nos permiten proteger la privacidad del usuario, ya que otorgan permisos elevados a sitios específicos. Esto otorgará acceso a las propiedades title y URL, así como a otras funciones. Agrega el código destacado al archivo manifest.json:

{
  "host_permissions": [
    "https://developer.chrome.com/*"
  ]
}

💡 ¿Cuáles son las principales diferencias entre el permiso de pestañas y los permisos de host?

Tanto el permiso "tabs" como los permisos de organizador tienen desventajas.

El permiso "tabs" otorga a una extensión la capacidad de leer datos sensibles en todas las pestañas. Con el tiempo, esta información podría usarse para recopilar el historial de navegación de un usuario. Por lo tanto, si solicitas este permiso, Chrome mostrará el siguiente mensaje de advertencia durante la instalación:

Cuadro de diálogo de advertencia de permisos de pestañas

Los permisos de host permiten que una extensión lea y consulte las propiedades sensibles de una pestaña coincidente, además de insertar secuencias de comandos en esas pestañas. Los usuarios verán el siguiente mensaje de advertencia durante la instalación:

Cuadro de diálogo de advertencia sobre el permiso de host

Estas advertencias pueden ser alarmantes para los usuarios. Para mejorar la experiencia de incorporación, te recomendamos que implementes permisos opcionales.

Cómo consultar las pestañas

Puedes recuperar las pestañas de URLs específicas con el método tabs.query(). Crea un archivo popup.js y agrega el siguiente código:

const tabs = await chrome.tabs.query({
  url: [
    "https://developer.chrome.com/docs/webstore/*",
    "https://developer.chrome.com/docs/extensions/*",
  ]
});

💡 ¿Puedo usar las APIs de Chrome directamente en la ventana emergente?

Una ventana emergente y otras páginas de extensión pueden llamar a cualquier API de Chrome porque se publican desde el esquema de Chrome. Por ejemplo, chrome-extension://EXTENSION_ID/popup.html.

Cómo enfocarse en una pestaña

Primero, la extensión ordenará alfabéticamente los nombres de las pestañas (los títulos de las páginas HTML incluidas). Luego, cuando se haga clic en un elemento de la lista, se enfocará en esa pestaña con tabs.update() y se traerá la ventana al frente con windows.update(). Agrega el siguiente código al archivo popup.js:

...
const collator = new Intl.Collator();
tabs.sort((a, b) => collator.compare(a.title, b.title));

const template = document.getElementById("li_template");
const elements = new Set();
for (const tab of tabs) {
  const element = template.content.firstElementChild.cloneNode(true);

  const title = tab.title.split("-")[0].trim();
  const pathname = new URL(tab.url).pathname.slice("/docs".length);

  element.querySelector(".title").textContent = title;
  element.querySelector(".pathname").textContent = pathname;
  element.querySelector("a").addEventListener("click", async () => {
    // need to focus window as well as the active tab
    await chrome.tabs.update(tab.id, { active: true });
    await chrome.windows.update(tab.windowId, { focused: true });
  });

  elements.add(element);
}
document.querySelector("ul").append(...elements);
...

💡 JavaScript interesante que se usa en este código

  • El objeto Collator que se usa para ordenar el array de pestañas según el idioma preferido del usuario.
  • La etiqueta de plantilla que se usa para definir un elemento HTML que se puede clonar en lugar de usar document.createElement() para crear cada elemento.
  • El constructor de URLs que se usa para crear y analizar URLs.
  • La sintaxis de propagación que se usa para convertir el conjunto de elementos en argumentos en la llamada append().

Agrupa las pestañas

La API de TabGroups permite que la extensión le asigne un nombre al grupo y elija un color de fondo. Agrega el permiso "tabGroups" al manifiesto agregando el código destacado:

{
  "permissions": [
    "tabGroups"
  ]
}

En popup.js, agrega el siguiente código para crear un botón que agrupe todas las pestañas con tabs.group() y las mueva a la ventana actual.

const button = document.querySelector("button");
button.addEventListener("click", async () => {
  const tabIds = tabs.map(({ id }) => id);
  if (tabIds.length) {
    const group = await chrome.tabs.group({ tabIds });
    await chrome.tabGroups.update(group, { title: "DOCS" });
  }
});

Prueba si funciona

Verifica que la estructura de archivos de tu proyecto coincida con el siguiente árbol de directorios:

Contenido de la carpeta del administrador de pestañas: manifest.json, popup.js, popup.css, popup.html y la carpeta de imágenes.

Carga tu extensión de forma local

Para cargar una extensión sin empaquetar en el modo de desarrollador, sigue los pasos que se indican en Hello World.

Abre algunas páginas de documentación.

Abre los siguientes documentos en ventanas diferentes:

Haz clic en la ventana emergente. Se verá de la siguiente manera:

Ventana emergente de la extensión Tabs Manager
Ventana emergente de la extensión Tabs Manager

Haz clic en el botón "Agrupar pestañas". Se verá de la siguiente manera:

Administrador de pestañas: Pestañas agrupadas
Pestañas agrupadas con la extensión Tabs Manager

🎯 Posibles mejoras

Según lo que aprendiste hoy, intenta implementar alguna de las siguientes acciones:

  • Personaliza la hoja de estilo de la ventana emergente.
  • Cambia el color y el título del grupo de pestañas.
  • Administrar las pestañas de otro sitio de documentación
  • Se agregó compatibilidad para desagrupar las pestañas agrupadas.

¡Sigue creando!

¡Felicitaciones por completar este instructivo 🎉! Sigue desarrollando tus habilidades con otros instructivos de esta serie:

Extensión Qué aprenderás
Tiempo de lectura Insertar un elemento en cada página automáticamente
Modo sin distracciones Ejecutar código en la página actual después de hacer clic en la acción de la extensión

Sigue explorando

Esperamos que hayas disfrutado de la creación de esta extensión de Chrome y que te entusiasme continuar tu recorrido de aprendizaje sobre el desarrollo de Chrome. Te recomendamos la siguiente ruta de aprendizaje: