5

I've got this system where I want to add in a favoriting feature where when someone clicks on the like button on a card it gets saved and displayed at port/wishlist.html but not able to go about and solve it, here is my Github Repository and some main codes.

homepage picture

models.py

from django.db import models
from django.contrib.auth.models import User
import datetime

YEAR_CHOICES = []
for r in range(1980, (datetime.datetime.now().year + 1)):
    YEAR_CHOICES.append((r, r))

class Music(models.Model):
    song = models.CharField(max_length=50, blank=False)
    pic = models.ImageField(blank=False, null=True)
    published_year = models.IntegerField(('year'), choices=YEAR_CHOICES, default=datetime.datetime.now().year)
    description = models.CharField(max_length=80)

    def __str__(self):
        return self.song

class Wishlist(models.Model):
    user = models.ForeignKey(User, on_delete=models.CASCADE,null=True)
    music = models.ForeignKey(Music, on_delete=models.DO_NOTHING)

views.py

@login_required
def liked(request):
    if request.method == "POST":
        if user.is_authenticated:
            # takes in the specific card id that is been liked and saves it and displays on Port/wishlist.html
            music.save()
        else:
            return HttpResponse("Your card is Invalid")
    else:
        return HttpResponse("Your request is Invalid")

    return render(request, template_name='main/wishlist.html', context={"wishlist": Wishlist.objects.all})

like.js

$(document).ready(function(){
    $(".like").click(function(){
        $(this).toggleClass("heart");
    });
});
riderken
  • 99
  • 20

2 Answers2

2

I would suggest doing something like this: Here we create a new url for add to wishlist(add_to_wishlist). In like.js pass music_id through ajax with POST.If a user is login then show user's wishlisted product as heart symbol as red. And you can show wishlisted product through link in template. You can Understand all others in my code. Please try this. Thanks.

urls.py

from django.urls import path
from main import views

app_name = 'main'

urlpatterns = [
    path('', views.home, name='home'),
    path('signup/', views.signup, name='signup'),
    path('wishlist/', views.liked, name='liked'),
    path('login/', views.login_req, name='login'),
    path('logout/', views.logout_req, name='logout'),
    path('add-to-wishlist/', views.add_to_wishlist, name='add_to_wishlist'), # For add to wishlist
]

views.py

def home(request):
    wishlisted_list =[]
    if request.user.is_authenticated:
        wishlisted_list = list(Wishlist.objects.filter(user_id=request.user).values_list('music_id',flat=True).order_by('music_id'))
    return render(request, template_name='main/home.html', context={"music": Music.objects.all(),'wishlisted_list':wishlisted_list})

@login_required
def liked(request):
    wishlist = {}
    if request.method == "GET":
        if request.user.is_authenticated:
            wishlist = Wishlist.objects.filter(user_id_id=request.user.pk)
        else:
            print("Please login")
            return HttpResponse("login")

    return render(request, template_name='main/wishlist.html', context={"wishlist": wishlist})

@login_required
def add_to_wishlist(request):
    if request.is_ajax() and request.POST and 'attr_id' in request.POST:
        if request.user.is_authenticated:
            data = Wishlist.objects.filter(user_id_id = request.user.pk,music_id_id = int(request.POST['attr_id']))
            if data.exists():
                data.delete()
            else:
                Wishlist.objects.create(user_id_id = request.user.pk,music_id_id = int(request.POST['attr_id']))
    else:
        print("No Product is Found")

    return redirect("main:home")

like.js

$(document).ready(function(){
    $(".like").click(function(){
        var attr_id = $(this).attr('attr_id')
        var action_url = $(this).attr('action_url')
        var that = $(this)

        $.ajax({
            url: action_url,
            type: "POST",
            data: {'attr_id': attr_id },
            headers: { "X-CSRFToken": $.cookie("csrftoken") },
            success: function (result) {
                console.log("Success")
                that.toggleClass("heart");
            },
            error: function () {
                alert("Please login");
            }
            
        });
    });
});

home.html

{% load static %}
<link rel="stylesheet" href="{% static 'main/home.css' %}" type="text/css">
<link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.13.0/css/all.css" integrity="sha384-Bfad6CLCknfcloXFOyFnlgtENryhrpZCe29RTifKEixXQZ38WheV+i/6YWSzkz3V" crossorigin="anonymous">

<meta name="viewport" content="width=device-width, initial-scale=1.0">

Hey there,
{% if user.is_authenticated %}
<h1>{{user.username}}</h1>
{% else %}
<h1>unknown</h1>
{% endif %}
<a href="{% url 'main:liked' %}" >Wishlist</a>

<section class="cards">
    {% for m in music %}

    <div class="card">

        <div class="top">
            <div class="label1">{{m.song}}</div>
            {% if m.pk in wishlisted_list %}
            {% for i in wishlisted_list %}
            {% if m.pk is i %}
            <span class="like heart" id="id" attr_id="{{m.pk}}" action_url="{% url 'main:add_to_wishlist' %}"><i class="fa fa-heart"></i></span>
            {% endif %}
            {% endfor %}
            {% else %}
            <span class="like" id="id" attr_id="{{m.pk}}" action_url="{% url 'main:add_to_wishlist' %}"><i class="fa fa-heart"></i></span>
            {% endif %}
        </div>


        <div class="middle">
            <a href="https://google.com" id="link" target="_blank">
                <div class="img-container"><img src="{{ m.pic.url }}"></div>
            </a>
        </div>

        <a href="https://google.com" id="link" target="_blank">
            <div class="bottom">
                <div class="label4">{{m.description}}</div>
            </div>
        </a>

    </div>
    {% endfor %}
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>
    <script src="{% static 'main/js/like.js' %}" type="text/javascript"></script>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery-cookie/1.4.1/jquery.cookie.min.js"></script>
</section>

wishlist.html

{% load static %}
<link rel="stylesheet" href="{% static 'main/home.css' %}" type="text/css">
<link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.13.0/css/all.css" integrity="sha384-Bfad6CLCknfcloXFOyFnlgtENryhrpZCe29RTifKEixXQZ38WheV+i/6YWSzkz3V" crossorigin="anonymous">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
Hey there,
{% if user.is_authenticated %}
<h1>{{user.username}}</h1>
{% else %}
<h1>unknown</h1>
{% endif %}
<a href="{% url 'main:home' %}" >Go to Home</a>
<section class="cards">
    {% if wishlist %}
    {% for m in wishlist %}
    <div class="card">
        <div class="top">
            <div class="label1">{{m.music_id}}</div>
            <span class="like" id="id" attr_id="{{m.music_id.pk}}" action_url="{% url 'main:add_to_wishlist' %}"></span>
        </div>
        <div class="middle">
            <a href="https://google.com" id="link" target="_blank">
                <div class="img-container"><img src="{{ m.music_id.pic.url }}"></div>
            </a>
        </div>
        <a href="https://google.com" id="link" target="_blank">
            <div class="bottom">
                <div class="label4">{{m.music_id.description}}</div>
            </div>
        </a>
    </div>
    {% endfor %}
    {% else %}
    <div class="card">
        <div class="middle">
            <div class="label1">Your Wishlist is empty...!</div>
        </div>
        <div class="bottom">
            <div class="label4"><a href="/">Go to Shop</a></div>
        </div>
    </div>
    {% endif %}
</section>
Riyas Ac
  • 1,553
  • 1
  • 9
  • 23
0

First things first, you need to add a primary key in the Music table assuming you name it as id

In the like.js file, you'll need to make an Ajax call to send the music ID to Django. Pass the music ID to the template when you render it so that you can pass it back during the Ajax call

like.js

$.ajax(path, {
        data: {"music_id": 12345},
        method: "POST",
        success: function (data, textStatus, jqXHR) {
            $(selector).toggleClass("heart");
        },
        error: function () {
            console.log("Something went wrong");
}

Now, in you view, you can have something like this view.py

def add_to_wishlist(request):
    data = json.loads(request.body.decode("utf-8"))

    user_id = request.user.id
    music_id = data.get('domain_name'))
    
    wishlist = Wishlist()
    wishlist.user_id = user_id
    wishlist.music_id = music_id
    wishlist.save()