Esempio n. 1
0
def layer_metadata(request, layername, template='layers/layer_metadata.html', ajax=True):
    layer = _resolve_layer(
        request,
        layername,
        'base.change_resourcebase_metadata',
        _PERMISSION_MSG_METADATA)
    layer_attribute_set = inlineformset_factory(
        Layer,
        Attribute,
        extra=0,
        form=LayerAttributeForm,
    )
    topic_category = layer.category

    poc = layer.poc
    metadata_author = layer.metadata_author

    # assert False, str(layer_bbox)
    config = layer.attribute_config()

    # Add required parameters for GXP lazy-loading
    layer_bbox = layer.bbox
    bbox = [float(coord) for coord in list(layer_bbox[0:4])]
    config["srs"] = getattr(settings, 'DEFAULT_MAP_CRS', 'EPSG:900913')
    config["bbox"] = bbox if config["srs"] != 'EPSG:900913' \
        else llbbox_to_mercator([float(coord) for coord in bbox])
    config["title"] = layer.title
    config["queryable"] = True

    if layer.storeType == "remoteStore":
        service = layer.service
        source_params = {
            "ptype": service.ptype,
            "remote": True,
            "url": service.base_url,
            "name": service.name}
        maplayer = GXPLayer(
            name=layer.typename,
            ows_url=layer.ows_url,
            layer_params=json.dumps(config),
            source_params=json.dumps(source_params))
    else:
        maplayer = GXPLayer(
            name=layer.typename,
            ows_url=layer.ows_url,
            layer_params=json.dumps(config))

    # Update count for popularity ranking,
    # but do not includes admins or resource owners
    if request.user != layer.owner and not request.user.is_superuser:
        Layer.objects.filter(
            id=layer.id).update(popular_count=F('popular_count') + 1)

    # center/zoom don't matter; the viewer will center on the layer bounds
    map_obj = GXPMap(projection=getattr(settings, 'DEFAULT_MAP_CRS', 'EPSG:900913'))

    NON_WMS_BASE_LAYERS = [
        la for la in default_map_config(request)[1] if la.ows_url is None]

    if request.method == "POST":
        if layer.metadata_uploaded_preserve:  # layer metadata cannot be edited
            out = {
                'success': False,
                'errors': METADATA_UPLOADED_PRESERVE_ERROR
            }
            return HttpResponse(
                json.dumps(out),
                content_type='application/json',
                status=400)

        layer_form = LayerForm(request.POST, instance=layer, prefix="resource")
        attribute_form = layer_attribute_set(
            request.POST,
            instance=layer,
            prefix="layer_attribute_set",
            queryset=Attribute.objects.order_by('display_order'))
        category_form = CategoryForm(
            request.POST,
            prefix="category_choice_field",
            initial=int(
                request.POST["category_choice_field"]) if "category_choice_field" in request.POST else None)
        tkeywords_form = TKeywordForm(
            request.POST,
            prefix="tkeywords")

    else:
        layer_form = LayerForm(instance=layer, prefix="resource")
        attribute_form = layer_attribute_set(
            instance=layer,
            prefix="layer_attribute_set",
            queryset=Attribute.objects.order_by('display_order'))
        category_form = CategoryForm(
            prefix="category_choice_field",
            initial=topic_category.id if topic_category else None)

        # Keywords from THESAURI management
        layer_tkeywords = layer.tkeywords.all()
        tkeywords_list = ''
        lang = 'en'  # TODO: use user's language
        if layer_tkeywords and len(layer_tkeywords) > 0:
            tkeywords_ids = layer_tkeywords.values_list('id', flat=True)
            if hasattr(settings, 'THESAURI'):
                for el in settings.THESAURI:
                    thesaurus_name = el['name']
                    try:
                        t = Thesaurus.objects.get(identifier=thesaurus_name)
                        for tk in t.thesaurus.filter(pk__in=tkeywords_ids):
                            tkl = tk.keyword.filter(lang=lang)
                            if len(tkl) > 0:
                                tkl_ids = ",".join(map(str, tkl.values_list('id', flat=True)))
                                tkeywords_list += "," + tkl_ids if len(tkeywords_list) > 0 else tkl_ids
                    except:
                        tb = traceback.format_exc()
                        logger.error(tb)

        tkeywords_form = TKeywordForm(
            prefix="tkeywords",
            initial={'tkeywords': tkeywords_list})

    if request.method == "POST" and layer_form.is_valid(
    ) and attribute_form.is_valid() and category_form.is_valid() and tkeywords_form.is_valid():
        new_poc = layer_form.cleaned_data['poc']
        new_author = layer_form.cleaned_data['metadata_author']

        if new_poc is None:
            if poc is None:
                poc_form = ProfileForm(
                    request.POST,
                    prefix="poc",
                    instance=poc)
            else:
                poc_form = ProfileForm(request.POST, prefix="poc")
            if poc_form.is_valid():
                if len(poc_form.cleaned_data['profile']) == 0:
                    # FIXME use form.add_error in django > 1.7
                    errors = poc_form._errors.setdefault('profile', ErrorList())
                    errors.append(_('You must set a point of contact for this resource'))
                    poc = None
            if poc_form.has_changed and poc_form.is_valid():
                new_poc = poc_form.save()

        if new_author is None:
            if metadata_author is None:
                author_form = ProfileForm(request.POST, prefix="author",
                                          instance=metadata_author)
            else:
                author_form = ProfileForm(request.POST, prefix="author")
            if author_form.is_valid():
                if len(author_form.cleaned_data['profile']) == 0:
                    # FIXME use form.add_error in django > 1.7
                    errors = author_form._errors.setdefault('profile', ErrorList())
                    errors.append(_('You must set an author for this resource'))
                    metadata_author = None
            if author_form.has_changed and author_form.is_valid():
                new_author = author_form.save()

        new_category = TopicCategory.objects.get(
            id=category_form.cleaned_data['category_choice_field'])

        for form in attribute_form.cleaned_data:
            la = Attribute.objects.get(id=int(form['id'].id))
            la.description = form["description"]
            la.attribute_label = form["attribute_label"]
            la.visible = form["visible"]
            la.display_order = form["display_order"]
            la.save()

        if new_poc is not None and new_author is not None:
            # layer.poc = new_poc
            # layer.metadata_author = new_author
            new_keywords = [x.strip() for x in layer_form.cleaned_data['keywords']]
            layer.keywords.clear()
            layer.keywords.add(*new_keywords)
            try:
                the_layer = layer_form.save()
            except:
                tb = traceback.format_exc()
                if tb:
                    logger.debug(tb)
                the_layer = layer

            up_sessions = UploadSession.objects.filter(layer=the_layer.id)
            if up_sessions.count() > 0 and up_sessions[0].user != the_layer.owner:
                up_sessions.update(user=the_layer.owner)
            Layer.objects.filter(id=the_layer.id).update(
                category=new_category
                )

            if getattr(settings, 'SLACK_ENABLED', False):
                try:
                    from geonode.contrib.slack.utils import build_slack_message_layer, send_slack_messages
                    send_slack_messages(build_slack_message_layer("layer_edit", the_layer))
                except:
                    print "Could not send slack message."

            if not ajax:
                return HttpResponseRedirect(
                    reverse(
                        'layer_detail',
                        args=(
                            layer.service_typename,
                        )))

        message = layer.typename

        try:
            # Keywords from THESAURI management
            tkeywords_to_add = []
            tkeywords_cleaned = tkeywords_form.clean()
            if tkeywords_cleaned and len(tkeywords_cleaned) > 0:
                tkeywords_ids = []
                for i, val in enumerate(tkeywords_cleaned):
                    try:
                        cleaned_data = [value for key, value
                                        in tkeywords_cleaned[i].items()
                                        if 'tkeywords-tkeywords' in key.lower() and 'autocomplete' not in key.lower()]
                        tkeywords_ids.extend(map(int, cleaned_data[0]))
                    except:
                        pass

                if hasattr(settings, 'THESAURI'):
                    for el in settings.THESAURI:
                        thesaurus_name = el['name']
                        try:
                            t = Thesaurus.objects.get(identifier=thesaurus_name)
                            for tk in t.thesaurus.all():
                                tkl = tk.keyword.filter(pk__in=tkeywords_ids)
                                if len(tkl) > 0:
                                    tkeywords_to_add.append(tkl[0].keyword_id)
                        except:
                            tb = traceback.format_exc()
                            logger.error(tb)

            layer.tkeywords.add(*tkeywords_to_add)
        except:
            tb = traceback.format_exc()
            logger.error(tb)

        return HttpResponse(json.dumps({'message': message}))

    if poc is not None:
        layer_form.fields['poc'].initial = poc.id
        poc_form = ProfileForm(prefix="poc")
        poc_form.hidden = True
    else:
        poc_form = ProfileForm(prefix="poc")
        poc_form.hidden = False

    if metadata_author is not None:
        layer_form.fields['metadata_author'].initial = metadata_author.id
        author_form = ProfileForm(prefix="author")
        author_form.hidden = True
    else:
        author_form = ProfileForm(prefix="author")
        author_form.hidden = False

    if 'access_token' in request.session:
        access_token = request.session['access_token']
    else:
        u = uuid.uuid1()
        access_token = u.hex

    viewer = json.dumps(
        map_obj.viewer_json(request.user, access_token, * (NON_WMS_BASE_LAYERS + [maplayer])))

    metadataxsl = False
    if "geonode.contrib.metadataxsl" in settings.INSTALLED_APPS:
        metadataxsl = True

    return render_to_response(template, RequestContext(request, {
        "resource": layer,
        "layer": layer,
        "layer_form": layer_form,
        "poc_form": poc_form,
        "author_form": author_form,
        "attribute_form": attribute_form,
        "category_form": category_form,
        "tkeywords_form": tkeywords_form,
        "viewer": viewer,
        "preview":  getattr(settings, 'LAYER_PREVIEW_LIBRARY', 'leaflet'),
        "crs":  getattr(settings, 'DEFAULT_MAP_CRS', 'EPSG:900913'),
        "metadataxsl": metadataxsl
    }))
Esempio n. 2
0
def document_metadata(
        request,
        docid,
        template='documents/document_metadata.html',
        ajax=True):

    document = None
    try:
        document = _resolve_document(
            request,
            docid,
            'base.change_resourcebase_metadata',
            _PERMISSION_MSG_METADATA)

    except Http404:
        return HttpResponse(
            loader.render_to_string(
                '404.html', context={
                }, request=request), status=404)

    except PermissionDenied:
        return HttpResponse(
            loader.render_to_string(
                '401.html', context={
                    'error_message': _("You are not allowed to edit this document.")}, request=request), status=403)

    if document is None:
        return HttpResponse(
            'An unknown error has occured.',
            content_type="text/plain",
            status=401
        )

    else:
        poc = document.poc
        metadata_author = document.metadata_author
        topic_category = document.category

        if request.method == "POST":
            document_form = DocumentForm(
                request.POST,
                instance=document,
                prefix="resource")
            category_form = CategoryForm(request.POST, prefix="category_choice_field", initial=int(
                request.POST["category_choice_field"]) if "category_choice_field" in request.POST and
                request.POST["category_choice_field"] else None)
            tkeywords_form = TKeywordForm(request.POST)
        else:
            document_form = DocumentForm(instance=document, prefix="resource")
            category_form = CategoryForm(
                prefix="category_choice_field",
                initial=topic_category.id if topic_category else None)

            # Keywords from THESAURUS management
            doc_tkeywords = document.tkeywords.all()
            tkeywords_list = ''
            lang = 'en'  # TODO: use user's language
            if doc_tkeywords and len(doc_tkeywords) > 0:
                tkeywords_ids = doc_tkeywords.values_list('id', flat=True)
                if hasattr(settings, 'THESAURUS') and settings.THESAURUS:
                    el = settings.THESAURUS
                    thesaurus_name = el['name']
                    try:
                        t = Thesaurus.objects.get(identifier=thesaurus_name)
                        for tk in t.thesaurus.filter(pk__in=tkeywords_ids):
                            tkl = tk.keyword.filter(lang=lang)
                            if len(tkl) > 0:
                                tkl_ids = ",".join(
                                    map(str, tkl.values_list('id', flat=True)))
                                tkeywords_list += "," + \
                                    tkl_ids if len(
                                        tkeywords_list) > 0 else tkl_ids
                    except Exception:
                        tb = traceback.format_exc()
                        logger.error(tb)

            tkeywords_form = TKeywordForm(instance=document)


        if request.method == "GET":
            print("TESTE NO LAYERS!!!")
            project = request.GET.get("list_projects")
            management_actions = request.GET.get("list_management_actions")
            if project:
                print("CLIQUEI EM PROJETO!!")
                settings.PROJETO_API = True
                settings.ACAO_GERENCIAL_API = False
            elif management_actions:
                print("CLIQUEI EM AÇÃO GERENCIAL")
                settings.ACAO_GERENCIAL_API = True
                settings.PROJETO_API = False

        if request.method == "POST" and document_form.is_valid(
        ) and category_form.is_valid():
            new_poc = document_form.cleaned_data['poc']
            new_author = document_form.cleaned_data['metadata_author']
            new_keywords = document_form.cleaned_data['keywords']
            new_regions = document_form.cleaned_data['regions']
            new_embrapa_keywords = document_form.cleaned_data['embrapa_keywords']
            new_embrapa_data_quality_statement = document_form.cleaned_data['embrapa_data_quality_statement']
            new_embrapa_authors = document_form.cleaned_data['embrapa_autores']

            new_category = None
            if category_form and 'category_choice_field' in category_form.cleaned_data and\
            category_form.cleaned_data['category_choice_field']:
                new_category = TopicCategory.objects.get(
                    id=int(category_form.cleaned_data['category_choice_field']))

            print("VIEWS DO DOCUMENTS!!")

            if new_poc is None:
                if poc is None:
                    poc_form = ProfileForm(
                        request.POST,
                        prefix="poc",
                        instance=poc)
                else:
                    poc_form = ProfileForm(request.POST, prefix="poc")
                if poc_form.is_valid():
                    if len(poc_form.cleaned_data['profile']) == 0:
                        # FIXME use form.add_error in django > 1.7
                        errors = poc_form._errors.setdefault(
                            'profile', ErrorList())
                        errors.append(
                            _('You must set a point of contact for this resource'))
                        poc = None
                if poc_form.has_changed and poc_form.is_valid():
                    new_poc = poc_form.save()

            if new_author is None:
                if metadata_author is None:
                    author_form = ProfileForm(request.POST, prefix="author",
                                              instance=metadata_author)
                else:
                    author_form = ProfileForm(request.POST, prefix="author")
                if author_form.is_valid():
                    if len(author_form.cleaned_data['profile']) == 0:
                        # FIXME use form.add_error in django > 1.7
                        errors = author_form._errors.setdefault(
                            'profile', ErrorList())
                        errors.append(
                            _('You must set an author for this resource'))
                        metadata_author = None
                if author_form.has_changed and author_form.is_valid():
                    new_author = author_form.save()

            document = document_form.instance
            if new_poc is not None and new_author is not None:
                document.poc = new_poc
                document.metadata_author = new_author

            document.embrapa_autores.clear()
            document.embrapa_autores.add(*new_embrapa_authors)
            document.embrapa_data_quality_statement.clear()
            document.embrapa_data_quality_statement.add(*new_embrapa_data_quality_statement)
            document.embrapa_keywords.clear()
            document.embrapa_keywords.add(*new_embrapa_keywords)
            document.keywords.clear()
            document.keywords.add(*new_keywords)
            document.regions.clear()
            document.regions.add(*new_regions)
            document.category = new_category
            document.save()
            document_form.save_many2many()

            register_event(request, EventType.EVENT_CHANGE_METADATA, document)
            if not ajax:
                return HttpResponseRedirect(
                    reverse(
                        'document_detail',
                        args=(
                            document.id,
                        )))

            message = document.id

            try:
                # Keywords from THESAURUS management
                # Rewritten to work with updated autocomplete
                if not tkeywords_form.is_valid():
                    return HttpResponse(json.dumps({'message': "Invalid thesaurus keywords"}, status_code=400))

                tkeywords_data = tkeywords_form.cleaned_data['tkeywords']

                thesaurus_setting = getattr(settings, 'THESAURUS', None)
                if thesaurus_setting:
                    tkeywords_data = tkeywords_data.filter(
                        thesaurus__identifier=thesaurus_setting['name']
                    )
                    document.tkeywords = tkeywords_data
            except Exception:
                tb = traceback.format_exc()
                logger.error(tb)

            return HttpResponse(json.dumps({'message': message}))

        # - POST Request Ends here -

        # Request.GET
        if poc is not None:
            # embrapa # 
            document_form.fields['poc'].initial = poc.id
            poc_form = ProfileForm(prefix="poc")
            poc_form.hidden = True

        if metadata_author is not None:
            document_form.fields['metadata_author'].initial = metadata_author.id
            author_form = ProfileForm(prefix="author")
            author_form.hidden = True

        metadata_author_groups = []
        if request.user.is_superuser or request.user.is_staff:
            metadata_author_groups = GroupProfile.objects.all()
        else:
            try:
                all_metadata_author_groups = chain(
                    request.user.group_list_all(),
                    GroupProfile.objects.exclude(
                        access="private").exclude(access="public-invite"))
            except Exception:
                all_metadata_author_groups = GroupProfile.objects.exclude(
                    access="private").exclude(access="public-invite")
            [metadata_author_groups.append(item) for item in all_metadata_author_groups
                if item not in metadata_author_groups]

        if settings.ADMIN_MODERATE_UPLOADS:
            if not request.user.is_superuser:
                document_form.fields['is_published'].widget.attrs.update(
                    {'disabled': 'true'})

                can_change_metadata = request.user.has_perm(
                    'change_resourcebase_metadata',
                    document.get_self_resource())
                try:
                    is_manager = request.user.groupmember_set.all().filter(role='manager').exists()
                except Exception:
                    is_manager = False
                if not is_manager or not can_change_metadata:
                    document_form.fields['is_approved'].widget.attrs.update(
                        {'disabled': 'true'})

        register_event(request, EventType.EVENT_VIEW_METADATA, document)
        return render(request, template, context={
            "resource": document,
            "document": document,
            "document_form": document_form,
            "poc_form": poc_form,
            "author_form": author_form,
            "category_form": category_form,
            "tkeywords_form": tkeywords_form,
            "metadata_author_groups": metadata_author_groups,
            "TOPICCATEGORY_MANDATORY": getattr(settings, 'TOPICCATEGORY_MANDATORY', False),
            "GROUP_MANDATORY_RESOURCES": getattr(settings, 'GROUP_MANDATORY_RESOURCES', False),
        })
Esempio n. 3
0
def document_metadata(request,
                      docid,
                      template='documents/document_metadata.html',
                      ajax=True):
    document = None
    try:
        document = _resolve_document(request, docid,
                                     'base.change_resourcebase_metadata',
                                     _PERMISSION_MSG_METADATA)
    except PermissionDenied:
        return HttpResponse(_("Not allowed"), status=403)
    except Exception:
        raise Http404(_("Not found"))
    if not document:
        raise Http404(_("Not found"))

    # Add metadata_author or poc if missing
    document.add_missing_metadata_author_or_poc()
    poc = document.poc
    metadata_author = document.metadata_author
    topic_category = document.category
    current_keywords = [keyword.name for keyword in document.keywords.all()]

    if request.method == "POST":
        document_form = DocumentForm(request.POST,
                                     instance=document,
                                     prefix="resource")
        category_form = CategoryForm(
            request.POST,
            prefix="category_choice_field",
            initial=int(request.POST["category_choice_field"])
            if "category_choice_field" in request.POST
            and request.POST["category_choice_field"] else None)

        if hasattr(settings, 'THESAURUS'):
            tkeywords_form = TKeywordForm(request.POST)
        else:
            tkeywords_form = ThesaurusAvailableForm(request.POST,
                                                    prefix='tkeywords')

    else:
        document_form = DocumentForm(instance=document, prefix="resource")
        document_form.disable_keywords_widget_for_non_superuser(request.user)
        category_form = CategoryForm(
            prefix="category_choice_field",
            initial=topic_category.id if topic_category else None)

        # Keywords from THESAURUS management
        doc_tkeywords = document.tkeywords.all()
        if hasattr(settings, 'THESAURUS') and settings.THESAURUS:
            warnings.warn(
                'The settings for Thesaurus has been moved to Model, \
            this feature will be removed in next releases', DeprecationWarning)
            tkeywords_list = ''
            lang = 'en'  # TODO: use user's language
            if doc_tkeywords and len(doc_tkeywords) > 0:
                tkeywords_ids = doc_tkeywords.values_list('id', flat=True)
                if hasattr(settings, 'THESAURUS') and settings.THESAURUS:
                    el = settings.THESAURUS
                    thesaurus_name = el['name']
                    try:
                        t = Thesaurus.objects.get(identifier=thesaurus_name)
                        for tk in t.thesaurus.filter(pk__in=tkeywords_ids):
                            tkl = tk.keyword.filter(lang=lang)
                            if len(tkl) > 0:
                                tkl_ids = ",".join(
                                    map(str, tkl.values_list('id', flat=True)))
                                tkeywords_list += f",{tkl_ids}" if len(
                                    tkeywords_list) > 0 else tkl_ids
                    except Exception:
                        tb = traceback.format_exc()
                        logger.error(tb)

            tkeywords_form = TKeywordForm(instance=document)
        else:
            tkeywords_form = ThesaurusAvailableForm(prefix='tkeywords')
            #  set initial values for thesaurus form
            for tid in tkeywords_form.fields:
                values = []
                values = [
                    keyword.id for keyword in doc_tkeywords
                    if int(tid) == keyword.thesaurus.id
                ]
                tkeywords_form.fields[tid].initial = values

    if request.method == "POST" and document_form.is_valid(
    ) and category_form.is_valid() and tkeywords_form.is_valid():
        new_poc = document_form.cleaned_data['poc']
        new_author = document_form.cleaned_data['metadata_author']
        new_keywords = current_keywords if request.keyword_readonly else document_form.cleaned_data[
            'keywords']
        new_regions = document_form.cleaned_data['regions']

        new_category = None
        if category_form and 'category_choice_field' in category_form.cleaned_data and \
                category_form.cleaned_data['category_choice_field']:
            new_category = TopicCategory.objects.get(
                id=int(category_form.cleaned_data['category_choice_field']))

        if new_poc is None:
            if poc is None:
                poc_form = ProfileForm(request.POST,
                                       prefix="poc",
                                       instance=poc)
            else:
                poc_form = ProfileForm(request.POST, prefix="poc")
            if poc_form.is_valid():
                if len(poc_form.cleaned_data['profile']) == 0:
                    # FIXME use form.add_error in django > 1.7
                    errors = poc_form._errors.setdefault(
                        'profile', ErrorList())
                    errors.append(
                        _('You must set a point of contact for this resource'))
            if poc_form.has_changed and poc_form.is_valid():
                new_poc = poc_form.save()

        if new_author is None:
            if metadata_author is None:
                author_form = ProfileForm(request.POST,
                                          prefix="author",
                                          instance=metadata_author)
            else:
                author_form = ProfileForm(request.POST, prefix="author")
            if author_form.is_valid():
                if len(author_form.cleaned_data['profile']) == 0:
                    # FIXME use form.add_error in django > 1.7
                    errors = author_form._errors.setdefault(
                        'profile', ErrorList())
                    errors.append(
                        _('You must set an author for this resource'))
            if author_form.has_changed and author_form.is_valid():
                new_author = author_form.save()

        document = document_form.instance
        resource_manager.update(document.uuid,
                                instance=document,
                                keywords=new_keywords,
                                regions=new_regions,
                                vals=dict(poc=new_poc or document.poc,
                                          metadata_author=new_author
                                          or document.metadata_author,
                                          category=new_category),
                                notify=True)
        resource_manager.set_thumbnail(document.uuid,
                                       instance=document,
                                       overwrite=False)
        document_form.save_many2many()

        register_event(request, EventType.EVENT_CHANGE_METADATA, document)
        url = hookset.document_detail_url(document)
        if not ajax:
            return HttpResponseRedirect(url)
        message = document.id

        try:
            # Keywords from THESAURUS management
            # Rewritten to work with updated autocomplete
            if not tkeywords_form.is_valid():
                return HttpResponse(
                    json.dumps({'message': "Invalid thesaurus keywords"},
                               status_code=400))

            thesaurus_setting = getattr(settings, 'THESAURUS', None)
            if thesaurus_setting:
                tkeywords_data = tkeywords_form.cleaned_data['tkeywords']
                tkeywords_data = tkeywords_data.filter(
                    thesaurus__identifier=thesaurus_setting['name'])
                document.tkeywords.set(tkeywords_data)
            elif Thesaurus.objects.all().exists():
                fields = tkeywords_form.cleaned_data
                document.tkeywords.set(tkeywords_form.cleanx(fields))

        except Exception:
            tb = traceback.format_exc()
            logger.error(tb)

        return HttpResponse(json.dumps({'message': message}))

    # - POST Request Ends here -

    # Request.GET
    if poc is not None:
        document_form.fields['poc'].initial = poc.id
        poc_form = ProfileForm(prefix="poc")
        poc_form.hidden = True

    if metadata_author is not None:
        document_form.fields['metadata_author'].initial = metadata_author.id
        author_form = ProfileForm(prefix="author")
        author_form.hidden = True

    metadata_author_groups = get_user_visible_groups(request.user)

    if settings.ADMIN_MODERATE_UPLOADS:
        if not request.user.is_superuser:
            can_change_metadata = request.user.has_perm(
                'change_resourcebase_metadata', document.get_self_resource())
            try:
                is_manager = request.user.groupmember_set.all().filter(
                    role='manager').exists()
            except Exception:
                is_manager = False
            if not is_manager or not can_change_metadata:
                if settings.RESOURCE_PUBLISHING:
                    document_form.fields['is_published'].widget.attrs.update(
                        {'disabled': 'true'})
                document_form.fields['is_approved'].widget.attrs.update(
                    {'disabled': 'true'})

    register_event(request, EventType.EVENT_VIEW_METADATA, document)
    return render(
        request,
        template,
        context={
            "resource":
            document,
            "document":
            document,
            "document_form":
            document_form,
            "poc_form":
            poc_form,
            "author_form":
            author_form,
            "category_form":
            category_form,
            "tkeywords_form":
            tkeywords_form,
            "metadata_author_groups":
            metadata_author_groups,
            "TOPICCATEGORY_MANDATORY":
            getattr(settings, 'TOPICCATEGORY_MANDATORY', False),
            "GROUP_MANDATORY_RESOURCES":
            getattr(settings, 'GROUP_MANDATORY_RESOURCES', False),
            "UI_MANDATORY_FIELDS":
            list(
                set(getattr(settings, 'UI_DEFAULT_MANDATORY_FIELDS', []))
                | set(getattr(settings, 'UI_REQUIRED_FIELDS', [])))
        })
Esempio n. 4
0
def map_metadata(request, mapid, template="maps/map_metadata.html", ajax=True):
    try:
        map_obj = _resolve_map(request, mapid,
                               "base.change_resourcebase_metadata",
                               _PERMISSION_MSG_VIEW)
    except PermissionDenied:
        return HttpResponse(MSG_NOT_ALLOWED, status=403)
    except Exception:
        raise Http404(MSG_NOT_FOUND)
    if not map_obj:
        raise Http404(MSG_NOT_FOUND)

    # Add metadata_author or poc if missing
    map_obj.add_missing_metadata_author_or_poc()
    current_keywords = [keyword.name for keyword in map_obj.keywords.all()]
    poc = map_obj.poc
    topic_thesaurus = map_obj.tkeywords.all()
    metadata_author = map_obj.metadata_author

    topic_category = map_obj.category

    if request.method == "POST":
        map_form = MapForm(request.POST,
                           instance=map_obj,
                           prefix="resource",
                           user=request.user)
        category_form = CategoryForm(
            request.POST,
            prefix="category_choice_field",
            initial=int(request.POST["category_choice_field"])
            if "category_choice_field" in request.POST
            and request.POST["category_choice_field"] else None)

        if hasattr(settings, 'THESAURUS'):
            tkeywords_form = TKeywordForm(request.POST)
        else:
            tkeywords_form = ThesaurusAvailableForm(request.POST,
                                                    prefix='tkeywords')
    else:
        map_form = MapForm(instance=map_obj,
                           prefix="resource",
                           user=request.user)
        map_form.disable_keywords_widget_for_non_superuser(request.user)
        category_form = CategoryForm(
            prefix="category_choice_field",
            initial=topic_category.id if topic_category else None)

        # Keywords from THESAURUS management
        map_tkeywords = map_obj.tkeywords.all()
        tkeywords_list = ''
        # Create THESAURUS widgets
        lang = 'en'
        if hasattr(settings, 'THESAURUS') and settings.THESAURUS:
            warnings.warn(
                'The settings for Thesaurus has been moved to Model, \
            this feature will be removed in next releases', DeprecationWarning)
            tkeywords_list = ''
            if map_tkeywords and len(map_tkeywords) > 0:
                tkeywords_ids = map_tkeywords.values_list('id', flat=True)
                if hasattr(settings, 'THESAURUS') and settings.THESAURUS:
                    el = settings.THESAURUS
                    thesaurus_name = el['name']
                    try:
                        t = Thesaurus.objects.get(identifier=thesaurus_name)
                        for tk in t.thesaurus.filter(pk__in=tkeywords_ids):
                            tkl = tk.keyword.filter(lang=lang)
                            if len(tkl) > 0:
                                tkl_ids = ",".join(
                                    map(str, tkl.values_list('id', flat=True)))
                                tkeywords_list += f",{tkl_ids}" if len(
                                    tkeywords_list) > 0 else tkl_ids
                    except Exception:
                        tb = traceback.format_exc()
                        logger.error(tb)

            tkeywords_form = TKeywordForm(instance=map_obj)
        else:
            tkeywords_form = ThesaurusAvailableForm(prefix='tkeywords')
            #  set initial values for thesaurus form
            for tid in tkeywords_form.fields:
                values = []
                values = [
                    keyword.id for keyword in topic_thesaurus
                    if int(tid) == keyword.thesaurus.id
                ]
                tkeywords_form.fields[tid].initial = values

    if request.method == "POST" and map_form.is_valid(
    ) and category_form.is_valid() and tkeywords_form.is_valid():

        new_poc = map_form.cleaned_data['poc']
        new_author = map_form.cleaned_data['metadata_author']
        new_keywords = current_keywords if request.keyword_readonly else map_form.cleaned_data[
            'keywords']
        new_regions = map_form.cleaned_data['regions']
        new_title = map_form.cleaned_data['title']
        new_abstract = map_form.cleaned_data['abstract']

        new_category = None
        if category_form and 'category_choice_field' in category_form.cleaned_data and\
                category_form.cleaned_data['category_choice_field']:
            new_category = TopicCategory.objects.get(
                id=int(category_form.cleaned_data['category_choice_field']))

        if new_poc is None:
            if poc is None:
                poc_form = ProfileForm(request.POST,
                                       prefix="poc",
                                       instance=poc)
            else:
                poc_form = ProfileForm(request.POST, prefix="poc")
            if poc_form.has_changed and poc_form.is_valid():
                new_poc = poc_form.save()

        if new_author is None:
            if metadata_author is None:
                author_form = ProfileForm(request.POST,
                                          prefix="author",
                                          instance=metadata_author)
            else:
                author_form = ProfileForm(request.POST, prefix="author")
            if author_form.has_changed and author_form.is_valid():
                new_author = author_form.save()

        if new_poc is not None and new_author is not None:
            map_obj.poc = new_poc
            map_obj.metadata_author = new_author
        map_obj.title = new_title
        map_obj.abstract = new_abstract
        map_obj.keywords.clear()
        map_obj.keywords.add(*new_keywords)
        map_obj.regions.clear()
        map_obj.regions.add(*new_regions)
        map_obj.category = new_category

        register_event(request, EventType.EVENT_CHANGE_METADATA, map_obj)
        if not ajax:
            return HttpResponseRedirect(hookset.map_detail_url(map_obj))

        message = map_obj.id

        try:
            # Keywords from THESAURUS management
            # Rewritten to work with updated autocomplete
            if not tkeywords_form.is_valid():
                return HttpResponse(
                    json.dumps({'message': "Invalid thesaurus keywords"},
                               status_code=400))

            thesaurus_setting = getattr(settings, 'THESAURUS', None)
            if thesaurus_setting:
                tkeywords_data = tkeywords_form.cleaned_data['tkeywords']
                tkeywords_data = tkeywords_data.filter(
                    thesaurus__identifier=thesaurus_setting['name'])
                map_obj.tkeywords.set(tkeywords_data)
            elif Thesaurus.objects.all().exists():
                fields = tkeywords_form.cleaned_data
                map_obj.tkeywords.set(tkeywords_form.cleanx(fields))

        except Exception:
            tb = traceback.format_exc()
            logger.error(tb)

        map_obj.save(notify=True)

        return HttpResponse(json.dumps({'message': message}))

    # - POST Request Ends here -

    # Request.GET
    if poc is None:
        poc_form = ProfileForm(request.POST, prefix="poc")
    else:
        map_form.fields['poc'].initial = poc.id
        poc_form = ProfileForm(prefix="poc")
        poc_form.hidden = True

    if metadata_author is None:
        author_form = ProfileForm(request.POST, prefix="author")
    else:
        map_form.fields['metadata_author'].initial = metadata_author.id
        author_form = ProfileForm(prefix="author")
        author_form.hidden = True

    layers = MapLayer.objects.filter(map=map_obj.id)

    metadata_author_groups = get_user_visible_groups(request.user)

    if settings.ADMIN_MODERATE_UPLOADS:
        if not request.user.is_superuser:
            can_change_metadata = request.user.has_perm(
                'change_resourcebase_metadata', map_obj.get_self_resource())
            try:
                is_manager = request.user.groupmember_set.all().filter(
                    role='manager').exists()
            except Exception:
                is_manager = False
            if not is_manager or not can_change_metadata:
                if settings.RESOURCE_PUBLISHING:
                    map_form.fields['is_published'].widget.attrs.update(
                        {'disabled': 'true'})
                map_form.fields['is_approved'].widget.attrs.update(
                    {'disabled': 'true'})

    register_event(request, EventType.EVENT_VIEW_METADATA, map_obj)
    return render(
        request,
        template,
        context={
            "resource":
            map_obj,
            "map":
            map_obj,
            "map_form":
            map_form,
            "poc_form":
            poc_form,
            "author_form":
            author_form,
            "category_form":
            category_form,
            "tkeywords_form":
            tkeywords_form,
            "layers":
            layers,
            "preview":
            getattr(settings, 'GEONODE_CLIENT_LAYER_PREVIEW_LIBRARY',
                    'mapstore'),
            "crs":
            getattr(settings, 'DEFAULT_MAP_CRS', 'EPSG:3857'),
            "metadata_author_groups":
            metadata_author_groups,
            "TOPICCATEGORY_MANDATORY":
            getattr(settings, 'TOPICCATEGORY_MANDATORY', False),
            "GROUP_MANDATORY_RESOURCES":
            getattr(settings, 'GROUP_MANDATORY_RESOURCES', False),
            "UI_MANDATORY_FIELDS":
            list(
                set(getattr(settings, 'UI_DEFAULT_MANDATORY_FIELDS', []))
                | set(getattr(settings, 'UI_REQUIRED_FIELDS', [])))
        })
Esempio n. 5
0
def map_metadata(request, mapid, template='maps/map_metadata.html', ajax=True):
    map_obj = _resolve_map(request, mapid, 'base.change_resourcebase_metadata',
                           _PERMISSION_MSG_VIEW)

    # Add metadata_author or poc if missing
    map_obj.add_missing_metadata_author_or_poc()
    current_keywords = [keyword.name for keyword in map_obj.keywords.all()]
    poc = map_obj.poc

    metadata_author = map_obj.metadata_author

    topic_category = map_obj.category

    if request.method == "POST":
        map_form = MapForm(request.POST, instance=map_obj, prefix="resource")
        category_form = CategoryForm(
            request.POST,
            prefix="category_choice_field",
            initial=int(request.POST["category_choice_field"])
            if "category_choice_field" in request.POST
            and request.POST["category_choice_field"] else None)
        tkeywords_form = TKeywordForm(request.POST)
    else:
        map_form = MapForm(instance=map_obj, prefix="resource")
        map_form.disable_keywords_widget_for_non_superuser(request.user)
        category_form = CategoryForm(
            prefix="category_choice_field",
            initial=topic_category.id if topic_category else None)

        # Keywords from THESAURUS management
        map_tkeywords = map_obj.tkeywords.all()
        tkeywords_list = ''
        lang = 'en'  # TODO: use user's language
        if map_tkeywords and len(map_tkeywords) > 0:
            tkeywords_ids = map_tkeywords.values_list('id', flat=True)
            if hasattr(settings, 'THESAURUS') and settings.THESAURUS:
                el = settings.THESAURUS
                thesaurus_name = el['name']
                try:
                    t = Thesaurus.objects.get(identifier=thesaurus_name)
                    for tk in t.thesaurus.filter(pk__in=tkeywords_ids):
                        tkl = tk.keyword.filter(lang=lang)
                        if len(tkl) > 0:
                            tkl_ids = ",".join(
                                map(str, tkl.values_list('id', flat=True)))
                            tkeywords_list += "," + \
                                tkl_ids if len(
                                    tkeywords_list) > 0 else tkl_ids
                except Exception:
                    tb = traceback.format_exc()
                    logger.error(tb)

        tkeywords_form = TKeywordForm(instance=map_obj)

    if request.method == "POST" and map_form.is_valid(
    ) and category_form.is_valid():
        new_poc = map_form.cleaned_data['poc']
        new_author = map_form.cleaned_data['metadata_author']
        new_keywords = current_keywords if request.keyword_readonly else map_form.cleaned_data[
            'keywords']
        new_regions = map_form.cleaned_data['regions']
        new_title = strip_tags(map_form.cleaned_data['title'])
        new_abstract = strip_tags(map_form.cleaned_data['abstract'])

        new_category = None
        if category_form and 'category_choice_field' in category_form.cleaned_data and\
                category_form.cleaned_data['category_choice_field']:
            new_category = TopicCategory.objects.get(
                id=int(category_form.cleaned_data['category_choice_field']))

        if new_poc is None:
            if poc is None:
                poc_form = ProfileForm(request.POST,
                                       prefix="poc",
                                       instance=poc)
            else:
                poc_form = ProfileForm(request.POST, prefix="poc")
            if poc_form.has_changed and poc_form.is_valid():
                new_poc = poc_form.save()

        if new_author is None:
            if metadata_author is None:
                author_form = ProfileForm(request.POST,
                                          prefix="author",
                                          instance=metadata_author)
            else:
                author_form = ProfileForm(request.POST, prefix="author")
            if author_form.has_changed and author_form.is_valid():
                new_author = author_form.save()

        if new_poc is not None and new_author is not None:
            map_obj.poc = new_poc
            map_obj.metadata_author = new_author
        map_obj.title = new_title
        map_obj.abstract = new_abstract
        map_obj.keywords.clear()
        map_obj.keywords.add(*new_keywords)
        map_obj.regions.clear()
        map_obj.regions.add(*new_regions)
        map_obj.category = new_category
        map_obj.save(notify=True)

        register_event(request, EventType.EVENT_CHANGE_METADATA, map_obj)
        if not ajax:
            return HttpResponseRedirect(
                reverse('map_detail', args=(map_obj.id, )))

        message = map_obj.id

        try:
            # Keywords from THESAURUS management
            # Rewritten to work with updated autocomplete
            if not tkeywords_form.is_valid():
                return HttpResponse(
                    json.dumps({'message': "Invalid thesaurus keywords"},
                               status_code=400))

            tkeywords_data = tkeywords_form.cleaned_data['tkeywords']

            thesaurus_setting = getattr(settings, 'THESAURUS', None)
            if thesaurus_setting:
                tkeywords_data = tkeywords_data.filter(
                    thesaurus__identifier=thesaurus_setting['name'])
                map_obj.tkeywords.set(tkeywords_data)
        except Exception:
            tb = traceback.format_exc()
            logger.error(tb)

        return HttpResponse(json.dumps({'message': message}))

    # - POST Request Ends here -

    # Request.GET
    if poc is None:
        poc_form = ProfileForm(request.POST, prefix="poc")
    else:
        map_form.fields['poc'].initial = poc.id
        poc_form = ProfileForm(prefix="poc")
        poc_form.hidden = True

    if metadata_author is None:
        author_form = ProfileForm(request.POST, prefix="author")
    else:
        map_form.fields['metadata_author'].initial = metadata_author.id
        author_form = ProfileForm(prefix="author")
        author_form.hidden = True

    config = map_obj.viewer_json(request)
    layers = MapLayer.objects.filter(map=map_obj.id)

    metadata_author_groups = []
    if request.user.is_superuser or request.user.is_staff:
        metadata_author_groups = GroupProfile.objects.all()
    else:
        try:
            all_metadata_author_groups = chain(
                request.user.group_list_all(),
                GroupProfile.objects.exclude(access="private").exclude(
                    access="public-invite"))
        except Exception:
            all_metadata_author_groups = GroupProfile.objects.exclude(
                access="private").exclude(access="public-invite")
        [
            metadata_author_groups.append(item)
            for item in all_metadata_author_groups
            if item not in metadata_author_groups
        ]

    if settings.ADMIN_MODERATE_UPLOADS:
        if not request.user.is_superuser:
            if settings.RESOURCE_PUBLISHING:
                map_form.fields['is_published'].widget.attrs.update(
                    {'disabled': 'true'})

            can_change_metadata = request.user.has_perm(
                'change_resourcebase_metadata', map_obj.get_self_resource())
            try:
                is_manager = request.user.groupmember_set.all().filter(
                    role='manager').exists()
            except Exception:
                is_manager = False
            if not is_manager or not can_change_metadata:
                map_form.fields['is_approved'].widget.attrs.update(
                    {'disabled': 'true'})

    register_event(request, EventType.EVENT_VIEW_METADATA, map_obj)
    return render(request,
                  template,
                  context={
                      "config":
                      json.dumps(config),
                      "resource":
                      map_obj,
                      "map":
                      map_obj,
                      "map_form":
                      map_form,
                      "poc_form":
                      poc_form,
                      "author_form":
                      author_form,
                      "category_form":
                      category_form,
                      "tkeywords_form":
                      tkeywords_form,
                      "layers":
                      layers,
                      "preview":
                      getattr(settings, 'GEONODE_CLIENT_LAYER_PREVIEW_LIBRARY',
                              'mapstore'),
                      "crs":
                      getattr(settings, 'DEFAULT_MAP_CRS', 'EPSG:3857'),
                      "metadata_author_groups":
                      metadata_author_groups,
                      "TOPICCATEGORY_MANDATORY":
                      getattr(settings, 'TOPICCATEGORY_MANDATORY', False),
                      "GROUP_MANDATORY_RESOURCES":
                      getattr(settings, 'GROUP_MANDATORY_RESOURCES', False),
                  })
Esempio n. 6
0
def layer_metadata(
        request,
        layername,
        template='layers/layer_metadata.html',
        ajax=True):
    layer = _resolve_layer(
        request,
        layername,
        'base.change_resourcebase_metadata',
        _PERMISSION_MSG_METADATA)
    layer_attribute_set = inlineformset_factory(
        Layer,
        Attribute,
        extra=0,
        form=LayerAttributeForm,
    )
    topic_category = layer.category

    poc = layer.poc
    metadata_author = layer.metadata_author

    # assert False, str(layer_bbox)
    config = layer.attribute_config()

    # Add required parameters for GXP lazy-loading
    layer_bbox = layer.bbox
    bbox = [float(coord) for coord in list(layer_bbox[0:4])]
    config["srs"] = getattr(settings, 'DEFAULT_MAP_CRS', 'EPSG:900913')
    config["bbox"] = bbox if config["srs"] != 'EPSG:900913' \
        else llbbox_to_mercator([float(coord) for coord in bbox])
    config["title"] = layer.title
    config["queryable"] = True

    if layer.storeType == "remoteStore":
        service = layer.service
        source_params = {
            "ptype": service.ptype,
            "remote": True,
            "url": service.base_url,
            "name": service.name}
        maplayer = GXPLayer(
            name=layer.alternate,
            ows_url=layer.ows_url,
            layer_params=json.dumps(config),
            source_params=json.dumps(source_params))
    else:
        maplayer = GXPLayer(
            name=layer.alternate,
            ows_url=layer.ows_url,
            layer_params=json.dumps(config))

    # Update count for popularity ranking,
    # but do not includes admins or resource owners
    if request.user != layer.owner and not request.user.is_superuser:
        Layer.objects.filter(
            id=layer.id).update(popular_count=F('popular_count') + 1)

    # center/zoom don't matter; the viewer will center on the layer bounds
    map_obj = GXPMap(
        projection=getattr(
            settings,
            'DEFAULT_MAP_CRS',
            'EPSG:900913'))

    NON_WMS_BASE_LAYERS = [
        la for la in default_map_config(request)[1] if la.ows_url is None]

    if request.method == "POST":
        if layer.metadata_uploaded_preserve:  # layer metadata cannot be edited
            out = {
                'success': False,
                'errors': METADATA_UPLOADED_PRESERVE_ERROR
            }
            return HttpResponse(
                json.dumps(out),
                content_type='application/json',
                status=400)

        layer_form = LayerForm(request.POST, instance=layer, prefix="resource")
        attribute_form = layer_attribute_set(
            request.POST,
            instance=layer,
            prefix="layer_attribute_set",
            queryset=Attribute.objects.order_by('display_order'))
        category_form = CategoryForm(request.POST, prefix="category_choice_field", initial=int(
            request.POST["category_choice_field"]) if "category_choice_field" in request.POST else None)
        tkeywords_form = TKeywordForm(
            request.POST,
            prefix="tkeywords")

    else:
        layer_form = LayerForm(instance=layer, prefix="resource")
        attribute_form = layer_attribute_set(
            instance=layer,
            prefix="layer_attribute_set",
            queryset=Attribute.objects.order_by('display_order'))
        category_form = CategoryForm(
            prefix="category_choice_field",
            initial=topic_category.id if topic_category else None)

        # Keywords from THESAURI management
        layer_tkeywords = layer.tkeywords.all()
        tkeywords_list = ''
        lang = 'en'  # TODO: use user's language
        if layer_tkeywords and len(layer_tkeywords) > 0:
            tkeywords_ids = layer_tkeywords.values_list('id', flat=True)
            if hasattr(settings, 'THESAURI'):
                for el in settings.THESAURI:
                    thesaurus_name = el['name']
                    try:
                        t = Thesaurus.objects.get(identifier=thesaurus_name)
                        for tk in t.thesaurus.filter(pk__in=tkeywords_ids):
                            tkl = tk.keyword.filter(lang=lang)
                            if len(tkl) > 0:
                                tkl_ids = ",".join(
                                    map(str, tkl.values_list('id', flat=True)))
                                tkeywords_list += "," + \
                                    tkl_ids if len(
                                        tkeywords_list) > 0 else tkl_ids
                    except BaseException:
                        tb = traceback.format_exc()
                        logger.error(tb)

        tkeywords_form = TKeywordForm(
            prefix="tkeywords",
            initial={'tkeywords': tkeywords_list})

    if request.method == "POST" and layer_form.is_valid() and attribute_form.is_valid(
    ) and category_form.is_valid() and tkeywords_form.is_valid():
        new_poc = layer_form.cleaned_data['poc']
        new_author = layer_form.cleaned_data['metadata_author']

        if new_poc is None:
            if poc is None:
                poc_form = ProfileForm(
                    request.POST,
                    prefix="poc",
                    instance=poc)
            else:
                poc_form = ProfileForm(request.POST, prefix="poc")
            if poc_form.is_valid():
                if len(poc_form.cleaned_data['profile']) == 0:
                    # FIXME use form.add_error in django > 1.7
                    errors = poc_form._errors.setdefault(
                        'profile', ErrorList())
                    errors.append(
                        _('You must set a point of contact for this resource'))
                    poc = None
            if poc_form.has_changed and poc_form.is_valid():
                new_poc = poc_form.save()

        if new_author is None:
            if metadata_author is None:
                author_form = ProfileForm(request.POST, prefix="author",
                                          instance=metadata_author)
            else:
                author_form = ProfileForm(request.POST, prefix="author")
            if author_form.is_valid():
                if len(author_form.cleaned_data['profile']) == 0:
                    # FIXME use form.add_error in django > 1.7
                    errors = author_form._errors.setdefault(
                        'profile', ErrorList())
                    errors.append(
                        _('You must set an author for this resource'))
                    metadata_author = None
            if author_form.has_changed and author_form.is_valid():
                new_author = author_form.save()

        new_category = TopicCategory.objects.get(
            id=category_form.cleaned_data['category_choice_field'])

        for form in attribute_form.cleaned_data:
            la = Attribute.objects.get(id=int(form['id'].id))
            la.description = form["description"]
            la.attribute_label = form["attribute_label"]
            la.visible = form["visible"]
            la.display_order = form["display_order"]
            la.save()

        if new_poc is not None or new_author is not None:
            if new_poc is not None:
                layer.poc = new_poc
            if new_author is not None:
                layer.metadata_author = new_author

        new_keywords = [x.strip() for x in layer_form.cleaned_data['keywords']]
        if new_keywords is not None:
            layer.keywords.clear()
            layer.keywords.add(*new_keywords)

        try:
            the_layer = layer_form.save()
        except BaseException:
            tb = traceback.format_exc()
            if tb:
                logger.debug(tb)
            the_layer = layer

        up_sessions = UploadSession.objects.filter(layer=the_layer.id)
        if up_sessions.count() > 0 and up_sessions[0].user != the_layer.owner:
            up_sessions.update(user=the_layer.owner)

        if new_category is not None:
            Layer.objects.filter(id=the_layer.id).update(
                category=new_category
            )

        if getattr(settings, 'SLACK_ENABLED', False):
            try:
                from geonode.contrib.slack.utils import build_slack_message_layer, send_slack_messages
                send_slack_messages(
                    build_slack_message_layer(
                        "layer_edit", the_layer))
            except BaseException:
                print "Could not send slack message."

        if not ajax:
            return HttpResponseRedirect(
                reverse(
                    'layer_detail',
                    args=(
                        layer.service_typename,
                    )))

        message = layer.alternate

        try:
            # Keywords from THESAURI management
            tkeywords_to_add = []
            tkeywords_cleaned = tkeywords_form.clean()
            if tkeywords_cleaned and len(tkeywords_cleaned) > 0:
                tkeywords_ids = []
                for i, val in enumerate(tkeywords_cleaned):
                    try:
                        cleaned_data = [value for key, value in tkeywords_cleaned[i].items(
                        ) if 'tkeywords-tkeywords' in key.lower() and 'autocomplete' not in key.lower()]
                        tkeywords_ids.extend(map(int, cleaned_data[0]))
                    except BaseException:
                        pass

                if hasattr(settings, 'THESAURI'):
                    for el in settings.THESAURI:
                        thesaurus_name = el['name']
                        try:
                            t = Thesaurus.objects.get(
                                identifier=thesaurus_name)
                            for tk in t.thesaurus.all():
                                tkl = tk.keyword.filter(pk__in=tkeywords_ids)
                                if len(tkl) > 0:
                                    tkeywords_to_add.append(tkl[0].keyword_id)
                        except BaseException:
                            tb = traceback.format_exc()
                            logger.error(tb)

            layer.tkeywords.add(*tkeywords_to_add)
        except BaseException:
            tb = traceback.format_exc()
            logger.error(tb)

        return HttpResponse(json.dumps({'message': message}))

    if settings.ADMIN_MODERATE_UPLOADS:
        if not request.user.is_superuser:
            layer_form.fields['is_published'].widget.attrs.update({'disabled': 'true'})
        if not request.user.is_superuser and not request.user.is_staff:
            can_change_metadata = request.user.has_perm(
                'change_resourcebase_metadata',
                layer.get_self_resource())
            try:
                is_manager = request.user.groupmember_set.all().filter(role='manager').exists()
            except:
                is_manager = False
            if not is_manager or not can_change_metadata:
                layer_form.fields['is_approved'].widget.attrs.update({'disabled': 'true'})

    if poc is not None:
        layer_form.fields['poc'].initial = poc.id
        poc_form = ProfileForm(prefix="poc")
        poc_form.hidden = True
    else:
        poc_form = ProfileForm(prefix="poc")
        poc_form.hidden = False

    if metadata_author is not None:
        layer_form.fields['metadata_author'].initial = metadata_author.id
        author_form = ProfileForm(prefix="author")
        author_form.hidden = True
    else:
        author_form = ProfileForm(prefix="author")
        author_form.hidden = False

    if 'access_token' in request.session:
        access_token = request.session['access_token']
    else:
        u = uuid.uuid1()
        access_token = u.hex

    viewer = json.dumps(map_obj.viewer_json(
        request.user, access_token, * (NON_WMS_BASE_LAYERS + [maplayer])))

    metadataxsl = False
    if "geonode.contrib.metadataxsl" in settings.INSTALLED_APPS:
        metadataxsl = True

    metadata_author_groups = []
    if request.user.is_superuser or request.user.is_staff:
        metadata_author_groups = GroupProfile.objects.all()
    else:
        all_metadata_author_groups = chain(
            request.user.group_list_all().distinct(),
            GroupProfile.objects.exclude(access="private").exclude(access="public-invite"))
        [metadata_author_groups.append(item) for item in all_metadata_author_groups
            if item not in metadata_author_groups]

    return render_to_response(template, RequestContext(request, {
        "resource": layer,
        "layer": layer,
        "layer_form": layer_form,
        "poc_form": poc_form,
        "author_form": author_form,
        "attribute_form": attribute_form,
        "category_form": category_form,
        "tkeywords_form": tkeywords_form,
        "viewer": viewer,
        "preview": getattr(settings, 'LAYER_PREVIEW_LIBRARY', 'leaflet'),
        "crs": getattr(settings, 'DEFAULT_MAP_CRS', 'EPSG:900913'),
        "metadataxsl": metadataxsl,
        "freetext_readonly": getattr(
            settings,
            'FREETEXT_KEYWORDS_READONLY',
            False),
        "metadata_author_groups": metadata_author_groups,
        "GROUP_MANDATORY_RESOURCES":
            getattr(settings, 'GROUP_MANDATORY_RESOURCES', False),
    }))
Esempio n. 7
0
def dataset_metadata(request,
                     layername,
                     template='datasets/dataset_metadata.html',
                     ajax=True):
    try:
        layer = _resolve_dataset(request, layername,
                                 'base.change_resourcebase_metadata',
                                 _PERMISSION_MSG_METADATA)
    except PermissionDenied as e:
        return HttpResponse(Exception(_("Not allowed"), e), status=403)
    except Exception as e:
        raise Http404(Exception(_("Not found"), e))
    if not layer:
        raise Http404(_("Not found"))

    dataset_attribute_set = inlineformset_factory(
        Dataset,
        Attribute,
        extra=0,
        form=LayerAttributeForm,
    )
    current_keywords = [keyword.name for keyword in layer.keywords.all()]
    topic_category = layer.category

    topic_thesaurus = layer.tkeywords.all()
    # Add metadata_author or poc if missing
    layer.add_missing_metadata_author_or_poc()

    poc = layer.poc
    metadata_author = layer.metadata_author

    # assert False, str(dataset_bbox)
    config = layer.attribute_config()

    # Add required parameters for GXP lazy-loading
    dataset_bbox = layer.bbox
    bbox = [float(coord) for coord in list(dataset_bbox[0:4])]
    if hasattr(layer, 'srid'):
        config['crs'] = {'type': 'name', 'properties': layer.srid}
    config["srs"] = getattr(settings, 'DEFAULT_MAP_CRS', 'EPSG:3857')
    config["bbox"] = bbox if config["srs"] != 'EPSG:3857' \
        else llbbox_to_mercator([float(coord) for coord in bbox])
    config["title"] = layer.title
    config["queryable"] = True

    # Update count for popularity ranking,
    # but do not includes admins or resource owners
    if request.user != layer.owner and not request.user.is_superuser:
        Dataset.objects.filter(id=layer.id).update(
            popular_count=F('popular_count') + 1)

    if request.method == "POST":
        if layer.metadata_uploaded_preserve:  # layer metadata cannot be edited
            out = {
                'success': False,
                'errors': METADATA_UPLOADED_PRESERVE_ERROR
            }
            return HttpResponse(json.dumps(out),
                                content_type='application/json',
                                status=400)

        thumbnail_url = layer.thumbnail_url
        dataset_form = DatasetForm(request.POST,
                                   instance=layer,
                                   prefix="resource",
                                   user=request.user)
        if not dataset_form.is_valid():
            logger.error(
                f"Dataset Metadata form is not valid: {dataset_form.errors}")
            out = {
                'success':
                False,
                'errors': [
                    f"{x}: {y[0].messages[0]}"
                    for x, y in dataset_form.errors.as_data().items()
                ]
            }
            return HttpResponse(json.dumps(out),
                                content_type='application/json',
                                status=400)
        if not layer.thumbnail_url:
            layer.thumbnail_url = thumbnail_url
        attribute_form = dataset_attribute_set(
            request.POST,
            instance=layer,
            prefix="dataset_attribute_set",
            queryset=Attribute.objects.order_by('display_order'))
        if not attribute_form.is_valid():
            logger.error(
                f"Dataset Attributes form is not valid: {attribute_form.errors}"
            )
            out = {
                'success':
                False,
                "errors": [
                    re.sub(re.compile('<.*?>'), '', str(err))
                    for err in attribute_form.errors
                ]
            }
            return HttpResponse(json.dumps(out),
                                content_type='application/json',
                                status=400)
        category_form = CategoryForm(
            request.POST,
            prefix="category_choice_field",
            initial=int(request.POST["category_choice_field"])
            if "category_choice_field" in request.POST
            and request.POST["category_choice_field"] else None)
        if not category_form.is_valid():
            logger.error(
                f"Dataset Category form is not valid: {category_form.errors}")
            out = {
                'success':
                False,
                'errors': [
                    re.sub(re.compile('<.*?>'), '', str(err))
                    for err in category_form.errors
                ]
            }
            return HttpResponse(json.dumps(out),
                                content_type='application/json',
                                status=400)
        if hasattr(settings, 'THESAURUS'):
            tkeywords_form = TKeywordForm(request.POST)
        else:
            tkeywords_form = ThesaurusAvailableForm(request.POST,
                                                    prefix='tkeywords')
            #  set initial values for thesaurus form
        if not tkeywords_form.is_valid():
            logger.error(
                f"Dataset Thesauri Keywords form is not valid: {tkeywords_form.errors}"
            )
            out = {
                'success':
                False,
                'errors': [
                    re.sub(re.compile('<.*?>'), '', str(err))
                    for err in tkeywords_form.errors
                ]
            }
            return HttpResponse(json.dumps(out),
                                content_type='application/json',
                                status=400)
    else:
        dataset_form = DatasetForm(instance=layer,
                                   prefix="resource",
                                   user=request.user)
        dataset_form.disable_keywords_widget_for_non_superuser(request.user)
        attribute_form = dataset_attribute_set(
            instance=layer,
            prefix="dataset_attribute_set",
            queryset=Attribute.objects.order_by('display_order'))
        category_form = CategoryForm(
            prefix="category_choice_field",
            initial=topic_category.id if topic_category else None)

        # Create THESAURUS widgets
        lang = settings.THESAURUS_DEFAULT_LANG if hasattr(
            settings, 'THESAURUS_DEFAULT_LANG') else 'en'
        if hasattr(settings, 'THESAURUS') and settings.THESAURUS:
            warnings.warn(
                'The settings for Thesaurus has been moved to Model, \
            this feature will be removed in next releases', DeprecationWarning)
            dataset_tkeywords = layer.tkeywords.all()
            tkeywords_list = ''
            if dataset_tkeywords and len(dataset_tkeywords) > 0:
                tkeywords_ids = dataset_tkeywords.values_list('id', flat=True)
                if hasattr(settings, 'THESAURUS') and settings.THESAURUS:
                    el = settings.THESAURUS
                    thesaurus_name = el['name']
                    try:
                        t = Thesaurus.objects.get(identifier=thesaurus_name)
                        for tk in t.thesaurus.filter(pk__in=tkeywords_ids):
                            tkl = tk.keyword.filter(lang=lang)
                            if len(tkl) > 0:
                                tkl_ids = ",".join(
                                    map(str, tkl.values_list('id', flat=True)))
                                tkeywords_list += f",{tkl_ids}" if len(
                                    tkeywords_list) > 0 else tkl_ids
                    except Exception:
                        tb = traceback.format_exc()
                        logger.error(tb)
            tkeywords_form = TKeywordForm(instance=layer)
        else:
            tkeywords_form = ThesaurusAvailableForm(prefix='tkeywords')
            #  set initial values for thesaurus form
            for tid in tkeywords_form.fields:
                values = []
                values = [
                    keyword.id for keyword in topic_thesaurus
                    if int(tid) == keyword.thesaurus.id
                ]
                tkeywords_form.fields[tid].initial = values

    if request.method == "POST" and dataset_form.is_valid(
    ) and attribute_form.is_valid() and category_form.is_valid(
    ) and tkeywords_form.is_valid():
        new_poc = dataset_form.cleaned_data['poc']
        new_author = dataset_form.cleaned_data['metadata_author']

        if new_poc is None:
            if poc is None:
                poc_form = ProfileForm(request.POST,
                                       prefix="poc",
                                       instance=poc)
            else:
                poc_form = ProfileForm(request.POST, prefix="poc")
            if poc_form.is_valid():
                if len(poc_form.cleaned_data['profile']) == 0:
                    # FIXME use form.add_error in django > 1.7
                    errors = poc_form._errors.setdefault(
                        'profile', ErrorList())
                    errors.append(
                        _('You must set a point of contact for this resource'))
                    poc = None
            if poc_form.has_changed and poc_form.is_valid():
                new_poc = poc_form.save()

        if new_author is None:
            if metadata_author is None:
                author_form = ProfileForm(request.POST,
                                          prefix="author",
                                          instance=metadata_author)
            else:
                author_form = ProfileForm(request.POST, prefix="author")
            if author_form.is_valid():
                if len(author_form.cleaned_data['profile']) == 0:
                    # FIXME use form.add_error in django > 1.7
                    errors = author_form._errors.setdefault(
                        'profile', ErrorList())
                    errors.append(
                        _('You must set an author for this resource'))
                    metadata_author = None
            if author_form.has_changed and author_form.is_valid():
                new_author = author_form.save()

        new_category = None
        if category_form and 'category_choice_field' in category_form.cleaned_data and\
                category_form.cleaned_data['category_choice_field']:
            new_category = TopicCategory.objects.get(
                id=int(category_form.cleaned_data['category_choice_field']))

        for form in attribute_form.cleaned_data:
            la = Attribute.objects.get(id=int(form['id'].id))
            la.description = form["description"]
            la.attribute_label = form["attribute_label"]
            la.visible = form["visible"]
            la.display_order = form["display_order"]
            la.featureinfo_type = form["featureinfo_type"]
            la.save()

        if new_poc is not None or new_author is not None:
            if new_poc is not None:
                layer.poc = new_poc
            if new_author is not None:
                layer.metadata_author = new_author

        new_keywords = current_keywords if request.keyword_readonly else dataset_form.cleaned_data[
            'keywords']
        new_regions = [x.strip() for x in dataset_form.cleaned_data['regions']]

        layer.keywords.clear()
        if new_keywords:
            layer.keywords.add(*new_keywords)
        layer.regions.clear()
        if new_regions:
            layer.regions.add(*new_regions)
        layer.category = new_category

        from geonode.upload.models import Upload

        up_sessions = Upload.objects.filter(
            resource_id=layer.resourcebase_ptr_id)
        if up_sessions.count() > 0 and up_sessions[0].user != layer.owner:
            up_sessions.update(user=layer.owner)

        register_event(request, EventType.EVENT_CHANGE_METADATA, layer)
        if not ajax:
            return HttpResponseRedirect(layer.get_absolute_url())

        message = layer.alternate

        try:
            if not tkeywords_form.is_valid():
                return HttpResponse(
                    json.dumps({'message': "Invalid thesaurus keywords"},
                               status_code=400))

            thesaurus_setting = getattr(settings, 'THESAURUS', None)
            if thesaurus_setting:
                tkeywords_data = tkeywords_form.cleaned_data['tkeywords']
                tkeywords_data = tkeywords_data.filter(
                    thesaurus__identifier=thesaurus_setting['name'])
                layer.tkeywords.set(tkeywords_data)
            elif Thesaurus.objects.all().exists():
                fields = tkeywords_form.cleaned_data
                layer.tkeywords.set(tkeywords_form.cleanx(fields))

        except Exception:
            tb = traceback.format_exc()
            logger.error(tb)

        resource_manager.update(
            layer.uuid,
            instance=layer,
            notify=True,
            extra_metadata=json.loads(
                dataset_form.cleaned_data['extra_metadata']))
        return HttpResponse(json.dumps({'message': message}))

    if settings.ADMIN_MODERATE_UPLOADS:
        if not request.user.is_superuser:
            can_change_metadata = request.user.has_perm(
                'change_resourcebase_metadata', layer.get_self_resource())
            try:
                is_manager = request.user.groupmember_set.all().filter(
                    role='manager').exists()
            except Exception:
                is_manager = False

            if not is_manager or not can_change_metadata:
                if settings.RESOURCE_PUBLISHING:
                    dataset_form.fields['is_published'].widget.attrs.update(
                        {'disabled': 'true'})
                dataset_form.fields['is_approved'].widget.attrs.update(
                    {'disabled': 'true'})

    if poc is not None:
        dataset_form.fields['poc'].initial = poc.id
        poc_form = ProfileForm(prefix="poc")
        poc_form.hidden = True
    else:
        poc_form = ProfileForm(prefix="poc")
        poc_form.hidden = False

    if metadata_author is not None:
        dataset_form.fields['metadata_author'].initial = metadata_author.id
        author_form = ProfileForm(prefix="author")
        author_form.hidden = True
    else:
        author_form = ProfileForm(prefix="author")
        author_form.hidden = False

    metadata_author_groups = get_user_visible_groups(request.user)

    register_event(request, 'view_metadata', layer)
    return render(
        request,
        template,
        context={
            "resource":
            layer,
            "dataset":
            layer,
            "dataset_form":
            dataset_form,
            "poc_form":
            poc_form,
            "author_form":
            author_form,
            "attribute_form":
            attribute_form,
            "category_form":
            category_form,
            "tkeywords_form":
            tkeywords_form,
            "preview":
            getattr(settings, 'GEONODE_CLIENT_LAYER_PREVIEW_LIBRARY',
                    'mapstore'),
            "crs":
            getattr(settings, 'DEFAULT_MAP_CRS', 'EPSG:3857'),
            "metadataxsl":
            getattr(settings, 'GEONODE_CATALOGUE_METADATA_XSL', True),
            "freetext_readonly":
            getattr(settings, 'FREETEXT_KEYWORDS_READONLY', False),
            "metadata_author_groups":
            metadata_author_groups,
            "TOPICCATEGORY_MANDATORY":
            getattr(settings, 'TOPICCATEGORY_MANDATORY', False),
            "GROUP_MANDATORY_RESOURCES":
            getattr(settings, 'GROUP_MANDATORY_RESOURCES', False),
            "UI_MANDATORY_FIELDS":
            list(
                set(getattr(settings, 'UI_DEFAULT_MANDATORY_FIELDS', []))
                | set(getattr(settings, 'UI_REQUIRED_FIELDS', [])))
        })
Esempio n. 8
0
def geoapp_metadata(request,
                    geoappid,
                    template='apps/app_metadata.html',
                    ajax=True):
    geoapp_obj = None
    try:
        geoapp_obj = _resolve_geoapp(request, geoappid,
                                     'base.change_resourcebase_metadata',
                                     _PERMISSION_MSG_METADATA)
    except PermissionDenied:
        return HttpResponse(_("Not allowed"), status=403)
    except Exception:
        raise Http404(_("Not found"))
    if not geoapp_obj:
        raise Http404(_("Not found"))

    # Add metadata_author or poc if missing
    geoapp_obj.add_missing_metadata_author_or_poc()
    poc = geoapp_obj.poc
    metadata_author = geoapp_obj.metadata_author
    topic_category = geoapp_obj.category
    current_keywords = [keyword.name for keyword in geoapp_obj.keywords.all()]

    if request.method == "POST":
        geoapp_form = GeoAppForm(request.POST,
                                 instance=geoapp_obj,
                                 prefix="resource")
        category_form = CategoryForm(
            request.POST,
            prefix="category_choice_field",
            initial=int(request.POST["category_choice_field"])
            if "category_choice_field" in request.POST
            and request.POST["category_choice_field"] else None)
        tkeywords_form = TKeywordForm(request.POST)
    else:
        geoapp_form = GeoAppForm(instance=geoapp_obj, prefix="resource")
        geoapp_form.disable_keywords_widget_for_non_superuser(request.user)
        category_form = CategoryForm(
            prefix="category_choice_field",
            initial=topic_category.id if topic_category else None)

        # Keywords from THESAURUS management
        doc_tkeywords = geoapp_obj.tkeywords.all()
        tkeywords_list = ''
        lang = 'en'  # TODO: use user's language
        if doc_tkeywords and len(doc_tkeywords) > 0:
            tkeywords_ids = doc_tkeywords.values_list('id', flat=True)
            if hasattr(settings, 'THESAURUS') and settings.THESAURUS:
                el = settings.THESAURUS
                thesaurus_name = el['name']
                try:
                    t = Thesaurus.objects.get(identifier=thesaurus_name)
                    for tk in t.thesaurus.filter(pk__in=tkeywords_ids):
                        tkl = tk.keyword.filter(lang=lang)
                        if len(tkl) > 0:
                            tkl_ids = ",".join(
                                map(str, tkl.values_list('id', flat=True)))
                            tkeywords_list += f",{tkl_ids}" if len(
                                tkeywords_list) > 0 else tkl_ids
                except Exception:
                    tb = traceback.format_exc()
                    logger.error(tb)

        tkeywords_form = TKeywordForm(instance=geoapp_obj)

    if request.method == "POST" and geoapp_form.is_valid(
    ) and category_form.is_valid():
        new_poc = geoapp_form.cleaned_data['poc']
        new_author = geoapp_form.cleaned_data['metadata_author']
        new_keywords = current_keywords if request.keyword_readonly else geoapp_form.cleaned_data[
            'keywords']
        new_regions = geoapp_form.cleaned_data['regions']

        new_category = None
        if category_form and 'category_choice_field' in category_form.cleaned_data and \
                category_form.cleaned_data['category_choice_field']:
            new_category = TopicCategory.objects.get(
                id=int(category_form.cleaned_data['category_choice_field']))

        if new_poc is None:
            if poc is None:
                poc_form = ProfileForm(request.POST,
                                       prefix="poc",
                                       instance=poc)
            else:
                poc_form = ProfileForm(request.POST, prefix="poc")
            if poc_form.is_valid():
                if len(poc_form.cleaned_data['profile']) == 0:
                    # FIXME use form.add_error in django > 1.7
                    errors = poc_form._errors.setdefault(
                        'profile', ErrorList())
                    errors.append(
                        _('You must set a point of contact for this resource'))
                    poc = None
            if poc_form.has_changed and poc_form.is_valid():
                new_poc = poc_form.save()

        if new_author is None:
            if metadata_author is None:
                author_form = ProfileForm(request.POST,
                                          prefix="author",
                                          instance=metadata_author)
            else:
                author_form = ProfileForm(request.POST, prefix="author")
            if author_form.is_valid():
                if len(author_form.cleaned_data['profile']) == 0:
                    # FIXME use form.add_error in django > 1.7
                    errors = author_form._errors.setdefault(
                        'profile', ErrorList())
                    errors.append(
                        _('You must set an author for this resource'))
                    metadata_author = None
            if author_form.has_changed and author_form.is_valid():
                new_author = author_form.save()

        geoapp_obj = geoapp_form.instance
        if new_poc is not None and new_author is not None:
            geoapp_obj.poc = new_poc
            geoapp_obj.metadata_author = new_author
        geoapp_obj.keywords.clear()
        geoapp_obj.keywords.add(*new_keywords)
        geoapp_obj.regions.clear()
        geoapp_obj.regions.add(*new_regions)
        geoapp_obj.category = new_category
        geoapp_obj.save(notify=True)

        register_event(request, EventType.EVENT_CHANGE_METADATA, geoapp_obj)
        if not ajax:
            return HttpResponseRedirect(
                reverse('geoapp_detail', args=(geoapp_obj.id, )))

        message = geoapp_obj.id

        try:
            # Keywords from THESAURUS management
            # Rewritten to work with updated autocomplete
            if not tkeywords_form.is_valid():
                return HttpResponse(
                    json.dumps({'message': "Invalid thesaurus keywords"},
                               status_code=400))

            tkeywords_data = tkeywords_form.cleaned_data['tkeywords']

            thesaurus_setting = getattr(settings, 'THESAURUS', None)
            if thesaurus_setting:
                tkeywords_data = tkeywords_data.filter(
                    thesaurus__identifier=thesaurus_setting['name'])
                geoapp_obj.tkeywords.set(tkeywords_data)
        except Exception:
            tb = traceback.format_exc()
            logger.error(tb)

        return HttpResponse(json.dumps({'message': message}))

    # - POST Request Ends here -

    # Request.GET
    if poc is not None:
        geoapp_form.fields['poc'].initial = poc.id
        poc_form = ProfileForm(prefix="poc")
        poc_form.hidden = True

    if metadata_author is not None:
        geoapp_form.fields['metadata_author'].initial = metadata_author.id
        author_form = ProfileForm(prefix="author")
        author_form.hidden = True

    metadata_author_groups = []
    if request.user.is_superuser or request.user.is_staff:
        metadata_author_groups = GroupProfile.objects.all()
    else:
        try:
            all_metadata_author_groups = chain(
                request.user.group_list_all(),
                GroupProfile.objects.exclude(access="private").exclude(
                    access="public-invite"))
        except Exception:
            all_metadata_author_groups = GroupProfile.objects.exclude(
                access="private").exclude(access="public-invite")
        [
            metadata_author_groups.append(item)
            for item in all_metadata_author_groups
            if item not in metadata_author_groups
        ]

    if settings.ADMIN_MODERATE_UPLOADS:
        if not request.user.is_superuser:
            can_change_metadata = request.user.has_perm(
                'change_resourcebase_metadata', geoapp_obj.get_self_resource())
            try:
                is_manager = request.user.groupmember_set.all().filter(
                    role='manager').exists()
            except Exception:
                is_manager = False
            if not is_manager or not can_change_metadata:
                if settings.RESOURCE_PUBLISHING:
                    geoapp_form.fields['is_published'].widget.attrs.update(
                        {'disabled': 'true'})
                geoapp_form.fields['is_approved'].widget.attrs.update(
                    {'disabled': 'true'})

    register_event(request, EventType.EVENT_VIEW_METADATA, geoapp_obj)
    return render(request,
                  template,
                  context={
                      "resource":
                      geoapp_obj,
                      "geoapp":
                      geoapp_obj,
                      "geoapp_form":
                      geoapp_form,
                      "poc_form":
                      poc_form,
                      "author_form":
                      author_form,
                      "category_form":
                      category_form,
                      "tkeywords_form":
                      tkeywords_form,
                      "metadata_author_groups":
                      metadata_author_groups,
                      "TOPICCATEGORY_MANDATORY":
                      getattr(settings, 'TOPICCATEGORY_MANDATORY', False),
                      "GROUP_MANDATORY_RESOURCES":
                      getattr(settings, 'GROUP_MANDATORY_RESOURCES', False),
                  })
Esempio n. 9
0
def geoapp_metadata(request, geoappid, template='apps/app_metadata.html', ajax=True):
    geoapp_obj = None
    try:
        geoapp_obj = _resolve_geoapp(
            request,
            geoappid,
            'base.change_resourcebase_metadata',
            _PERMISSION_MSG_METADATA)
    except PermissionDenied:
        return HttpResponse(_("Not allowed"), status=403)
    except Exception:
        raise Http404(_("Not found"))
    if not geoapp_obj:
        raise Http404(_("Not found"))

    # Add metadata_author or poc if missing
    geoapp_obj.add_missing_metadata_author_or_poc()
    poc = geoapp_obj.poc
    metadata_author = geoapp_obj.metadata_author
    topic_category = geoapp_obj.category.all()

    topic_thesaurus = geoapp_obj.tkeywords.all()

    if request.method == "POST":
        geoapp_form = GeoAppForm(
            request.POST,
            instance=geoapp_obj,
            prefix="resource")
        category_form = CategoryForm(request.POST, prefix="category_choice_field", initial=int(
            request.POST["category_choice_field"]) if "category_choice_field" in request.POST and
            request.POST["category_choice_field"] else [])
        region_form = RegionsForm(request.POST, prefix="region_choice_field",
            initial=(
                request.POST.getlist("region_choice_field") if "region_choice_field" in request.POST or
                request.POST.getlist("region_choice_field") else []))

        if hasattr(settings, 'THESAURUS'):
            tkeywords_form = TKeywordForm(request.POST)
        else:
            tkeywords_form = ThesaurusAvailableForm(request.POST, prefix='tkeywords')

    else:
        geoapp_form = GeoAppForm(instance=geoapp_obj, prefix="resource")
        geoapp_form.disable_keywords_widget_for_non_superuser(request.user)
        #  set initial values for category form
        ids = list(c.id for c in topic_category)
        category_form = CategoryForm(
            prefix="category_choice_field",
            initial=ids)
        region_list = list(r.id for r in geoapp_obj.regions.all())
        region_form = RegionsForm(
            prefix="region_choice_field",
            initial=region_list)

        # Create THESAURUS widgets
        lang = settings.THESAURUS_DEFAULT_LANG if hasattr(settings, 'THESAURUS_DEFAULT_LANG') else 'en'
        if hasattr(settings, 'THESAURUS') and settings.THESAURUS:
            warnings.warn('The settings for Thesaurus has been moved to Model, \
            this feature will be removed in next releases', DeprecationWarning)
            layer_tkeywords = geoapp_obj.tkeywords.all()
            tkeywords_list = ''
            if layer_tkeywords and len(layer_tkeywords) > 0:
                tkeywords_ids = layer_tkeywords.values_list('id', flat=True)
                if hasattr(settings, 'THESAURUS') and settings.THESAURUS:
                    el = settings.THESAURUS
                    thesaurus_name = el['name']
                    try:
                        t = Thesaurus.objects.get(identifier=thesaurus_name)
                        for tk in t.thesaurus.filter(pk__in=tkeywords_ids):
                            tkl = tk.keyword.filter(lang=lang)
                            if len(tkl) > 0:
                                tkl_ids = ",".join(
                                    map(str, tkl.values_list('id', flat=True)))
                                tkeywords_list += f",{tkl_ids}" if len(
                                    tkeywords_list) > 0 else tkl_ids
                    except Exception:
                        tb = traceback.format_exc()
                        logger.error(tb)
            tkeywords_form = TKeywordForm(instance=geoapp_obj)
        else:
            tkeywords_form = ThesaurusAvailableForm(prefix='tkeywords')
            #  set initial values for thesaurus form
            for tid in tkeywords_form.fields:
                values = []
                values = [keyword.id for keyword in topic_thesaurus if int(tid) == keyword.thesaurus.id]
                tkeywords_form.fields[tid].initial = values

    initial_thumb_url = geoapp_obj.thumbnail_url
    if request.method == "POST" and geoapp_form.is_valid() and tkeywords_form.is_valid():
        new_poc = geoapp_form.cleaned_data['poc']
        new_author = geoapp_form.cleaned_data['metadata_author']
        new_keywords = geoapp_form.cleaned_data['keywords']
        new_regions = [int(c.strip()) for c in request.POST.getlist('region_choice_field')]
        new_categories = [int(c.strip()) for c in request.POST.getlist('category_choice_field')]

        if new_poc is None:
            if poc is None:
                poc_form = ProfileForm(
                    request.POST,
                    prefix="poc",
                    instance=poc)
            else:
                poc_form = ProfileForm(request.POST, prefix="poc")
            if poc_form.is_valid():
                if len(poc_form.cleaned_data['profile']) == 0:
                    # FIXME use form.add_error in django > 1.7
                    errors = poc_form._errors.setdefault(
                        'profile', ErrorList())
                    errors.append(
                        _('You must set a point of contact for this resource'))
                    poc = None
            if poc_form.has_changed and poc_form.is_valid():
                new_poc = poc_form.save()

        if new_author is None:
            if metadata_author is None:
                author_form = ProfileForm(request.POST, prefix="author",
                                          instance=metadata_author)
            else:
                author_form = ProfileForm(request.POST, prefix="author")
            if author_form.is_valid():
                if len(author_form.cleaned_data['profile']) == 0:
                    # FIXME use form.add_error in django > 1.7
                    errors = author_form._errors.setdefault(
                        'profile', ErrorList())
                    errors.append(
                        _('You must set an author for this resource'))
                    metadata_author = None
            if author_form.has_changed and author_form.is_valid():
                new_author = author_form.save()

        geoapp_obj = geoapp_form.instance
        if new_poc is not None and new_author is not None:
            geoapp_obj.poc = new_poc
            geoapp_obj.metadata_author = new_author

        if initial_thumb_url and not geoapp_obj.thumbnail_url:
            geoapp_obj.thumbnail_url = initial_thumb_url

        geoapp_obj.keywords.clear()
        geoapp_obj.keywords.add(*new_keywords)
        geoapp_obj.regions.clear()
        geoapp_obj.regions.add(*new_regions)
        geoapp_obj.category.clear()
        geoapp_obj.category.add(*new_categories)
        geoapp_obj.save(notify=True)

        register_event(request, EventType.EVENT_CHANGE_METADATA, geoapp_obj)
        if not ajax:
            return HttpResponseRedirect(
                reverse(
                    'geoapp_detail',
                    args=(
                        geoapp_obj.id,
                    )))

        try:
            # Keywords from THESAURUS management
            # Rewritten to work with updated autocomplete
            if not tkeywords_form.is_valid():
                return HttpResponse(json.dumps({'message': "Invalid thesaurus keywords"}, status_code=400))

            thesaurus_setting = getattr(settings, 'THESAURUS', None)
            if thesaurus_setting:
                tkeywords_data = tkeywords_form.cleaned_data['tkeywords']
                tkeywords_data = tkeywords_data.filter(
                    thesaurus__identifier=thesaurus_setting['name']
                )
                geoapp_obj.tkeywords.set(tkeywords_data)
            elif Thesaurus.objects.all().exists():
                fields = tkeywords_form.cleaned_data
                geoapp_obj.tkeywords.set(tkeywords_form.cleanx(fields))

        except Exception:
            tb = traceback.format_exc()
            logger.error(tb)

        return HttpResponse(json.dumps({'message': "Metadata has been updated"}))

    # - POST Request Ends here -

    # Request.GET
    if poc is not None:
        geoapp_form.fields['poc'].initial = poc.id
        poc_form = ProfileForm(prefix="poc")
        poc_form.hidden = True

    if metadata_author is not None:
        geoapp_form.fields['metadata_author'].initial = metadata_author.id
        author_form = ProfileForm(prefix="author")
        author_form.hidden = True

    metadata_author_groups = []
    if request.user.is_superuser or request.user.is_staff:
        metadata_author_groups = GroupProfile.objects.all()
    else:
        try:
            all_metadata_author_groups = chain(
                request.user.group_list_all(),
                GroupProfile.objects.exclude(
                    access="private").exclude(access="public-invite"))
        except Exception:
            all_metadata_author_groups = GroupProfile.objects.exclude(
                access="private").exclude(access="public-invite")
        [metadata_author_groups.append(item) for item in all_metadata_author_groups
            if item not in metadata_author_groups]

    if settings.ADMIN_MODERATE_UPLOADS:
        if not request.user.is_superuser:
            can_change_metadata = request.user.has_perm(
                'change_resourcebase_metadata',
                geoapp_obj.get_self_resource())
            try:
                is_manager = request.user.groupmember_set.all().filter(role='manager').exists()
            except Exception:
                is_manager = False
            if not is_manager or not can_change_metadata:
                if settings.RESOURCE_PUBLISHING:
                    geoapp_form.fields['is_published'].widget.attrs.update(
                        {'disabled': 'true'})
                geoapp_form.fields['is_approved'].widget.attrs.update(
                    {'disabled': 'true'})

    register_event(request, EventType.EVENT_VIEW_METADATA, geoapp_obj)
    return render(request, template, context={
        "resource": geoapp_obj,
        "geoapp": geoapp_obj,
        "geoapp_form": geoapp_form,
        "poc_form": poc_form,
        "author_form": author_form,
        "category_form": category_form,
        "region_form": region_form,
        "tkeywords_form": tkeywords_form,
        "metadata_author_groups": metadata_author_groups,
        "TOPICCATEGORY_MANDATORY": getattr(settings, 'TOPICCATEGORY_MANDATORY', False),
        "GROUP_MANDATORY_RESOURCES": getattr(settings, 'GROUP_MANDATORY_RESOURCES', False),
        "UI_MANDATORY_FIELDS": list(
            set(getattr(settings, 'UI_DEFAULT_MANDATORY_FIELDS', []))
            |
            set(getattr(settings, 'UI_REQUIRED_FIELDS', []))
        )
    })