Django - ExcelCalCulator_5
Page content
개요
Django 한 그릇 뚝딱
교재의 내용에서 멀티캠퍼스 강의에 맞게 일부 수정함- 2019년 버전이고 현재는 2023년이기 때문에 소스코드 변경 사항이 필요할 거 같아서 글을 남김
교재 홍보
Step 01 - 이전 글
- 1편 : https://dschloe.github.io/python/2023/08/django_excel_calculator_1/
- 2편 : https://dschloe.github.io/python/2023/08/django_excel_calculator_2/
- 3편 : https://dschloe.github.io/python/2023/08/django_excel_calculator_3/
- 4편 : https://dschloe.github.io/python/2023/08/django_excel_calculator_4/
Step 02 - 파일 업로드 하기
- 로그인을 통해 메인 화면으로 왔다면, 파일 업로드 기능 구현
Step 03 - 파일 업로드 기능 구현
check - 1 : index.html 구현
- 파일 경로 : ExcelCalculate > main > templates > main > index.html
- 파일 제출 버튼을 눌렀을 때 가려는 url을 등록한다.
- 또한
enctype="multipart/form-data"
를 추가한다.- 이것을 사용해야 파일의 내용이 올바르게 전달된다.
<div class="content">
<div class="fileInputDiv">
<form action="**calculate/**" method="POST" enctype="multipart/form-data">{% csrf_token %}
<div class="input-group">
하단 버튼을 통해 파일을 업로드 해주세요.(.xls 확장자의 파일만 가능합니다.)<br>
<input id="fileInput" name="fileInput" type="file" class="form-control">
<input type="submit" class="btn btn-success btn-lg" value="파일 제출">
</div>
</form>
</div>
</div>
calculate/
경로는 초기에ExcelCalculate > ExcelCalculate > urls.py
에서 이미 설정해놨다.- 링크 참조 :
from django.contrib import admin
from django.urls import path, include
urlpatterns = [
path('email/', include('sendEmail.urls'), name="email"),
path('calculate/', include('calculate.urls'), name="calculate"),
path('', include('main.urls'), name="main"),
path("admin/", admin.site.urls),
]
ExcelCalcalculate > calculate > urls.py
에서도 이미 설정을 해놨다.
from django.urls import path
from . import views
urlpatterns = [
path('', views.calculate, name="calculate_do"),
]
check - 2 : views.py 구현
- 파일 경로 :
ExcelCalculate > calculate > views.py
- 이 때,
request.POST
가 아닌request.FILES
를 이용한다.
# Create your views here.
def calculate(request):
file = request.FILES['fileInput']
print("# 사용자가 등록한 파일의 이름: ", file)
return HttpResponse("calculate, calculate function!")
check - 3 : 테스트
- 이제 data.xlsx 파일을 업로드 한다.
- 파일 제출 버튼을 누를 시, 웹에서는 정상적으로
calculate, calculate function!
출력이 되어야 하고 터미널에서는 아래와 같이 print() 문구가 나와야 한다.
Step 04 - pandas 사용
- data.xlsx 파일을 분석해 아래 항목들의 값을 구해 볼 것이다.
- grade별 value 최솟값, 최댓값, 평균값
- 이메일 도메인 주소별 인원수
- 함수 처리는 ExcelCalculate > calculate > views.py에서 처리한다.
from django.shortcuts import render, redirect
from django.http import HttpResponse
import pandas as pd
# Create your views here.
def calculate(request):
file = request.FILES['fileInput']
print("# 사용자가 등록한 파일의 이름: ", file)
df = pd.read_excel(file, sheet_name="Sheet1", header=0)
print(df.head())
# grade별 value 리스트 만들기
grade_dic = {}
total_row_num = len(df.index)
for i in range(total_row_num):
data = df.loc[i, :]
if not data.grade in grade_dic.keys():
grade_dic[data.grade] = [data.value]
else:
grade_dic[data.grade].append(data.value)
# print(grade_dic)
# grade별 최솟값 최댓값 평균값 구하기
grade_calculate_dic = {}
for key in grade_dic.keys():
grade_calculate_dic[key] = {}
grade_calculate_dic[key]['min'] = min(grade_dic[key])
grade_calculate_dic[key]['max'] = max(grade_dic[key])
grade_calculate_dic[key]['avg'] = float(sum(grade_dic[key])) / len(grade_dic[key])
# 결과 출력
grade_list = list(grade_calculate_dic.keys())
grade_list.sort()
for key in grade_list:
print("# grade: ", key)
print("min:", grade_calculate_dic[key]['min'], end="")
print("/ max:", grade_calculate_dic[key]['max'], end="")
print("/ avg:", grade_calculate_dic[key]['avg'], end="\n\n")
# 아래 코드와 동일
result = df.groupby('grade')['value'].agg(["min", "max", "mean"])
print(result)
# 이메일 주소 도메인별 인원 구하기
email_domain_dic = {}
for i in range(total_row_num):
data = df.loc[i, :]
email_domain = data['email'].split("@")[1]
if not email_domain in email_domain_dic.keys():
email_domain_dic[email_domain] = 1
else:
email_domain_dic[email_domain] += 1
print("## EMAIL 도메인별 사용 인원")
for key in email_domain_dic.keys():
print("#", key, ": ", email_domain_dic[key], "명")
df['domain'] = df['email'].apply(lambda x : x.split("@")[1])
result2 = df.groupby('domain')['value'].agg("count").sort_values(ascending=False)
print(result2)
return HttpResponse("calculate, calculate function!")
- grade별 value 최솟값, 최댓값, 평균값을 구한 결괏값은 다음과 같다.
- 이메일 도메인 주소별 인원수