Estou tentando definir um re_path no Django que capture todas as URLs, exceto aquelas que começam com /admin/. Meu objetivo é redirecionar URLs desconhecidas para uma visualização personalizada (RedirectView), ao mesmo tempo em que garanto que todas as URLs de administração (incluindo subcaminhos como /admin/mymodel/something/) sejam excluídas.
from django.urls import re_path, path
from django.contrib import admin
from . import views
urlpatterns = [
path('admin/', admin.site.urls), # Ensure Django admin URLs are handled
]
# Catch-all pattern that should exclude /admin/ URLs
urlpatterns += [
re_path(r"^.*/(?!admin/$)[^/]+/$", views.RedirectView.as_view(), name="my-view"),
]
Emitir :
URLs como localhost:8000/admin/mymodel/something/ são ignoradas corretamente, o que é bom.
No entanto, URLs de segmento único como localhost:8000/something/ não estão sendo correspondidas, mesmo que devessem ser redirecionadas.
O que
new_pattern
está abaixo pode resolver o problema:PADRÕES
Demonstração do original_pattern: https://regex101.com/r/fp5aYg/1
Demonstração para new_pattern: https://regex101.com/r/2AWQcK/5
NOTAS
O
new_pattern
pode começar com qualquer caractere que não seja barra ou nenhum caractere. A primeira barra/
não deve ser seguida poradmin/
. Cada barra/
deve ser seguida por pelo menos um ou mais caracteres que não sejam barra[^/]+
seguidos por uma barra/
:/([^/]+/)+
. A string DEVE terminar em uma barra/$
. Deve haver pelo menos duas barras na string separadas por um caractere que não seja barra. Por exemplo, a correspondência não corresponderá a strings com duas barras consecutivas como estas://something//something//
, ousomething/something//something
^[^/]*
Comece no início da string. Capture 0 ou mais caracteres que não sejam barras, ou seja[^/]
, combine tudo antes da primeira barra/
./
a primeira barra.(?!admin/)
A primeira barra não pode ser seguida poradmin/
(?:...)+
Grupo não capturador (?:...)
que se repete 1 ou mais vezes (+
).[^/\n]+
Capture qualquer caractere que não seja barra para frente[^/]
, caractere que não seja quebra de linha\n
1 ou mais vezes. (Observação: tive que adicionar o caractere de quebra de linha\n
para que a demonstração de várias linhas funcionasse corretamente.)[^/\n]+/
Uma sequência de caracteres sem barra é seguida por uma barra/
.$
O fim da string$
segue a segunda ou posterior barra/$
.CADEIAS DE TESTE:
PARTIDAS:
NÃO-JOGOS:
ajuste seu re_path que deve excluir URLs /admin/
A boa notícia é que o Django combina caminhos de cima para baixo. Então, se o caminho for um,
admin/…
ele primeiro procurará poradmin.site.urls
. A menos que você defina o.final_catch_all_view
atributo [Django-doc] do site de administração comoFalse
, ele tem um catchall que manipulará todos os caminhos comcode/
.Você pode então usar um catchall com:
Eu também incluiria uma barra final para deixar a lógica [Django-doc] do Django primeiro fazer algum trabalho se o caminho não tiver barra final. Mas se não tiver, você pode removê-la.
APPEND_SLASH