Skip to content
Snippets Groups Projects
Commit 82e7c37a authored by Mansoor Saleem's avatar Mansoor Saleem
Browse files

Merge branch 'Mansoor-02' into 'master'

Article and Comment Section

See merge request !2
parents c5e6a493 ab55025f
No related branches found
No related tags found
1 merge request!2Article and Comment Section
Pipeline #3074 canceled
Showing
with 474 additions and 0 deletions
# Generated by Django 2.2.1 on 2019-05-19 17:14
from django.conf import settings
from django.db import migrations, models
import django.db.models.deletion
class Migration(migrations.Migration):
dependencies = [
migrations.swappable_dependency(settings.AUTH_USER_MODEL),
('articles', '0003_auto_20190519_1655'),
]
operations = [
migrations.AddField(
model_name='article',
name='author',
field=models.ForeignKey(default=None, on_delete=django.db.models.deletion.PROTECT, to=settings.AUTH_USER_MODEL),
),
]
# Generated by Django 2.2 on 2019-05-22 16:07
from django.db import migrations, models
import django.db.models.deletion
class Migration(migrations.Migration):
dependencies = [
('articles', '0004_article_author'),
]
operations = [
migrations.CreateModel(
name='Comment',
fields=[
('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('user', models.CharField(max_length=250)),
('email', models.TextField()),
('created', models.DateTimeField(auto_now_add=True)),
('post', models.ForeignKey(default=1, on_delete=django.db.models.deletion.SET_DEFAULT, related_name='comments', to='articles.Article')),
],
),
]
File added
File added
File added
File added
File added
File added
from django.db import models
from django.utils import timezone
from django.contrib.auth.models import User
# Create your models here.
class Article(models.Model):
title = models.CharField(max_length=100)
slug = models.SlugField()
body = models.TextField()
date = models.DateTimeField(auto_now_add=True)
thumb = models.ImageField(default='default.png', blank=True)
author = models.ForeignKey(User, on_delete=models.PROTECT, default=None)
def __str__(self):
return self.title
def snippet(self):
return self.body[:50] + '...'
class Comment(models.Model):
post = models.ForeignKey(Article, on_delete=models.SET_DEFAULT, default=1, related_name='comments')
user = models.CharField(max_length=250)
email = models.TextField()
created = models.DateTimeField(auto_now_add=True)
approved = models.BooleanField(default=False)
def approved(self):
self.approved = True
self.save()
def __str__(self):
return self.user
#add in thumbnail later
#add in author later
#python manage.py makemigrations
#python manage.py makemigrations
#use the upper two commands whenever you make changes in the model
#whenever we make channges to the models when need to migrate kit
#11 theres alway error when you migrate so the fix is simply to add "on_delete=models.PROTECT"
#we create a snippet which is a model whose function is to cut the number of words to let say 100
#to add ... at the end
#9 blank = true beacuse the if a doesnt want to upload anythingits ok
{% extends 'base_layout.html' %}
{% block content %}
<h1>Add New Comment</h1>
<form method='POST'>{% csrf_token %}
{{ form.as_p }}
<button type='submit'>Submit</button>
</form>
{% endblock %}
\ No newline at end of file
{% extends 'base_layout.html' %}
{% block content %}
<div class="create-article">
<h2>Create an Awesome New Article</h2>
<form class="site-form" action="{% url 'articles:create' %}" method="post" enctype="multipart/form-data">
{% csrf_token %}
{{ form }}
<input type="submit" value="Create">
</form>
</div>
{% endblock %}
{% extends 'base_layout.html' %}
{% block content%}
<body>
<div class="article-detail">
<div class="article">
<img src="{{ article.thumb.url }}" />
<h2>{{ article.title }}</h2>
<p>{{ article.body }}</p>
<p>{{ article.date }}</p>
</div>
</div>
<hr>
<h1>Leave a Comment</h1>
<p>Total No of Comments {{post.comments.count}}</p>
<a href="{% url 'articles:add_comment' slug=post.slug}">Leave A Comment</a>
{% for comment in post.comments.all %}
<p>{{comment.created}}</p>
<p>{{comment.user}}</p>
<p>{{comment.body}}</p>
{% empty %}
<p> There is no comment </p>
{% endfor %}
<body/>
{% endblock %}
\ No newline at end of file
{% extends 'base_layout.html' %}
< !-- this file extends from base layout template -->
{% block content%}
<h1>Articles List</h1>
<div class="articles">
{% for article in articles %}
<div class="article">
<h2><a href="{% url 'articles:detail' slug=article.slug %}">{{ article.title }}</a></h2>
<p>{{ article.snippet }}</p>
<p>{{ article.date }}</p>
</div>
{% endfor %}
</div>
{% endblock %}
< !-- extending a base template, a base template has all of the stuff eg header footer etc all goes in to the base template -->
< !-- so that is how we extend template ie you dont have to add header and footer etc which are saved in base template -->
from django.test import TestCase
# Create your tests here.
from django.conf.urls import url
from .import views
app_name = 'articles'
urlpatterns = [
url(r'^$', views.article_list, name="list"),
url(r'^create/$', views.article_create, name="create"),
]
#?P<slug> this whole thing a name capturing group
#\w is anynumber or any alphabet then - then + for any length and then $ for end
#7 naming so that all may be different eg naming = list
#8 #here we get slug from views.py and use here
from django.http import HttpResponse
from django.shortcuts import render, redirect
from .models import Article
from django.contrib.auth.decorators import login_required
from .import forms
def article_list(request):
articles = Article.objects.all().order_by('date');
return render(request, 'articles/article_list.html', { 'articles': articles })
def article_detail(request, slug):
# return HttpResponse(slug)
article = Article.objects.get(slug=slug)
return render(request, 'articles/article_detail.html', { 'article': article })
@login_required(login_url="/accounts/login/")
def article_create(request):
if request.method == 'POST':
form = forms.CreateArticle(request.POST, request.FILES)
if form.is_valid():
# save article to db
instance = form.save(commit=False)
instance.author = request.user
instance.save()
return redirect('articles:list')
else:
form = forms.CreateArticle()
return render(request, 'articles/article_create.html', { 'form': form })
#this variable 'articles' saves all objects in Article and by .order by it sorts it by
#field date which is already an element in models.py under Article
#third parameter in this render function is the data that we want to send to the view
#or template,inside curly brackets we write a Dictionary,"articles" is the property here,whereas the articles on the right is articles on the 7th line,
#this Dictionary will be sended to the template
#so when we render line 9 we display at the output the data
#we cature that slug vairable and use it in url.py url of slug
# return HttpResponse(slug)
assets/logo.png

2.97 KiB

assets/stars.png

100 KiB

body{
font:15px/1.5 Arial,helvetica,sans-serif;
padding: 0;
margin: 0;
background-color: #f4f4f4;
}
/*Global */
.container{
width:80%;
margin: auto;
overflow: hidden;
}
ul{
margin: 0;
padding: 0;
}
.button_1{
height: 38px;
background: #e8491d;
border: 0;
padding-left: 20px;
padding-right: 20px;
margin-right: 400px;
color: #ffffff;
}
.dark{
padding: 15px;
background: #35424a;
color: #ffffff;
margin-top: 10px;
margin-bottom: 10px;
}
/*header **/
header{
background: #35424a;
color: #ffffff;
padding-top: 30px;
min-height: 70px;
border-bottom: #e8491d 3px solid;
}
header a{
color: #ffffff;
text-decoration: none;
text-transform: uppercase;
font-size: 16px;
}
header li{
float: left;
display: inline;
padding: 0 20px 0 20px;
}
header #branding{
float:left;
}
header #branding h1{
margin : 0;
}
header nav{
float: right;
margin-top: 10px;
}
header .highlight, header .current a{
color:#e8491d !important;
font-weight: bold;
}
header a:hover{
color: #cccccc;
font-weight: bold;
}
/*showcase*/
#showcase{
min-height: 400px;
background:url('../Images/showcase.jpg'), no-repeat,0 200px;
text-align: center;
color: #ffffff;
}
#showcase h1{
margin top: 100px;
font-size: 55px;
margin-bottom: 18px;
}
#showcase p{
font-size: 20px;
}
/* Newsletter*/
#newsletter p{
padding: 15px;
color: #ffffff;
background:#35424a;
}
#newsletter h1{
float: left;
}
#newsletter form{
float: right;
margin-top: 15px;
}
#newsletter input[type="email"]{
padding: 4px;
height: 25px;
width: 250px
}
/* Boxes */
#boxes{
margin-top: 20px;
}
#boxes .box{
float: left;
text-align: center;
width: 30%;
padding: 10px;
}
#Boxes .box img {
width: 90px;
}
/* Sidebar*/
aside#sidebar{
float:right;
width: 30%;
margin-top: 10px;
}
aside#sidebar .quote input, aside#sidebar .quote textarea{
width:90%;
padding:5px;
}
/* Main-col */
article#main-col{
float: left;
width: 65%;
}
/* Services*/
ul#services li{
list-style: none;
padding: 20px;
border: #cccccc solid 1px;
margin-bottom: 5px;
background:#e6e6e6;
}
footer{
padding: 20px;
margin-top: 20px;
color: #ffffff;
background-color: #e8491d;
text-align: center;
}
/*login **/
.login-page {
width: 60%;
padding: 7% 0 0;
margin: auto;
}
.form {
position: relative;
z-index: 1;
background: #FFFFFF;
max-width: 468px;
margin: 60px auto 100px;
padding: 45px;
text-align: center;
box-shadow: 0 0 20px 0 rgba(0, 0, 0, 0.2), 0 5px 5px 0 rgba(0, 0, 0, 0.24);
}
.form input {
font-family: "Roboto", sans-serif;
outline: 0;
background: #f2f2f2;
width: 100%;
border: 0;
margin: 0 0 15px;
padding: 15px;
box-sizing: border-box;
font-size: 14px;
}
.form button {
font-family: "Roboto", sans-serif;
text-transform: uppercase;
outline: 0;
background: #e8491d;
width: 100%;
border: 0;
padding: 15px;
color: #FFFFFF;
font-size: 14px;
-webkit-transition: all 0.3 ease;
transition: all 0.3 ease;
cursor: pointer;
}
.form button:hover,.form button:active,.form button:focus {
background: #cccccc;
}
.form .message {
margin: 15px 0 0;
color: #b3b3b3;
font-size: 12px;
}
.form .message a {
color: #e8491d;
text-decoration: none;
}
.form {
border-top: 20px;
}
form p {
float: left;
margin-bottom: 30px;
}
form #role{
background: #f2f2f2;
float: left;
margin-top: 6px;
font-family: "Roboto", sans-serif;
margin-left: 5px;
}
form label{
font-family: "Roboto", sans-serif;
margin-left: 6px;
}
/*signup **/
.signup{
padding-top: 7%;
}
/*articles shown in admins dashboard**/
table {
font:15px/1.5 Arial,helvetica,sans-serif;
border-collapse: collapse;
width: 100%;
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment