Víctor López Ferrando

Implementació de la Contrarellotge matemàtica

1 de desembre de 2017

La Contrarellotge matemàtica és un portal web on es realitzen concursos matemàtics online. Es tracta d'un projecte sense ànim de lucre, amb l'objectiu de difondre les matemàtiques entre els joves, que vaig presentar el mes de febrer de 2017. Actualment compta amb més de 800 usuaris registrats de 175 centres educatius diferents, als quals els hem plantejat més de 150 problemes matemàtics.

En aquest article explicaré com funciona la Contrarellotge matemàtica: els llenguatges de programació emprats, les llibreries i frameworks que fem servir, l'arquitectura del sistema i altres serveis que ens permeten gestionar-ho tot i assegurar un bon funcionament.

1. L'aplicació web

Comencem pel moll de l'os. L'aplicació web és el conjunt de programes que hem elaborat encarregats de generar les pàgines web, gestionar les dades que envien els usuaris, etc.

L'aplicació de la Contrarellotge matemàtica està desenvolupada com una aplicació Django. Django és un framework en Python que facilita la programació d'aplicacions web: ens dóna unes pautes pel que fa a l'organització del codi, afavoreix el seguiment de bones pràctiques de programació i ens estalvia els aspectes més tediosos del desenvolupament. El seu lema és «per perfeccionistes amb dates límit», i compleix a la perfecció la seua funció.

Ens podem fer una idea de l'abast del projecte fent un recompte del nombre de fitxers i de les línies de codi de què consta. En total, es tracta d'unes 8.500 línies de codi (sovint es considera que 10.000 línies de codi marquen el llindar entre un projecte petit i un de mitjà). Vegem quins són els llenguatges d'aquest codi:

Llenguatge de programació Fitxers Línies de codi
HTML 50 3.905
CSS 2 534
JavaScript 3 1.163
Python 38 2.779
Latex 3 96
Total 96 8.477

Explicarem ara breument quin paper juga cadascun d'aquests llenguatges de programació en l'aplicació.

D'una banda, hi ha tres llenguatges que defineixen com són les pàgines que veiem al nostre navegador:

  • HTML: defineix com són les pàgines web. A l'HTML trobem els menús, text, taules, panells, etc. Tenim 50 fitxers, aproximadament un per cada pàgina, i en total sumen pràcticament la meitat de les línies de codi del projecte.
  • CSS: dóna estil a les pàgines webs: defineix quins són els colors de cada element, la mida del text, l'espaiat, etc. Tot l'estil està centralitzat en dos fitxers: un per a les fonts (el tipus de lletra), i un altre per la resta.
  • JavaScript: aquest llenguatge l'executa el navegador i s'encarrega de gestionar tot allò que passa al web mentre no actualitzem la pàgina. En JavaScript hem programat el funcionament de les Contrarellotges (incloent-hi el Concurs de prova, les Participacions virtuals, etc.).

Llenguatges de programació emprats Llenguatges de programació emprats (mida proporcional a la quantitat de codi)

Per generar diplomes, usem:

  • Latex: aquest llenguatge —el preferit pels matemàtics per escriure fórmules i documents— l'emprem per a elaborar els diplomes. També és el llenguatge en què escrivim les fórmules dels problemes.

Finalment, destaca el llenguatge que emprem al servidor per a orquestrar-ho tot:

  • Python: es tracta d'un llenguatge d'alt nivell, és a dir, capaç de realitzar tasques complicades amb comandes breus i comprensibles. Les gairebé 3.000 línies de codi Python que hem implementat són el nucli de l'aplicació, la part més important i complexa.

Llibreries externes

El recompte de línies de codi anterior no inclou el codi de les llibreries externes que hem usat i que ens faciliten moltes tasques.

Per exemple, hem emprat un seguit de llibreries JavaScript:

  • KaTeX: dibuixa totes les fórmules matemàtiques de manera molt ràpida i eficient.
  • D3.js: llibreria de visualització de dades molt flexible amb què hem elaborat les gràfiques de la pàgina d'estadístiques.
  • Leaflet i Wikimedia maps: per mostrar el mapa de les localitats dels usuaris.
  • Select2: ens permet fer els desplegables amb cerca per triar la Localitat i el Centre educatiu a la pàgina de perfil.
  • Moment.js: ens ajuda a treballar amb dades temporals, especialment important pels concursos en directe.
  • jQuery: llibreria clàssica a partir de la qual hem desenvolupat tot el funcionament dels concursos en directe.

Pel que fa a l'estil, també hem usat un parell de llibreries o frameworks CSS que ens han facilitat molt la vida:

  • Bootstrap: framework popularíssim que ens dóna l'estil bàsic de tota la pàgina i que entre altres coses ens facilita fer que totes les pàgines siguen responsive: que estiguen adaptades per ser visualitzades des de dispositius mòbils, tauletes, portàtils o pantalles d'escriptori.
  • Font Awesome: ens proveeix de totes les icones que mostrem.

2. Arquitectura del sistema

L'aplicació web que hem descrit fins ara, és només una part d'un sistema més gran. Concretament, correspon a la caixa «django» del següent esquema, que mostra l'arquitectura d'una aplicació web típica:

Arquitectura d'una aplicació web Django Arquitectura d'una aplicació web Django clàssica.

El navegador web es comunica amb un servidor (en el nostre cas allotjat a Londres a l'empresa Linode i amb el sistema operatiu Ubuntu). El servidor executa el servidor web Apache, un programa que parla el protocol HTTP i que per tant és capaç de comunicar-se amb el navegador.

Segons què busca el navegador, Apache decidirà què fer. Si demana una imatge, un document PDF o qualsevol altre fitxer estàtic, Apache el lliurarà directament. Si en canvi vol el contingut d'una pàgina dinàmica, delegarà la generació de la pàgina a l'aplicació web Django.

A la caixa de Django trobem les 8.500 línies de codi de què parlàvem abans, que saben com generar cada pàgina: quin contingut va a la portada, o a la pàgina d'un problema del mes; com gestionar una resposta enviada, o una participació virtual.

Finalment, MySQL és la base de dades on emmagatzemem les dades: usuaris, problemes, participacions en els concursos, etc.

Arquitectura de les Contrarellotges en directe

Hem mostrat l'arquitectura d'una aplicació web clàssica, que per exemple seria suficient per a gestionar els Problemes del mes. Però les Contrarellotges són més que això: són concursos en temps real en què tots els usuaris participen alhora i s'assabenten en directe del que estan fent els altres participants.

Per implementar aquesta mena de concursos, hem usat el modern projecte Django Channels, una extensió de Django que permet aquest tipus de comunicació en temps real. Aquest és l'esquema resultant:

Arquitectura amb Django Channels Arquitectura d'una aplicació Django Channels: comunicació en temps real mitjançant WebSockets.

D'una banda, hem afegit la comunicació amb WebSockets: sense actualitzar la pàgina, el JavaScript és capaç d'enviar al servidor les opcions que marquen els usuaris, i també de rebre els enunciats, correccions i les accions dels altres usuaris.

D'altra banda, hem afegit una rapidíssima base de dades en memòria, Redis, que necessita Django Channels per mantenir la comunicació amb els WebSockets.

El repte: una allau de visitants al mateix temps

La Contrarellotge matemàtica, junt amb al meu blog, s'allotgen en un modest servidor d'1 processador que costa 10 € al mes, però que té potència de sobres pel funcionament normal d'aquestes webs. No obstant això, els concursos en directe són una altra qüestió: més de 100 usuaris es poden connectar alhora i realitzar accions que saturarien aquest servidor.

Per gestionar aquesta càrrega, durant les contrarellotges lloguem un servidor més gran (per exemple, un de 6 processadors costa només 0,10 € l'hora), cosa que ens permet canviar l'arquitectura de l'aplicació de la següent manera:

Arquitectura del concurs en directe Arquitectura dels concursos en directe: la càrrega més gran de còmput es mou a un servidor més gran.

D'aquesta forma el cost de cada Contrarellotge pot voltar els 20 cèntims. Com diu un amic meu enginyer a Google, arquitectura del software per a pobres :p.

3. Serveis complementaris

Més enllà de l'aplicació web, també emprem un seguit de serveis complementaris que ens ajuden amb el manteniment, la difusió i la seguretat. A continuació expliquem quins són aquests serveis.

Anàlisi de les visites amb Piwik

És important analitzar algunes dades sobre les visites per millorar contínuament la web. Ens interessa saber quantes visites tenim, però també d'on provenen (e-mail, Twitter, XTEC...), quina mena de dispositius usen (mòbils, portàtils...), quins navegadors, etc. Per fer-ho, usem el programari lliure Piwik allotjat al mateix servidor, que ens permet analitzar aquestes dades sense haver d'enviar-les a servidors externs.

Gràfica visitesVisites a contrarellotge.cat durant els últims 12 mesos. Les "visites amb conversions" són els registres d'usuaris.

Comunicació segura: HTTPS amb Let's Encrypt

Totes les dades que s'envien i reben des de contrarellotge.cat ho fan a través del protocol HTTPS (HTTP Secure), cosa que evita que cap intermediari puga interceptar dades sensibles com les contrasenyes dels usuaris. Per fer-ho, usem certificats de Let's Encrypt, l'autoritat certificadora gratuita que ha revolucionat el món dels certificats durant els últims dos anys.

Enviament massiu de correus amb Mailgun

Usem Mailgun per a enviar els correus en què anunciem les Contrarellotges, Problemes del mes, així com els correus de promoció als instituts. Açò ens permet monitorar quants correus s'obrin, per quants ha fallat l'enviament, etc. Tampoc ens suposa cap cost addicional perquè no superem els 10.000 correus mensuals.

Monitoratge de l'estat de la web amb Uptime Robot

En cas que la web s'ature per algun motiu, volem ser notificats immediatament, i per això usem Uptime Robot, un servei que visita contínuament la web i comprova que tot funcione. En cas que la pàgina no estiga accessible, envia un correu electrònic que ens avisa.

Difusió a les xarxes socials: Twitter

Aquest setembre vam crear l'usuari @contrarellotgem a Twitter, que actualment compta amb 115 seguidors. S'ha demostrat que és un canal molt útil per anunciar les novetats, i serveix per a donar a conéixer la iniciativa, especialment entre els professors de matemàtiques de secundària.

Optimització pels motors de cerca

Cada mes, centenars de visites ens arriben des dels motors de cerca —principalment Google. Per facilitar que troben i indexen correctament les nostres pàgines hem usat algunes tècniques com:

  • Oferir una llista de totes les pàgines del lloc al sitemap.xml.
  • Afegir una descripció a cada pàgina perquè la llegisca el cercador.
  • Fer pàgines optimitzades i ràpides seguint les directrius del PageSpeed Insights.
  • Usar un esquema canònic d'URLs: totes amb https i començant amb www.

Còpies de seguretat

Diàriament fem còpies de seguretat de la base de dades i també de tot el disc dur del servidor mitjançant el servei de Backup que ofereix l'empresa d'allotjament Linode. D'aquesta manera estem preparats per qualsevol imprevist i ens assegurem de no perdre mai les dades.

4. Conclusió

Com hem vist, es tracta d'un projecte d'una certa complexitat i que planteja uns interessants reptes de programació —deixant de banda la part de posar els problemes matemàtics i les seues solucions!

Vaig començar el desenvolupament en juliol de 2016, i una de les claus de l'èxit ha sigut l'estratègia de fer un desenvolupament incremental. Cada pocs mesos he anat afegint funcionalitats, a mesura que tenia temps per implementar-les. D'aquesta manera he pogut prioritzar el més important a cada moment, i també motivar-me a mesura que veia els resultats i la resposta positiva d'estudiants i professors.

Però el més important és que l'objectiu sempre ha sigut passar-m'ho bé desenvolupant el projecte, igual que els participants gaudeixen resolent els problemes que plantegem. En la programació, com en les matemàtiques, trobem la bellesa en les solucions enginyoses, en la simplificació de raonaments complexos, en la superació de petits reptes que ens porten a una comprensió més profunda del problema, i quan busquem aquesta bellesa, sabem que anem pel bon camí.