Scroll view
Si estás en un dispositivo móvil. |
Fragment view
Tal como se ve en la presentación. |
Speaker mode
Para ver las notas del presentador. |
Print mode
Exportar a PDF. |
Search
Busca en la presentación (Ctrl + Shift + F). |
Shortcuts |
Navega usando
Santos Gallegos
-
[email protected]
@stsewd
- Fin
|
![]() |
Autenticación: ¿Quién eres?
Autorización: ¿Qué puedes hacer?
Django tiene un sistema de autenticación y autorización muy completo. ÚSALO
from django.contrib.auth.decorators import login_required
from django.contrib.auth.mixins import LoginRequiredMixin
@login_required
def my_view(request):
pass
class MyView(LoginRequiredMixin, View):
pass
from django.contrib.auth.decorators import login_required
from django.contrib.auth.decorators import permission_required
@login_required
def list_books(request):
books = Book.objects.filter(user=request.user)
...
@login_required
@permission_required("books.change_book")
def update_book(request):
book_id = request.POST["book_id"]
book = Book.objects.get(user=request.user, pk=book_id)
...
Controles de acceso son muy fáciles de implementar y usar. Pero si son omitidos o implementados incorrectamente, pueden ser un gran problema.
Escribe tests por cada operación
urllib.parse
urllib.parse
from urllib.parse import urlparse
urlparse("https://example.com/path/to/file/?query#fragment")
ParseResult(
scheme="https",
netloc="example.com",
path="/path/to/file/",
params="",
query="query",
fragment="fragment",
)
urllib.parse
The urlsplit() and urlparse() APIs do not perform validation of inputs. They may not raise errors on inputs that other applications consider invalid. They may also succeed on some inputs that might not be considered URLs elsewhere. Their purpose is for practical functionality rather than purity.
https://docs.python.org/3/library/urllib.parse.html#url-parsing-security
URL | ||
---|---|---|
https://example.com | protocolo con dominio | |
https://docs.example.com | protocolo con sub-dominio | |
https://docs.example.example.com | protocolo con sub-dominio |
= urllib.parse | = browser |
URL | ||
---|---|---|
https://example.com. | protocolo con dominio | |
https://docs.example.com. | protocolo con dominio |
= urllib.parse | = browser |
URL | ||
---|---|---|
example.com | path relativo | |
/example.com | path absoluto | |
//example.com | protocolo relativo |
= urllib.parse | = browser |
URL | ||
---|---|---|
foo://example.com | URL con protocolo foo | |
mailto:[email protected] | Abrir cliente de email |
= urllib.parse | = browser |
URL | ||
---|---|---|
javascript:alert(document.domain) | Ejecutar JS | |
javascript://example.com/alert(document.domain) | Ejecutar JS (comentario) | |
javascript://example.com/%0Aalert(document.domain) | Ejecutar JS (comentario seguido de salto de línea) |
= urllib.parse | = browser |
URL | ||
---|---|---|
https:/{NEWLINE}/example.com | protocolo con dominio | |
https://example.{NEWLINE}com | protocolo con dominio | |
https://example.com/path{NEWLINE}to/file | protocolo con dominio |
= urllib.parse | = browser |
URL | ||
---|---|---|
https:/example.com | protocolo sin dominio | protocolo con dominio |
https://user:[email protected] | URL con basic auth | URL con basic auth |
= urllib.parse | = browser |
URL | ||
---|---|---|
\example.com | path relativo | path absoluto |
\\example.com | path relativo | dominio relativo |
/\example.com | path absoluto | dominio relativo |
https:\\example.com\path\to\file | Protocolo y path | Full URL |
= urllib.parse | = browser |
https://example.com/login/?next=https://evil.example.com
Es una vulnerabilidad que permite a un atacante inyectar código HTML en una página web. Usualmente esto permite al atacante ejecutar JS en el contexto de la página.
def index(request):
name = request.GET.get("name")
return HttpResponse(f"<h1>Hello, {name}!</h1>")
Uso incorrecto de las funciones de escape
https://docs.djangoproject.com/en/5.0/ref/utils/#django.utils.html.format_html
Confiar que ciertos tipos de datos no pueden contener código malicioso.
No poner entre comillas valores de atributos de los tags HTML
<p title={{ name }}>Hello, {{ name }}!</p>
Retornar una objecto HttpResponse
sin especificar el tipo de contenido.
Es una vulnerabilidad que permite a un atacante ejecutar comandos SQL en una base de datos.
cursor.execute(f"SELECT * FROM users WHERE username='{username}'")
Mal uso de queries parametrizadas
https://docs.djangoproject.com/en/5.1/topics/db/sql/#passing-parameters-into-raw
Confiar en que ciertos tipos de datos no pueden contener comandos SQL
Es una vulnerabilidad que permite a un atacante realizar peticiones a la red interna de la aplicación.
url = request.GET.get("url")
response = requests.get(url)
Es una vulnerabilidad que permite a un atacante ejecutar comandos arbitrarios en el sistema operativo.
domain = request.GET.get("domain")
os.system(f"ping -c 1 {domain}")
Es una vulnerabilidad que permite a un atacante que la evaluación de una expresión regular sea muy costosa.
https://redosdetector.com/
https://makenowjust-labs.github.io/recheck/playground/
Ni de las LLMs