Step 0 : install library
pip install django djangorestframework Pillow django-cors-headers
BashStep 1: Create a Project
django-admin startproject Portfolio
cd Portfolio
python manage.py startapp myfolio
Bashstep 2: settings.py
INSTALLED_APPS = [
# Third-party apps
'rest_framework', # Add this line
# Your apps
'myfolio', # Replace 'portfolio' with the name of your app
'corsheaders',
]
MIDDLEWARE = [
'corsheaders.middleware.CorsMiddleware',
]
CORS_ALLOW_ALL_ORIGINS = True
#CORS_ALLOWED_ORIGINS = [
# "http://localhost:3000",
#]
PythonAdditional settings.py
Configurations
For handling media files (like images for your PortfolioItem
and ProjectImage
models), you should also define MEDIA_URL and MEDIA_ROOT in your settings.py
:
# Media files
import os
MEDIA_URL = '/media/'
MEDIA_ROOT = os.path.join(BASE_DIR, 'media')
BashDjango REST Framework Settings
Optionally, you can customize Django REST Framework’s behavior by adding its settings to your settings.py
file. Here’s an example configuration that you might find useful:
REST_FRAMEWORK = {
'DEFAULT_PERMISSION_CLASSES': [
'rest_framework.permissions.AllowAny',
],
'DEFAULT_RENDERER_CLASSES': [
'rest_framework.renderers.JSONRenderer',
],
'DEFAULT_PARSER_CLASSES': [
'rest_framework.parsers.JSONParser',
],
}
BashModels (models.py
)
from django.conf import settings
from django.db import models
from django.utils import timezone
User = settings.AUTH_USER_MODEL
class Skill(models.Model):
SKILL_LEVELS = [
('beginner', 'Beginner'),
('intermediate', 'Intermediate'),
('expert', 'Expert'),
]
name = models.CharField(max_length=100)
description = models.TextField(blank=True)
proficiency_level = models.CharField(max_length=12, choices=SKILL_LEVELS)
def __str__(self):
return self.name
class Experience(models.Model):
position = models.CharField(max_length=100)
company = models.CharField(max_length=100)
description = models.TextField(blank=True)
duration = models.CharField(max_length=100)
relevant_skills = models.ManyToManyField(Skill)
def __str__(self):
return f"{self.position} at {self.company}"
class Education(models.Model):
degree = models.CharField(max_length=100)
institution = models.CharField(max_length=100)
field_of_study = models.CharField(max_length=100)
duration = models.CharField(max_length=100)
description = models.TextField(blank=True)
def __str__(self):
return f"{self.degree} from {self.institution}"
class PortfolioItem(models.Model):
title = models.CharField(max_length=200)
description = models.TextField()
image = models.ImageField(upload_to='portfolio/images/')
url = models.URLField(blank=True)
date_created = models.DateField(default=timezone.now)
skills = models.ManyToManyField(Skill, blank=True)
def __str__(self):
return self.title
class ProjectImage(models.Model):
portfolio_item = models.ForeignKey(PortfolioItem, on_delete=models.CASCADE, related_name='images')
image = models.ImageField(upload_to='project_images/')
def __str__(self):
return f"Image for {self.portfolio_item.title}"
class ContactInfo(models.Model):
email = models.EmailField()
phone_number = models.CharField(max_length=20)
linkedin_profile = models.URLField(blank=True)
github_profile = models.URLField(blank=True)
other_social_media_profiles = models.JSONField(blank=True, null=True)
def __str__(self):
return self.email
class Testimonial(models.Model):
author = models.CharField(max_length=100)
position = models.CharField(max_length=100)
company = models.CharField(max_length=100)
testimonial_text = models.TextField()
def __str__(self):
return f"Testimonial by {self.author}"
class Certification(models.Model):
title = models.CharField(max_length=200)
issuing_organization = models.CharField(max_length=200)
date_earned = models.DateField()
description = models.TextField(blank=True)
def __str__(self):
return self.title
class BlogPost(models.Model):
title = models.CharField(max_length=200)
content = models.TextField()
date_published = models.DateField(default=timezone.now)
author = models.ForeignKey(User, on_delete=models.CASCADE)
# Add category and tags relationship here
def __str__(self):
return self.title
# Models for Category and Tag not shown for brevity. They would typically have a name and possibly a description field.
class Comment(models.Model):
author = models.CharField(max_length=100)
email = models.EmailField(blank=True)
content = models.TextField()
date_posted = models.DateTimeField(default=timezone.now)
related_item = models.ForeignKey(BlogPost, on_delete=models.CASCADE)
def __str__(self):
return f"Comment by {self.author} on {self.date_posted}"
PythonSerializers (serializers.py
)
from rest_framework import serializers
from .models import Skill, Experience, Education, PortfolioItem, ProjectImage, ContactInfo, Testimonial, Certification, BlogPost, Comment
class SkillSerializer(serializers.ModelSerializer):
class Meta:
model = Skill
fields = '__all__'
class ExperienceSerializer(serializers.ModelSerializer):
class Meta:
model = Experience
fields = '__all__'
class EducationSerializer(serializers.ModelSerializer):
class Meta:
model = Education
fields = '__all__'
class PortfolioItemSerializer(serializers.ModelSerializer):
images = serializers.PrimaryKeyRelatedField(many=True, read_only=True) # Assuming you want to show image IDs initially
class Meta:
model = PortfolioItem
fields = '__all__'
class ProjectImageSerializer(serializers.ModelSerializer):
class Meta:
model = ProjectImage
fields = '__all__'
class ContactInfoSerializer(serializers.ModelSerializer):
class Meta:
model = ContactInfo
fields = '__all__'
class TestimonialSerializer(serializers.ModelSerializer):
class Meta:
model = Testimonial
fields = '__all__'
class CertificationSerializer(serializers.ModelSerializer):
class Meta:
model = Certification
fields = '__all__'
class BlogPostSerializer(serializers.ModelSerializer):
class Meta:
model = BlogPost
fields = '__all__'
read_only_fields = ('author',)
class CommentSerializer(serializers.ModelSerializer):
class Meta:
model = Comment
fields = '__all__'
PythonViews (views.py
)
from rest_framework import viewsets
from rest_framework.permissions import IsAuthenticated
from .models import Skill, Experience, Education, PortfolioItem, ProjectImage, ContactInfo, Testimonial, Certification, BlogPost, Comment
from .serializers import SkillSerializer, ExperienceSerializer, EducationSerializer, PortfolioItemSerializer, ProjectImageSerializer, ContactInfoSerializer, TestimonialSerializer, CertificationSerializer, BlogPostSerializer, CommentSerializer
class SkillViewSet(viewsets.ModelViewSet):
queryset = Skill.objects.all()
serializer_class = SkillSerializer
class ExperienceViewSet(viewsets.ModelViewSet):
queryset = Experience.objects.all()
serializer_class = ExperienceSerializer
class EducationViewSet(viewsets.ModelViewSet):
queryset = Education.objects.all()
serializer_class = EducationSerializer
class PortfolioItemViewSet(viewsets.ModelViewSet):
queryset = PortfolioItem.objects.all()
serializer_class = PortfolioItemSerializer
class ProjectImageViewSet(viewsets.ModelViewSet):
queryset = ProjectImage.objects.all()
serializer_class = ProjectImageSerializer
class ContactInfoViewSet(viewsets.ModelViewSet):
queryset = ContactInfo.objects.all()
serializer_class = ContactInfoSerializer
class TestimonialViewSet(viewsets.ModelViewSet):
queryset = Testimonial.objects.all()
serializer_class = TestimonialSerializer
class CertificationViewSet(viewsets.ModelViewSet):
queryset = Certification.objects.all()
serializer_class = CertificationSerializer
class BlogPostViewSet(viewsets.ModelViewSet):
permission_classes = [IsAuthenticated]
queryset = BlogPost.objects.all()
serializer_class = BlogPostSerializer
def perform_create(self, serializer):
serializer.save(author=self.request.user)
class CommentViewSet(viewsets.ModelViewSet):
queryset = Comment.objects.all()
serializer_class = CommentSerializer
PythonURLs (urls.py
)
from django.urls import path, include
from rest_framework.routers import DefaultRouter
from .views import SkillViewSet, ExperienceViewSet, EducationViewSet, PortfolioItemViewSet, ProjectImageViewSet, ContactInfoViewSet, TestimonialViewSet, CertificationViewSet, BlogPostViewSet, CommentViewSet
router = DefaultRouter()
router.register(r'skills', SkillViewSet)
router.register(r'experiences', ExperienceViewSet)
router.register(r'educations', EducationViewSet)
router.register(r'portfolioitems', PortfolioItemViewSet)
router.register(r'projectimages', ProjectImageViewSet)
router.register(r'contactinfos', ContactInfoViewSet)
router.register(r'testimonials', TestimonialViewSet)
router.register(r'certifications', CertificationViewSet)
router.register(r'blogposts', BlogPostViewSet)
router.register(r'comments', CommentViewSet)
urlpatterns = [
path('', include(router.urls)),
]
PythonAdmin (admin.py
)
from django.contrib import admin
from .models import Skill, Experience, Education, PortfolioItem, ProjectImage, ContactInfo, Testimonial, Certification, BlogPost, Comment
admin.site.register(Skill)
admin.site.register(Experience)
admin.site.register(Education)
admin.site.register(PortfolioItem)
admin.site.register(ProjectImage)
admin.site.register(ContactInfo)
admin.site.register(Testimonial)
admin.site.register(Certification)
admin.site.register(BlogPost)
admin.site.register(Comment)
PythonProject urls.py
from django.contrib import admin
from django.urls import path, include
from django.conf import settings
from django.conf.urls.static import static
urlpatterns = [
path('admin/', admin.site.urls),
path('', include('myfolio.urls')), # Replace 'your_app' with the name of your Django app
# other paths...
]
# Serving media files in development mode
if settings.DEBUG:
urlpatterns += static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)
PythonMigrate database
python manage.py makemigrations
python manage.py migrate
PythonCreate Superuser
python manage.py createsuperuser
Python