# For copyright and license terms, see COPYRIGHT.rst (top level of repository)
# Repository: https://github.com/C3S/collecting_society_web
import logging
import colander
import deform
from portal_web.views.forms.datatables import (
    DatatableSequence,
    DatatableSequenceWidget
)
from ....models import Artist
log = logging.getLogger(__name__)
[docs]
def prepare_ignored(value):
    # workaround for conditinally required fields, as form validators are not
    # processed, if a normal required field is missing
    return value if value else "IGNORED" 
[docs]
def prepare_required(value):
    # oid required for add/edit
    if value['mode'] != "create" and value['oid'] == "IGNORED":
        value['oid'] = ""
    # code required for add/edit
    if value['mode'] != "create" and value['code'] == "IGNORED":
        value['code'] = ""
    # email required for create/edit
    if value['mode'] != "add" and value['email'] == "IGNORED":
        value['email'] = ""
    return value 
# --- Fields ------------------------------------------------------------------
@colander.deferred
def artist_sequence_widget(node, kw):
    request = kw['request']
    # get initial source data
    domain = []
    if getattr(node, 'group', None):
        domain.append(('group', '=', node.group))
    artists = Artist.search(
        domain=domain,
        offset=0,
        limit=10,
        order=[('name', 'asc')])
    source_data = [{
        'name': artist.name,
        'code': artist.code,
        'oid': artist.oid,
        'description': artist.description,
        'mode':
            Artist.is_foreign_editable(request.web_user, artist)
            and 'edit' or 'add',
    } for artist in artists]
    # get statistics
    total_domain = []
    if getattr(node, 'group', None):
        total_domain.append(('group', '=', node.group))
    total = Artist.search_count(total_domain)
    # return widget
    return DatatableSequenceWidget(
        request=kw.get('request'),
        template='datatables/artist_sequence',
        source_data=source_data,
        source_data_total=total
    )
[docs]
class ModeField(colander.SchemaNode):
    oid = "mode"
    schema_type = colander.String
    widget = deform.widget.HiddenWidget()
    validator = colander.OneOf(
        ['add', 'create', 'edit']) 
[docs]
class OidField(colander.SchemaNode):
    oid = "oid"
    schema_type = colander.String
    widget = deform.widget.HiddenWidget()
    preparer = [prepare_ignored]
    validator = colander.Any(
        colander.uuid,
        colander.Regex(r'^IGNORED\Z', '')
    ) 
[docs]
class NameField(colander.SchemaNode):
    oid = "name"
    schema_type = colander.String
    widget = deform.widget.TextInputWidget() 
[docs]
class CodeField(colander.SchemaNode):
    oid = "code"
    schema_type = colander.String
    widget = deform.widget.HiddenWidget()
    preparer = [prepare_ignored]
    validator = colander.Any(
        colander.Regex(r'^A\d{10}\Z'),
        colander.Regex(r'^IGNORED\Z', '')
    ) 
[docs]
class DescriptionField(colander.SchemaNode):
    oid = "description"
    schema_type = colander.String
    widget = deform.widget.HiddenWidget()
    missing = "" 
[docs]
class EmailField(colander.SchemaNode):
    oid = "email"
    schema_type = colander.String
    widget = deform.widget.TextInputWidget()
    preparer = [prepare_ignored]
    validator = colander.Any(
        colander.Email(),
        colander.Regex(r'^IGNORED\Z', '')
    ) 
# --- Schemas -----------------------------------------------------------------
[docs]
class ArtistSchema(colander.Schema):
    mode = ModeField()
    oid = OidField()
    name = NameField()
    description = DescriptionField()
    code = CodeField()
    email = EmailField()
    preparer = [prepare_required]
    title = "" 
[docs]
class ArtistSequence(DatatableSequence):
    artist_sequence = ArtistSchema()
    widget = artist_sequence_widget 
[docs]
class ArtistIndividual(ArtistSequence):
    min_len = 1
    max_len = 1