image field in models

Good evening,
in a models.py I have an image field

Photo = models.ImageField(upload_to='Contributors/', blank=True, default='Site/Mamozio.png')

On insertion, if I don’t choose the image, it stores the default one
I would need 2 clarifications:

  1. When I choose the image, if it is already present it duplicates the image for me, instead of using the one already present
  2. If I enter the form to edit some field, when I save it stores the default photo image for me.

Am I doing something wrong or is this the right behavior ?

If you’re talking about a “file upload” selection box on an HTML form, that is correct, When you select a file to be uploaded, Django has no idea that you’re trying to reference an existing file.

To determine what is happening here, we’d need to see the form and the view involved with this process.

This is the code of the models

Photo = models.ImageField(upload_to='Contributors/', blank=True, default='Site/Mamozio.png')

This the view

class CollaboratorsModiView(View):
    template_name = 'Site/CollaboratorsModi.html'

    def get(self, request, pk):
        collaborator = get_object_or_404(Collaborators, pk=pk)
        form = CollaboratorsForm(instance=collaborator)
        return(request, self.template_name, {'form': form, 'collaborator': collaborator})

    def post(self, request, pk):
        collaborator = get_object_or_404(Collaborators, pk=pk)
        form = CollaboratorsForm(request.POST, request.FILES,instance=collaborator)
        form.instance.pk = pk # Add this line to make sure the ID remains unchanged
        if form.is_valid():
            # It is used to not make the save by update to some fields yet.
            # form.save(commit=False).
            # print('Code value after validation:', form.cleaned_data.get('Description'))
            # when no photo is inserted, store the link to the Base file.
            if 'Photo' in request.FILES:
                contributor.Photo = request.FILES['Photo']
            else:
                # If no new image has been provided, keep the default value
                contributor.Photo = 'Site/Mamozio.png'
            form.save()
            messages.success(request,
                             f “Edit COLLABORATOR ‘{form.cleaned_data.get(’Master Data‘)}’ saved successfully.”)
            return redirect('CollaboratorsList')
        else:
            print(“The form is invalid. errors:”, form.errors)
            messages.error(request, “The form is invalid. Errors: ”, form.errors)
            print(“The form is invalid. Errors:”, form.errors)
            print('pk ', pk)
            return(request, self.template_name, {'form': form, 'collaborator': collaborator})

This the html for the input

    {% if form.Foto.value %}
    <p class=“col3”>
        <img src=“{{ form.Foto.value.url }}” alt=“Foto Collaboratore” title=“Foto Collaboratore” width=“150” height=“150”>
        {{ form.Foto }}

        <label for=“{{ form.Curricolo.id_for_label }}”> Curricolo: </label>
        {{ form.Curricolo }}
    </p>
    {% else %}
        <p class=“col3”>
            {{ form.Foto }}
        </p>
    {% endif %}

What does the form look like?

I didn’t understand the question.
Do I have to give you the code of CollaboratorsForms ?

Yes, that’s the other part of this process that we haven’t seen yet.

Below is the code for the Collaborators Form

from django import forms
from Sito.models import Collaborators

class CollaboratorsForm(forms.ModelForm):
    class Meta:
        model = Collaborators
        fields = '__all__'
        widgets = {
            'Master Data': forms.TextInput(attrs={'autofocus': True, 'class': 'form-control', 'placeholder': 'MANDATORY'}),
            'MunicipalityID': forms.Select(attrs={'class': '', 'placeholder': 'MANDATORY', 'onchange': "municipalityChoice('Collaborators')"}),
        }
        error_messages = {
            'Master Data': {
                'required': 'Code field is required.'
                # Other custom error messages.
            },
            # Other form fields
        }

    # ... Checks that the same code does not already exist in INSERT.
    # in Variation check that there is not another instance with the same COIDCE
    def clean_anagrafica(self):
        registry = self.cleaned_data.get('Registry').
        # Get the instance currently being edited
        instance_being_edited = getattr(self, 'instance', None)
        # Check only if you are editing an existing instance
        if instance_being_edited and Collaborators.objects.exclude(pk=instance_being_edited.pk).filter(
                                                            Instance_being_edited).exists():
            # Add the error message to the specified key in the errors dictionary
            self.errors['Master'] = self.error_class(["Master already exists."])
            # Remove 'Code' field from cleaned_data to avoid problems with saving
            of the self.cleaned_data['Master data']
        return master data

The first thing I notice is that you show that you have this in your model:

And your view references this:

But your template has references to Foto:

Sorry I don’t know why in the template I didn’t translate it.
The field in Italian is Photo, translated into English Photo
Everywhere I always use the field Foto (translated Photo), it doesn’t depend on that

I’m sorry, I’m not following you here.

It’s going to be best if you either correct your original post, or repost your code, to show the code exactly as you’re trying to run it. (Without trying to translate anything.)

Models

Foto = models.ImageField(upload_to='Collaboratori/', blank=True, default='Sito/Mamozio.png')

Form

from django import forms
from Sito.models import Collaboratori


class CollaboratoriForm(forms.ModelForm):
    class Meta:
        model = Collaboratori
        fields = '__all__'
        widgets = {
            'Anagrafica': forms.TextInput(attrs={'autofocus': True, 'class': 'form-control', 'placeholder': 'OBBLIGATORIO'}),
            'ComuneID': forms.Select(attrs={'class': '', 'placeholder': "OBBLIGATORIO", 'onchange': "comuneScelta('Collaboratori')"}),
        }
        error_messages = {
            'Anagrafica': {
                'required': 'Il campo Codice è obbligatorio.',
                # Altri messaggi di errore personalizzati
            },
            # Altri campi del form
        }

    # ... Controlla che non esista già lo stesso codice in INSERIMENTO
    #       in Variazione controlla che non ci sia un'altra istanza con lo stesso COIDCE
    def clean_anagrafica(self):
        anagrafica = self.cleaned_data.get('Anagrafica')
        # Ottieni l'istanza attualmente in modifica
        instance_being_edited = getattr(self, 'instance', None)
        # Controlla solo se stai modificando un'istanza esistente
        if instance_being_edited and Collaboratori.objects.exclude(pk=instance_being_edited.pk).filter(
                                                            Anagrafica=anagrafica).exists():
            # Aggiungi il messaggio di errore alla chiave specifica nel dizionario errors
            self.errors['Anagrafica'] = self.error_class(["Anagrafica già presente."])
            # Rimuovi il campo 'Codice' dal cleaned_data per evitare problemi di salvataggio
            del self.cleaned_data['Anagrafica']
        return anagrafica

View

from django.contrib import messages
from django.shortcuts import render, get_object_or_404, redirect
from django.urls import reverse
from django.views.generic import ListView, View

from Sito.models import Collaboratori
from Sito.forms.CollaboratoriForm import CollaboratoriForm


class CollaboratoriListaView(ListView):
    model = Collaboratori
    template_name = 'Sito/CollaboratoriLista.html'
    context_object_name = 'collaboratori'


    def get_queryset(self):
        # Se il campo di Ricerca é usato ritorna i Movimenti filtrati, altrimenti ritorna tutti i Movimenti
        query = self.request.GET.get('q', '')

        if query:  # Se c'è un inpu t di ricerca, filtra i risultati
            # print('query ', query, AllenamentiSchede.objects.filter(ClienteID__Anagrafica__icontains=query))
            return Collaboratori.objects.filter(Anagrafica__icontains=query)
        else:  # Altrimenti, restituisci tutti i movimenti
            return Collaboratori.objects.all()

    def get_context_data(self, **kwargs):
        context = super().get_context_data(**kwargs)
        context['messaggio'] = "Non ci sono Anagrafiche. Crea una nuova Anagrafica." if not context['collaboratori'] else None
        return context


class CollaboratoriInseView(View):
    template_name = 'Sito/CollaboratoriInse.html'

    def get(self, request):
        form = CollaboratoriForm()
        return render(request, self.template_name, {'form': form})

    def post(self, request):
        form = CollaboratoriForm(request.POST, request.FILES)
        if form.is_valid():
            collaboratore = form.save(commit=False)
            # comune.Anagrafica = request.Anagrafica
            # Quando non viene inserita la foto, memorizza il link al file di Base
            if 'Foto' in request.FILES:
                collaboratore.Foto = request.FILES['Foto']
            else:
                # Se nessuna nuova immagine è stata fornita, mantieni il valore predefinito
                collaboratore.Foto = 'Sito/Mamozio.png'
            collaboratore.save()
            # Aggiungi un messaggio di successo
            messages.success(request, f"SALVATO ANAGRAFICA '{Collaboratori.Anagrafica}' ")
            # Azzerare i campi del form
            form = CollaboratoriForm()
        else:
            # Stampa tutti gli errori dei campi del form nel terminale
            for field, errors in form.errors.items():
                messages.error(request, f"Errore nel campo {field}: {', '.join(errors)}")
                print(f"Errore nel campo {field}: {', '.join(errors)}")

            # Visualizza un messaggio di errore generico nella console
            print("Errore nel form. Controlla la console per dettagli.")
            # return HttpResponseBadRequest("Errore nel form. Controlla la console per dettagli.")

        # Redirect alla stessa pagina
        # return redirect('CollaboratoriInse', pk=collaboratore.pk)
        return redirect('CollaboratoriInse')


class CollaboratoriModiView(View):
    template_name = 'Sito/CollaboratoriModi.html'

    def get(self, request, pk):
        collaboratore = get_object_or_404(Collaboratori, pk=pk)
        form = CollaboratoriForm(instance=collaboratore)
        return render(request, self.template_name, {'form': form, 'collaboratore': collaboratore})

    def post(self, request, pk):
        collaboratore = get_object_or_404(Collaboratori, pk=pk)
        form = CollaboratoriForm(request.POST, request.FILES,instance=collaboratore)
        form.instance.pk = pk  # Aggiungi questa riga per assicurarti che l'ID rimanga invariato
        if form.is_valid():
            # Serve per non effettuare ancora il salvataggio per aggiornamento ad alcuni campi
            # form.save(commit=False)
            # print('Valore di Codice dopo la validazione:', form.cleaned_data.get('Descrizione'))
            # Quando non viene inserita la foto, memorizza il link al file di Base
            if 'Foto' in request.FILES:
                collaboratore.Foto = request.FILES['Foto']
            else:
                # Se nessuna nuova immagine è stata fornita, mantieni il valore predefinito
                collaboratore.Foto = 'Sito/Mamozio.png'
            form.save()
            messages.success(request,
                             f"Modifica COLLABORATORE '{form.cleaned_data.get('Anagrafica')}' salvata con successo.")
            return redirect('CollaboratoriLista')
        else:
            print("Il form non è valido. Errori:", form.errors)
            messages.error(request, "Il form non è valido. Errori: ", form.errors)
            print("Il form non è valido. Errori:", form.errors)
            print('pk ', pk)
            return render(request, self.template_name, {'form': form, 'collaboratore': collaboratore})


class CollaboratoriVisuView(View):
    template_name = 'Sito/CollaboratoriVisu.html'

    def get(self, request, pk):
        collaboratore = get_object_or_404(Collaboratori, pk=pk)
        return render(request, self.template_name, {'collaboratore': collaboratore})


class CollaboratoriCancView(View):
    template_name = 'CollaboratoriLista'

    def get(self, request, pk):
        collaboratore = get_object_or_404(Collaboratori, pk=pk)
        # Salva i dettagli del comune prima della cancellazione
        collaboratore = {'ID': collaboratore.id,
                   'Campo': collaboratore.Anagrafica}  # Sostituisci 'Campo' con il nome del campo desiderato

        # Cancella il Movimento
        collaboratore.delete()

        # Aggiungi un messaggio di conferma
        messages.success(request,
                         f'COLLABORATORI {collaboratore["ID"]} - {collaboratore["Campo"]} è stata cancellata con successo.')

        # Reindirizza l'utente alla Lista dopo la cancellazione
        return redirect(reverse(self.template_name))

HTML

<!--<div  class="form-tabella">-->
<div class="grid-col3">
    <p class="span3Iniz">
        ID: <span class="padreID"> {{ collaboratore.pk }} </span>
        <label for="{{ form.NonAttivo.id_for_label }}"> Non Attivo: </label>
        {{ form.NonAttivo }}   {{ form.NonAttivo.errors }}
    </p>

    <p class="col1">
        <label for="{{ form.Anagrafica.id_for_label }}"> Anagrafica: </label>
    </p>
    <p class="col2">
        {{ form.Anagrafica }} {{ form.Anagrafica.errors }}
    </p>

    <p class="col1">
        <label for="{{ form.Sesso.id_for_label }}"> Sesso: </label>
    </p>
    <p class="col2">
        {{ form.Sesso }}
    </p>

    <p class="col1">
        <label for="{{ form.Indirizzo.id_for_label }}"> Indirizzo:</label>
    </p>
    {{ form.Indirizzo }}

    <p class="col1">
        <label for="{{ form.Comune.id_for_label }}"> Comune:</label>
    </p>
        {{ form.ComuneID }} {{ form.ComuneID.errors }}
        <label for="{{ form.Cap.id_for_label }}"> CAP:</label>
        <div class="campoDiFianco">
            {{ form.Cap }}
            <label for="{{ form.Prov.id_for_label }}"> Prov: </label>
            <span id="prov-co" class="campo-collegato"> {{ Prov }} </span>
        </div>

    <p class="col1">
        <label for="{{ form.CodFiscale.id_for_label }}"> Cod. Fiscale:</label>
    </p>
    <div class="campoDiFianco">
        {{ form.CodFiscale }}
        <label for="{{ form.PartitaIva.id_for_label }}"> Partita Iva:</label>
        {{ form.PartitaIva }}
    </div>

    <p class="col1">
        <label for="{{ form.Telefono.id_for_label }}"> Telefono: </label>
    </p>
    <div class="campoDiFianco">
        {{ form.Telefono }}
        <label for="{{ form.Cellulare.id_for_label }}"> Cellulare: </label>
        {{ form.Cellulare }}
    </div>

    <p class="col1">
        <label for="{{ form.eMail.id_for_label }}"> eMail: </label>
    </p>
        <div class="campoDiFianco">
            {{ form.eMail }}
            <label for="{{ form.PEC.id_for_label }}"> PEC: </label>
            {{ form.PEC }}
        </div>

    <p class="col1">
        <label for="{{ form.Ruolo.id_for_label }}"> Ruolo: </label>
    </p>
    {{ form.Ruolo }}

    {% if form.Foto.value %}
        <p class="col3">
            <img src="{{ form.Foto.value.url }}" alt="Foto Collaboratore" title="Foto Collaboratore" width="150" height="150">
            {{ form.Foto }}

            <label for="{{ form.Curricolo.id_for_label }}"> Curricolo: </label>
<!--            {{ form.Curricolo }}-->
        </p>

    {% else %}
        <p class="col3">
            {{ form.Foto }}
        </p>
    {% endif %}


    <!--        <div class="AnnuSalva">-->
    <p class="col1-2">
        <!-- Bottone ANNULLA -->
        <a href="/Sito/Collaboratori"> Annulla </a>
        <!-- Bottone SALVA -->
        <input type="submit" value="Salva">
    </p>

</div>

Briefly - I am unable to recreate the symptoms you are describing based upon the information provided here so far.

I do not see a <form ... tag in the portion of the html you have posted here. Is there more in this form that you are not showing?

Also, is there any JavaScript interacting with this page?