from django . contrib import admin
from django . db import models
from django . forms import widgets , ModelForm
from django . core . exceptions import ValidationError
from polymorphic . admin import PolymorphicParentModelAdmin , PolymorphicChildModelAdmin , PolymorphicChildModelFilter
from solo . admin import SingletonModelAdmin
from django . utils . safestring import mark_safe
from seminar . utils import hlavni_problem
# Todo: reversion
import seminar . models as m
import seminar . treelib as tl
admin . site . register ( m . Rocnik )
class CisloForm ( ModelForm ) :
class Meta :
model = m . Cislo
fields = ' __all__ '
def clean ( self ) :
if self . cleaned_data . get ( ' verejne_db ' ) == False :
return self . cleaned_data
# cn = m.CisloNode.objects.get(cislo=self.instance)
# errors = []
# for ch in tl.all_children(cn):
# if isinstance(ch, m.TemaVCisleNode):
# if ch.tema.stav not in \
# (m.Problem.STAV_ZADANY, m.Problem.STAV_VYRESENY):
# errors.append(ValidationError('Téma %(tema)s není zadané ani vyřešené', params={'tema':ch.tema}))
#
# if isinstance(ch, m.UlohaZadaniNode) or isinstance(ch, m.UlohaVzorakNode):
# if ch.uloha.stav not in \
# (m.Problem.STAV_ZADANY, m.Problem.STAV_VYRESENY):
# errors.append(ValidationError('Úloha %(uloha)s není zadaná ani vyřešená', params={'uloha':ch.uloha}))
# if isinstance(ch, m.ReseniNode):
# for problem in ch.reseni.problem_set:
# if problem not in \
# (m.Problem.STAV_ZADANY, m.Problem.STAV_VYRESENY):
# errors.append(ValidationError('Problém %s není zadaný ani vyřešený', code=problem))
# if errors:
# errors.append(ValidationError(mark_safe('<b>Pokud chceš učinit všechny problémy, co nejsou zadané ani vyřešené, zadanými a číslo zveřejnit, můžeš to udělat pomocí akce v <a href="/admin/seminar/cislo">seznamu čísel</a></b>')))
# raise ValidationError(errors)
errors = [ ]
for ch in m . Uloha . objects . filter ( cislo_zadani = self . instance ) :
if ch . stav not in ( m . Problem . STAV_ZADANY , m . Problem . STAV_VYRESENY ) :
errors . append (
ValidationError ( ' Úloha %(uloha)s není zadaná ani vyřešená ' , params = { ' uloha ' : ch } ) )
if errors :
errors . append ( ValidationError ( mark_safe (
' <b>Pokud chceš učinit všechny problémy, co nejsou zadané ani vyřešené, zadanými a číslo zveřejnit, můžeš to udělat pomocí akce v <a href= " /admin/seminar/cislo " >seznamu čísel</a></b> ' ) ) )
raise ValidationError ( errors )
return self . cleaned_data
@admin . register ( m . Cislo )
class CisloAdmin ( admin . ModelAdmin ) :
form = CisloForm
actions = [ ' force_publish ' ]
def force_publish ( self , request , queryset ) :
for cislo in queryset :
# cn = m.CisloNode.objects.get(cislo=cislo)
# for ch in tl.all_children(cn):
# if isinstance(ch, m.TemaVCisleNode):
# if ch.tema.stav not in (m.Problem.STAV_ZADANY, m.Problem.STAV_VYRESENY):
# ch.tema.stav = m.Problem.STAV_ZADANY
# ch.tema.save()
#
# if isinstance(ch, m.UlohaZadaniNode) or isinstance(ch, m.UlohaVzorakNode):
# if ch.uloha.stav not in (m.Problem.STAV_ZADANY, m.Problem.STAV_VYRESENY):
# ch.uloha.stav = m.Problem.STAV_ZADANY
# ch.uloha.save()
# if isinstance(ch, m.ReseniNode):
# for problem in ch.reseni.problem_set:
# if problem not in (m.Problem.STAV_ZADANY, m.Problem.STAV_VYRESENY):
# problem.stav = m.Problem.STAV_ZADANY
# problem.save()
for ch in m . Uloha . objects . filter ( cislo_zadani = cislo ) :
if ch . stav not in ( m . Problem . STAV_ZADANY , m . Problem . STAV_VYRESENY ) :
ch . stav = m . Problem . STAV_ZADANY
ch . save ( )
hp = hlavni_problem ( ch )
if hp . stav not in ( m . Problem . STAV_ZADANY , m . Problem . STAV_VYRESENY ) :
hp . stav = m . Problem . STAV_ZADANY
hp . save ( )
# TODO Řešení, vzoráky?
# TODO Konfera/Článek?
cislo . verejne_db = True
cislo . save ( )
force_publish . short_description = ' Zveřejnit vybraná čísla a všechny návrhy úloh v nich učinit zadanými '
@admin . register ( m . Problem )
class ProblemAdmin ( PolymorphicParentModelAdmin ) :
base_model = m . Problem
child_models = [
m . Tema ,
m . Clanek ,
m . Uloha ,
m . Konfera ,
]
# Pokud chceme orezavat na aktualni rocnik, musime do modelu pridat odkaz na rocnik. Zatim bere vse.
search_fields = [ ' nazev ' ]
# V ProblemAdmin to nejde, protoze se to nepropise do deti
class ProblemAdminMixin ( object ) :
show_in_index = True
autocomplete_fields = [ ' nadproblem ' , ' autor ' , ' garant ' ]
filter_horizontal = [ ' opravovatele ' ]
@admin . register ( m . Tema )
class TemaAdmin ( ProblemAdminMixin , PolymorphicChildModelAdmin ) :
base_model = m . Tema
@admin . register ( m . Clanek )
class ClanekAdmin ( ProblemAdminMixin , PolymorphicChildModelAdmin ) :
base_model = m . Clanek
@admin . register ( m . Uloha )
class UlohaAdmin ( ProblemAdminMixin , PolymorphicChildModelAdmin ) :
base_model = m . Uloha
@admin . register ( m . Konfera )
class KonferaAdmin ( ProblemAdminMixin , PolymorphicChildModelAdmin ) :
base_model = m . Konfera
class TextAdminInline ( admin . TabularInline ) :
model = m . Text
formfield_overrides = {
models . TextField : { ' widget ' : widgets . TextInput }
}
exclude = [ ' text_zkraceny_set ' , ' text_zkraceny ' ]
admin . site . register ( m . Text )
class ResitelInline ( admin . TabularInline ) :
model = m . Resitel
extra = 1
admin . site . register ( m . Pohadka )
admin . site . register ( m . Obrazek )
# Polymorfismus pro stromy
# TODO: Inlines podle https://django-polymorphic.readthedocs.io/en/stable/admin.html
@admin . register ( m . TreeNode )
class TreeNodeAdmin ( PolymorphicParentModelAdmin ) :
base_model = m . TreeNode
child_models = [
m . RocnikNode ,
m . CisloNode ,
m . MezicisloNode ,
m . TemaVCisleNode ,
m . UlohaZadaniNode ,
m . PohadkaNode ,
m . UlohaVzorakNode ,
m . TextNode ,
m . CastNode ,
m . OrgTextNode ,
]
actions = [ ' aktualizuj_nazvy ' ]
# XXX: nejspíš je to totální DB HOG, nechcete to použít moc často.
def aktualizuj_nazvy ( self , request , queryset ) :
newqs = queryset . get_real_instances ( )
for tn in newqs :
tn . aktualizuj_nazev ( )
tn . save ( )
self . message_user ( request , " Názvy aktualizovány. " )
aktualizuj_nazvy . short_description = " Aktualizuj vybraným TreeNodům názvy "
@admin . register ( m . RocnikNode )
class RocnikNodeAdmin ( PolymorphicChildModelAdmin ) :
base_model = m . RocnikNode
show_in_index = True
@admin . register ( m . CisloNode )
class CisloNodeAdmin ( PolymorphicChildModelAdmin ) :
base_model = m . CisloNode
show_in_index = True
@admin . register ( m . MezicisloNode )
class MezicisloNodeAdmin ( PolymorphicChildModelAdmin ) :
base_model = m . MezicisloNode
show_in_index = True
@admin . register ( m . TemaVCisleNode )
class TemaVCisleNodeAdmin ( PolymorphicChildModelAdmin ) :
base_model = m . TemaVCisleNode
show_in_index = True
@admin . register ( m . UlohaZadaniNode )
class UlohaZadaniNodeAdmin ( PolymorphicChildModelAdmin ) :
base_model = m . UlohaZadaniNode
show_in_index = True
@admin . register ( m . PohadkaNode )
class PohadkaNodeAdmin ( PolymorphicChildModelAdmin ) :
base_model = m . PohadkaNode
show_in_index = True
@admin . register ( m . UlohaVzorakNode )
class UlohaVzorakNodeAdmin ( PolymorphicChildModelAdmin ) :
base_model = m . UlohaVzorakNode
show_in_index = True
@admin . register ( m . TextNode )
class TextNodeAdmin ( PolymorphicChildModelAdmin ) :
base_model = m . TextNode
show_in_index = True
@admin . register ( m . CastNode )
class TextNodeAdmin ( PolymorphicChildModelAdmin ) :
base_model = m . CastNode
show_in_index = True
fields = ( ' nadpis ' , )
@admin . register ( m . OrgTextNode )
class TextNodeAdmin ( PolymorphicChildModelAdmin ) :
base_model = m . OrgTextNode
show_in_index = True
admin . site . register ( m . Nastaveni , SingletonModelAdmin )
admin . site . register ( m . Novinky )