Aplicació web amb motor Python

De wikijoan
Salta a la navegació Salta a la cerca

Introducció: Aplicació web amb motor Python

En certes ocasions volem resoldre problemes i realitzar càlculs, i el millor llenguatge de programació és Python, ja sigui per les seves llibreries, o perquè hem trobat una solució al nostre problema en aquest llenguatge.

El que plantegem en aquesta pràctica és fer una interfície web, però per darrera tenim un motor Python. La idea no és difícil d'entendre. Amb Python, entre totes les seves llibreries, té la possibilitat de fer de servidor web. I per tant, com hem vist, des de la nostra aplicació web podem fer una crida AJAX al servidor web de Python, i esperar la resposta que el Python ens ha de proporcionar. Aquest és el mateix esquema que hem fet (o farem) amb NodeJS en el cantó del servidor.

Primer exemple. Matemàtiques a 5è de Primària. Aritmètica bàsica

Pere aritmetica.png

Hem de fer una aplicació web per resoldre uns exercicis d'aritmètica que es resolen a 5è de Primària. L'enunciat: posar els operadors aritmètics (+, -, *, /) per obtenir el resultat. Podem utilitzar parèntesi:

5  8  3  = 55

Solució:

5 * (8 + 3)  = 55

Amb Python podem trobar la solució per força bruta. Aquesta solució la podríem trobar amb qualsevol altre llenguatge de programació, donat que no utilitzem llibreries especials. Tanmateix, en aquesta ocasió ho hem fet amb Python.

El programa té dues opcions:

1) Donats 3 valors d'entrada, oferir totes les combinacions possibles

2) Per uns valor d'entrada i el resultat final, oferir la solució (o solucions): és a dir, els operadors i els parèntesi que hem d'utiltizar.

Limitacions:

  • Els valors d'entrada han de ser números naturals (positius i sense decimals)
  • Només es pot utilitzar un únic parèntesi (lògic si tenim tres números d'entrada)

Solució (descarrega tots els fitxers)

Solució Python (sense servidor web)

En la carpeta python/ se't proporciones 5 versions incrementals del problema. Evidentment la bona és la 5ena. Els comentaris estan dins el codi, i a la capçalera hi ha el comentari de les versions.

Has de mirar el codi i entendre'l (no és difícil, crec). Aquest és el nostre motor que integrarem més tard amb un servidor web python.

Python3: servidor web. Exemple bàsic sumar tres números (exercici previ)

Abans de resoldre el problema plantejat, anem a fer dos petits exemples.

Crida (request) amb el mètode GET (Exemple 1)

Fitxers index.html i http_server.py.

Fem una crida AJAX al servidor web basat en Python, mitjançant el mètod GET. Primer arrenquem el servidor web:

$ python3 http_server.py 8080

I ara des del navegador accedir a:

I millor, des de index.html fem una crida AJAX al servidor web (mètode GET):

Crida (request) amb el mètode POST (formulari). Sumar tres números (Exemple 2)

Fitxers sumar_tres_numeros.html i http_server_sumar_tres_numeros.py.

Arrenquem el servidor web:

$ python3 http_server_sumar_tres_numeros.py

Estudia bé el codi.

Python3: servidor web. Problema d'aritmètica 5è

Fitxers: pere_aritmetica i http_server_pere_aritmetica.py

I ara ja podem atacar el nostre problema. Integrem solucio_v5.py amb el codi del servidor web http_server_sumar_tres_numeros.py, per obtenir http_server_pere_aritmetica.py

Interfície web

Ara que ja tenim un servidor web que ens ofereix la solució, ja poem pensar en la interfície web, pensant en com l'usuari es relacionarà i interaccionarà amb l'aplicatiu.

Tenim els següents requisits:

  • hem vist que tindrem un número variable de valors d'entrada. D'entrada tindrem tres caixes de text per a les entrades, i una caixa de text per al resultat final (que serà opcional). S'hauria de fer una validació en les caixes de text de manera que només puguem entrar valors enters i positiu.
  • Botó Calcula: Si no hi ha valor en la casella de resultat, hem de llistar totes les combinacions amb els tres valors d'entrada; si tenim el resultat final, hem de llistar totes les solucions de manera que combinant aritmèticament els tres números ens doni la solució.

Un cop tenim la interfície web, ja podem fer la crida AJAX al nostre motor Python, que calcularà i ens proporcionarà la solució.

Segon exemple. Intersecció de rectes

Interseccio rectes.png

Recordem que l'equació de la recta té la forma y = mx + b, on m és el pendent, i b és el coeficient que és el punt on la recta talla l'eix de les y.

Dues rectes sempres es tallarant en un sol punt, a no ser que:

  • siguin iguals, per tant són rectes coincidents i tenen en comú infinits punts.
  • tinguin el mateix pendent però el coeficient b sigui diferent: són rectes paral·leles i no es tallen en cap punt, el sistema no té solució.

En aquest exemple fem ús de la llibreria numpy (molt potent) de Python per trobar la solució on es creuen les rectes. I fem ús de la llibreria matplotlib (molt potent) per fer la representació gràfica.

La solució d'on es creuen dues rectes és molt fàcil (no caldria utilitzar la llibreria numpy), però a partir d'aquí es podrien fer coses molt més complexes que només es podrien abordar amb llibreries de mètodes numèrics com numpy. És per això que justifiquem que aquest problema l'hem d'abordar amb Python (i no amb NodeJS o PHP), perquè tenim unes llibreries matemàtiques adients.

I en el cantó del client volem fer un front-end fàcil, amb un petit formulari per entrar les dues equacions y=mx+b, un espai per posar la solució, i un altre espai per mostrar la gràfica resultant.

Python2 o Python3?

Els scripts v1 i v2 (veure més avall) només s'han provat amb Python2.

En la v3, quan es volia fer el servidor web, el codi que s'ha implementat és de Python3 (que no vol dir que no es pugués fer amb Python2). Per tant, v3 i v4 estan amb Python3.

En la vostra màquina poden coexistir sense problema les dues versions de Python.

Per instal·lar les llibreries farem: (primer haureu d'instal·lar l'eina pip per instal·lar mòduls i resoldre dependències, equivalent al npm de NodeJS)

$ pip install numpy
$ pip install matplotlib
o bé
$ pip3 install numpy
$ pip3 install matplotlib

El professor va tenir un lio de versions entre Python2 i Python3, que vosaltres no hauríeu de tenir. Ho vaig resoldre reinstal·lant els mòduls:

$ pip install --upgrade --force-reinstall numpy
$ pip install --upgrade --force-reinstall matplotlib

Curiosament, he hagut d'instal·lar un mòdul (que prèviament no el tenia instal·lat o bé el tenia instal·lat sense saber-ho): Pillow, que està relacionat amb la generació d'imatges. Crec que s'hauria d'instal·lar com a dependència amb matplotlib. En tot cas:

$ pip install -U Pillow

Versions del projecte

  • interseccio_v1.py
$ python interseccio_v1.py
$ python3 interseccio_v1.py

És el primer exemple per comprovar que tenim ben instal·lades les llibreries matplotlib i numpy. Genera la imatge en la carpeta img/.

  • interseccio_v2.py. Passem els arguments en línia de comanda:
$ python interseccio_v2.py 1.0 2.0 4.0 -3.0
  • interseccio_v3.py. És el mateix que v2 però funciona amb python3. Només és per comprovar que el codi continua funcionant amb Python3.
$ python3 interseccio_v2.py 1.0 2.0 4.0 -3.0
  • interseccio_v4.py. Ja funciona com a servidor web pel port 8080.
$ python3 interseccio_v4.py

Per provar el mètode GET pots fer:

Amb el mètode GET pots mostrar o bé la solució, o bé la imatge generada (però no he aconseguit fer-ho tots dos alhora, veure les línies comentades en la funció do_GET().

No continuïs amb el mètode POST fins que no et funcioni el mètode GET.

  • interseccio_rectes.html: aquest és el front-end (que tu pots millorar...). És un formulari que envia les dades al servidor web Python per POST, crida AJAX. I rep les dades del servidor i les mostra per pantalla (solució i gràfica).

En el navegador web:

El codi v4 contempla els següents casos:

  • rectes coincidents i rectes paral·leles.
  • podem posar y=x+4 en comptes de y=1x+4
  • els coeficients han de ser enters (positius o negatius).
  • S'ha solucionat que la gràfica canvïi quan tornem a enviar el formulari amb unes altres dades (problemes de caché), fent que el nom del fitxer de la gràfica sigui aleatori (entre 0000.png i 9999.png)

No contempla les següents millores, que es deixen per a l'alumne:

  • y = 3x + 4 (espais en blanc)
  • posar coeficients decimals y=3.5x-2.4

Descàrrega codi

Se t'adjunta els scripts necessaris, i un tutorial de matplotlib per si vols aprofundir en la generació de gràfiques amb Python.

Descarregar tot el codi:

Feina per l'alumne

Estarem contens si l'alumne pot reproduir el funcionament dels exercicis.

A partir d'aquí, es poden fer moltes millores. Per exemple, en les gràfiques, podem complicar-nos la vida una mica si fem interseccions de rectes i paràboles, o de paràboles. Recordem que la paràbola és la funció quadràtica: y=ax^2 + bx + c.

Entrega

Entrega en el Google Classroom en el temps previst. N'hi haurà prou en demostrar que s'han executat correctament tots els codis proposats. Implementa alguna millora significativa.


creat per Joan Quintana Compte, desembre 2019