Una introducción larga y tediosa con un reclamo de megalomanía.
Una vez que descubrí que, como siempre, algo no me convenía mucho en este mundo. Es decir, al ingresar algún tipo de consulta larga en un motor de búsqueda en una computadora de escritorio y luego cambiar a una tableta, no pude recordar el texto de la consulta textualmente para obtener exactamente los mismos resultados. Todo comenzó muy bien. Vi en el motor de búsqueda un enlace a la respuesta a mi pregunta y me di cuenta de que promete una lectura larga. Luego apagué la computadora y me dejé caer en el sofá con la tableta con la idea de que ahora lo volvería a escribir todo en el motor de búsqueda, abriré ese enlace ahora en la tableta y acostado, tranquilo, en una posición más cómoda, lo leeré ... Pero no aquí fue. Algunas discrepancias menores en el texto, y mi enlace ya no está en el motor de búsqueda. Jugar el enlace en sí tampoco es una opción: es demasiado largo. Al pensar en las opciones para el texto de la consulta, estaba casi furioso por romper la tableta. Maldita sea, tuve que levantarme, volver a encender la computadora, iniciar el navegador y profundizar en el historial para encontrar el texto exacto de mi solicitud.

Extensión instalada en Chrome y FirefoxIdea
Pensé, pero sería bueno escribir una extensión de este tipo para el navegador que le permitiera transferir cualquiera de sus pestañas abiertas a través del servidor a cualquier otra computadora y continuar trabajando con ellas allí. Sí, algunos navegadores ya tienen una función en la nube: solo necesita iniciar sesión en ambos dispositivos y ... Pero esa es la trampa. Pero, ¿qué pasa si tengo Chrome en mi computadora y Firefox en mi tableta? Y luego ... Solo inicia sesión, sí. Si aún recordaba mi contraseña de la cuenta de google. Y simplemente no tengo una cuenta en Firefox. Ni siquiera sé si hay alguna cuenta allí? Hay, por supuesto, servicios en la nube de terceros donde puede registrarse y probablemente de alguna manera arrojar el enlace deseado para usted. Pero aún es necesario registrarse allí y memorizar firmemente otra contraseña ... No, esto es completamente poco realista. Al final, puede lanzarse un enlace por correo. Pero todo esto lleva mucho tiempo y copiar y pegar, y luego en la barra de direcciones, lo que, por ejemplo, en una tableta es extremadamente inconveniente. No, todo esto es una especie de tontería ...
Tumbado en el sofá, lentamente me di cuenta de que todas estas acciones requieren demasiado movimiento ... No, muchachos, eso no servirá. Y cuando entiendo que algo no me conviene en este mundo, me siento a escribir código para hacer todo a mi manera. Pensé que estaba autorizado en las redes sociales tanto en la tableta como en la computadora de escritorio. Y en diferentes navegadores, por ejemplo, en la misma computadora, también. En general, la solución para mí era obvia: autenticar al usuario a través de las redes sociales.
Digresión lírica
Por cierto, cuando escribo algo propio, lo hago también a mi manera. Escribo en javaScript puro en un cuaderno avanzado, no uso github, no uso bibliotecas de terceros, ni siquiera uso jquery. Por lo tanto, no habrá un tutorial sobre cómo escribir una extensión del navegador. No te voy a enseñar esto. No hagas lo que yo hago. Te advierto: este es un mal ejemplo. También quiero contarles a todos los críticos potenciales, anticipando su reacción; sí, estoy completamente de acuerdo con toda su ira justa. Sí, no puede insertar todo el script en uno o dos archivos, pero debe cortar todo, como una ensalada, en muchos pedazos pequeños para que luego pueda ensamblarse durante 3 horas en un comando largo e inteligente desde la línea de comandos. Sí, no puede combinar código javascript y código html en un archivo; es mejor arruinar otro nivel de abstracción que los combine. Sí, no puedes usar el diseño de la tabla, pero maldición, ¡es hierro! Y, aún más, ahora me van a quemar, no puede usar innerHtml y crear una estructura html compleja de una sola vez, pero necesita unir y separar a todos los niños en un bucle y adjuntar cuidadosamente y luego eliminar cada controlador ... Sí, estoy haciendo todo mal. Pecaminoso, me arrepiento. Pero lo hago conscientemente, porque es más fácil. ¿Y quién me lo prohibirá? Al final, no es ilegal, ¿verdad? No sé cómo programar como lo requiere un mod moderno, y ni siquiera quiero intentarlo, porque creo que el diagrama del proceso de desarrollo es innecesariamente complicado. Estoy a favor de escribir código con mis manos y no construirlo a partir de las piezas de otra persona sin escribir una sola línea. Sin embargo, mi código es ligero, no necesita ser ensamblado por un equipo especial y funciona rápidamente. Estoy escribiendo código usando la tecnología F5. Esto es cuando, para ver cómo funciona la versión actual en cualquier momento del proceso de desarrollo, simplemente haga clic en el navegador F5.

Sin embargo, todavía tenía que colgar los controladores en un bucle, porque de lo contrario la extensión no pasa la prueba. También en extensiones, por si acaso, en el archivo de índice html, de repente, los scripts conectados dinámicamente están prohibidos. Entonces los conecté a través de la etiqueta del script.
Almacenamiento de pestañas
Entonces, decidí que las pestañas abiertas en el navegador deberían guardarse en ciertas listas, que se llamarán computadoras: computadora de casa, computadora de trabajo, computadora local. Local: esto es cuando la lista no se almacena en el servidor, sino en la base de datos del navegador y, en consecuencia, solo puede usarla en el navegador desde el que se guarda. Esto es para aquellas pestañas que no necesitan ser lanzadas entre diferentes computadoras. Bueno, el resto de las listas se pueden ver en cualquier computadora y navegador de entre los admitidos por la extensión.
Para cada pestaña, el usuario puede dejar un comentario de texto arbitrario. Por ejemplo, es conveniente para mí recordar qué series detuve al ver la serie, y también marcar por mí mismo lo que está en la página, si no está claro por su título y tipo de enlace.
Según la documentación para crear extensiones para Chrome y Firefox, el código de extensión debe ubicarse en dos archivos: el principal y el de fondo. El script principal se ocupa de la visualización de la interfaz de usuario, y el script de fondo puede controlar las pestañas del navegador e intercambiar datos con el servidor. La administración de pestañas en Chrome y Firefox es muy similar. Por ejemplo, el controlador de eventos para abrir o cerrar pestañas en Chrome tiene este aspecto:
chrome.tabs.onUpdated.addListener( function(tabId, changeInfo) { });
Y en Firefox así:
browser.tabs.onUpdated.addListener( function(tabId, changeInfo, tabInfo) { });
Y la función que muestra una lista de todas las pestañas abiertas se escribe exactamente igual para ambos navegadores:
chrome.tabs.query({},function(data){ });
Sí, sí, Chrome también escribe Chrome en Firefox ... etc. Esto es un poco extraño, sin embargo, el hecho de que los navegadores se estén moviendo hacia la estandarización de su API es muy alentador.
En realidad, toda la funcionalidad de la extensión se logra mediante el uso de varias funciones: abrir la ventana de extensión haciendo clic en su icono, leer pestañas abiertas, cerrar la pestaña, crear una nueva pestaña, escuchar eventos de pestañas e intercambiar datos con la ventana de extensión. Eso es todo. Estos métodos solo están disponibles en el script de fondo.
Después de leer, las pestañas abiertas en el navegador se envían a mi servidor y se guardan allí en una base de datos SQL normal. El script del servidor está escrito en PHP. Hay una tabla de usuario que almacena enlaces a filas en otra tabla: la tabla de datos. Estos datos son las direcciones de las páginas, sus nombres y comentarios de texto del usuario, almacenados en el formato de cadenas de texto en un campo de tipo de texto de aproximadamente un kilobyte de largo. Los datos se almacenan en forma no cifrada. Se pueden guardar alrededor de 1,000 pestañas por megabyte. Se proporciona un máximo de 25 de estos almacenamientos ("Computadoras") para cada usuario.
Sin embargo, la versión gratuita de la extensión limita al usuario a dos almacenamientos: la computadora del hogar y la computadora del trabajo, y cada uno de ellos no puede almacenar más de 10 pestañas. Todavía estoy trabajando en la versión paga y los métodos de pago. Habrá hasta 25 "computadoras" y hasta aproximadamente 1000 pestañas en cada una, así como una selección de imágenes de fondo, iconos y nombres para cada computadora, listas jerárquicas y mucho más.
Hay otro repositorio: computadora local. Aquí no hay restricciones, ya que los datos de la pestaña se almacenan en la base de datos del navegador local en la computadora del usuario. Aquí puede almacenar tantas pestañas como desee, pero no más de lo que permite el disco duro. Además, dado que los datos no se almacenan en el almacenamiento local, sino en indexedDB, no hay límite de 5 o algunos megabytes allí. Solo es importante no borrar accidentalmente este repositorio junto con el historial del navegador. También planeo exportar e importar pestañas a un archivo de texto.
Para trabajar con indexedDB, escribí una pequeña sublibrary que solo tiene 106 líneas de largo. A diferencia de la base de datos en el servidor, aquí no es necesario que todos los datos se destilen en una cadena de texto, sino que se pueden guardar inmediatamente en la matriz asociativa tal como están. El principio de almacenamiento es el siguiente: la clave es el valor. Y el valor puede ser una gran matriz asociativa.
Autenticación de usuario
FirefoxLa autorización, como ya señalé, ocurre a través de las redes sociales y, en el servidor, usando el protocolo OAuth. Todavía es compatible con Facebook y VKontakte, pero planeo aumentar el número de métodos de autenticación de usuarios. El esquema de autorización del servidor OAuth se describe en detalle en la documentación de ambas redes sociales, por lo que no tiene sentido detenerse en él en detalle. Solo noto que no me gustó el hecho de que durante la autorización se abre una nueva pestaña del navegador, incluso si el usuario ya ha iniciado sesión en la red social y ya ha otorgado los derechos de extensión. El script de extensión de fondo debe capturar esta pestaña y luego forzarla a cerrar, y en general, no se ve estéticamente agradable, se pega en las otras pestañas y parpadea cuando aparece y se destruye.
Para cerrarlo, para VKontakte debe verificar la presencia de la dirección en el controlador de eventos de pestaña:
oauth.vk.com/blank.html
Y para Facebook:
https://www.facebook.com/connect/blank.html
Y por si acaso:
facebook.com/connect/login_success.html
Por lo tanto, al principio envié un ensamblaje de extensión a Google Web Store, en el que se realizó la autorización en el cliente con un pull-up preliminar de la red social de la API de JavaScript del cliente correspondiente. Además, dado que la extensión está instalada en el usuario y necesito autorizar en mi servidor, también extraje html de mi servidor en el script de extensión en el i-frame, pero ya extraje la API de la red social ...
Y el esquema de intercambio de datos con el servidor era así. Una página de índice de extensión envía un comando (información de clic, por ejemplo) a un script de extensión de fondo. La secuencia de comandos de fondo que usa postMessage envía datos a i-frame html. I-frame envía datos al script php en el servidor. El servidor responde en el i-frame, el i-frame responde en el script de fondo, el script de fondo responde en el índice, el usuario ve la respuesta. Uff ... Y lo más importante: ¡todo funcionó!
En general, esto no funcionó. Google envolvió mi extensión con una serie de formulaciones, entre las cuales había algo vago que, dicen, su extensión no cumple con nuestra política de seguridad. A través de la correspondencia con el apoyo, pude lograr detalles. Es decir, no les gustó el hecho de que la extensión extrae html y js de servidores de terceros ... En general, tuve que terminar con la autorización del cliente y volver al servidor. Sí, el envío de una solicitud de publicación http desde un script de extensión en segundo plano directamente a su servidor, sin embargo, resultó estar permitido. Bien Eso es incluso mejor. Resultó más corto y no es necesario extraer la API de JavaScript de las redes sociales; este es un tiempo de espera adicional para el usuario.
Ver pestañas
Volver a las opciones de expansión. La lista de pestañas en sí es una serie de líneas en las que primero aparece el favicon de la imagen, luego el título de la página y finalmente el enlace. Lo que no cabe en el tamaño de línea designado en la pantalla se recorta. Pero la base de datos se guarda por completo. Además, cualquier línea se puede mover hacia arriba de la pantalla en forma de mosaico de color. Esto es para los sitios más importantes que deben estar ante sus ojos en primer lugar.
Lista de pestañas de ChromeLos colores para los mosaicos se seleccionan automáticamente en función del nombre de dominio del sitio. La función acepta la url. El nombre de dominio se divide en tres grupos de caracteres aproximadamente iguales: los primeros caracteres de cada grupo se convierten a los valores de los componentes de color: R, G, B. Esta conversión se realiza de la siguiente manera. Los códigos de estos tres caracteres se reducen al rango d1, de 0 a 25, al tomar el resto de la división en 26. Incluso los caracteres del alfabeto ruso se reducirán a este rango. No importa que la letra 27 se convierta en la primera: no necesitamos que los componentes de color de todas las letras del alfabeto sean necesariamente diferentes, permítales repetirlos. Luego, los tres números obtenidos del rango d1 (0 ... 25) se reducen proporcionalmente al rango d2 (150 ... 255). En general, estos rangos se establecen al comienzo de la función y se pueden cambiar a cualquier otro. Tomé 150 ... 255 para que los componentes de color sean brillantes. Si establece, por ejemplo, 0 ... 100, los mosaicos se volverán oscuros. Por lo tanto, tres caracteres del nombre de dominio se convierten en 3 números del rango 150 ... 255. Y luego, como probablemente haya adivinado, se interpretan como los componentes de color de los mosaicos R, G y B. Todo es muy simple.
getSiteColor=function(url) { var d1=[0,25], d2=[150,255]; var code=0, codep=0, color=0, str='', domen='', ar=[], inc=0; ar=url.split('//'); if (ar.length>1) {str=ar[1];} else {str=ar[0];}; str=str.split('www.').join(''); domen=str.split('/')[0]; str=domen.split('.').join(''); ar=[]; inc=Math.floor(str.length/3); if (str.length % 3 >0) {inc++;}; for (var i=0; i<str.length; i+=inc) { code=str.slice(i, i+1).charCodeAt(0); codep=code % (d1[1]-d1[0]+1); color=Math.round( codep * (d2[1]-d2[0]) / (d1[1]-d1[0]) ) + d2[0]; ar.push(color); }; return {r:ar[0], g:ar[1], b:ar[2], domen:domen}; }
Estructura de documentos html
Un documento html consta de varios elementos de lienzo con posicionamiento absoluto, combinados por superposición, y un bloque div en el que se muestra la lista. Se cuelga una función en el tamaño de la ventana del navegador que cambia el tamaño de todos estos elementos, ajustándolos a la nueva altura y anchura. También hay un tamaño mínimo, superación que provoca la aparición de barras de desplazamiento. La imagen de fondo se muestra en el lienzo inferior. Decidí que para diferentes listas (es decir, computadoras), se deben establecer diferentes fondos para facilitar la navegación del usuario. La imagen de fondo llena una ventana con la preservación de sus proporciones y se ilumina un poco para no llamar la atención: se dibuja un rectángulo blanco translúcido encima. Sobre el lienzo de fondo se encuentra el lienzo del menú principal, solo llena la parte superior de la pantalla. Bueno e incluso más arriba se encuentra el bloque div, en el que se forma la lista de pestañas. La navegación del menú del lienzo se realiza a través de mi mini biblioteca.

Navegador Opera y YandexLocalización
En la pantalla principal hay una bandera, al hacer clic en la cual la interfaz cambia entre ruso e inglés. Aquí la página se redirige a la misma dirección, pero con un parámetro en la línea de comando. Este parámetro se lee antes de cargar todos los demás elementos. Y en función de su valor, este o aquel archivo js con frases en ruso o inglés se carga en la matriz asociativa para frases: lng_en.js o lng_ru.js. Y en la aplicación misma, para mostrar frases de interfaz, ya se utilizan enlaces a cadenas de texto de esta matriz asociativa. Además, dependiendo del valor en la barra de direcciones, se carga un archivo que contiene los elementos de la interfaz gráfica: botones: buttons_en.png o buttons_ru.png. Decidí que es mejor crear botones junto con los íconos e inscripciones en cada idioma en el editor de gráficos que crear un botón vacío e superponer íconos e inscripciones en él, especialmente porque no hay muchos de ellos y toda esta lista de sprites pesa solo 50 Kb Planeo continuar trabajando en el diseño y hacer que todos los botones tengan diferentes formas.

El archivo general con sprites main.png, que contiene elementos gráficos que no están vinculados a una localización específica, se carga de todos modos.
Versión web
Pensé que sería bueno si los enlaces cuidadosamente almacenados desde la computadora de la casa o el trabajo pudieran verse desde el teléfono. Pero no todos los navegadores de sistemas operativos móviles admiten extensiones. Entonces creé un ensamblaje web. Al visitar el sitio en una dirección específica, aún puede iniciar sesión en una de las redes sociales y ver sus pestañas.
Sí, no hay forma de agregar pestañas a la lista o editar. Pero al menos puede abrir pestañas de la lista y ver las páginas. Creo que vale la pena trabajar en la versión móvil de este sitio y mostrar listas más grandes de pestañas en él.
Versión web en IE 11Publicidad
Realmente no he trabajado en promover mi expansión hasta ahora. Acaba de crear grupos en las redes sociales e invitó a todos sus amigos allí. Sí, lanzó una campaña publicitaria en Yandex Direct por 1.500 rublos. Ella no dio ningún resultado especial, pero tal vez no hice el anuncio correctamente. O tal vez el problema es que indiqué un enlace a la versión en inglés de la página de inicio de la extensión. Y tal vez valió la pena dar un enlace no a la página de inicio, sino inmediatamente a una de las tiendas de extensiones. Como sabes, no soy un genio del marketing. En general, intentaré nuevamente con otros parámetros. La campaña dio 39 clics. Es difícil decir si adquirí algunos usuarios nuevos como resultado de ello.
Había una rareza con la versión en Firefox.
Las estadísticas del 17 de octubre muestran hasta 227 descargas. No sé si la campaña en Yandex.Direct contribuyó a esto o no, pero por alguna razón, 1-2 descargas por día nuevamente continúan por alguna razón. Al mismo tiempo, para la extensión de Firefox existe el concepto de usuarios diarios:
Por qué hubo 227 descargas, pero solo hubo 1-2 usuarios diarios, no está claro. Quizás fue algún tipo de fracaso. En general, todavía no entendía qué era y dónde están todas estas personas ...
Las estadísticas en la tienda de extensiones de Chrome Web Store complacieron un horario eternamente sin carga, eso es lo que no vi, y de 5 a 10 usuarios diarios.
Además, envié el ensamblaje a la tienda de extensiones de Opera. Sin embargo, después de haber presentado dos versiones y sin esperar la moderación de ninguna de ellas, en algún momento escupí sobre la difusión de otras nuevas allí. Y, de hecho, ¿por qué es esto necesario si Opera instala perfectamente las extensiones de la tienda Chrome?
Resumen
Creé tres compilaciones de extensiones: para Chrome, Firefox y la versión web. En realidad, los tres conjuntos son uno y el mismo conjunto, lo que simplemente indica en la configuración qué motor de navegador se está utilizando actualmente. Y se inicializan las funciones correspondientes para trabajar con pestañas. Modifico este valor antes de empacar en zip y enviar el paquete a la tienda de extensión adecuada.
Las versiones para Chrome y Firefox han sido probadas y colocadas en sus respectivas tiendas de extensiones oficiales. Además, el registro como desarrollador de extensiones con Google cuesta $ 5. Mozilla lo tiene gratis. La versión web de la extensión se encuentra en el servidor. El ensamblaje de la tienda Chrome funciona bien en navegadores compatibles: también se puede instalar en Yandex Browser y Opera. Planeo lanzar nuevas versiones con características aún más avanzadas.
En general, las extensiones del navegador son poderosas. Ahora no necesito levantarme del sofá, y tampoco hay necesidad de ira para romper la tableta. Esto es completo Zen. Bueno para todos