Etc/Side

[제 12회 소프트웨어 경진대회] 솜식Talk

  • -
728x90

메인 이미지

교내 소프트웨어 경진대회에 출품하기 위해 아주 간단한 웹사이트를 제작하였다. 혼자서 제작하다보니 많이 아쉬운 부분이 있다. 특히 SSR로 진행했기 때문에, 추후 디벨롭을 한다면 react를 사용해서 제대로 해두어야겠다.


주요 기능은 솜보드(CRUD) | 이번주 학식(크롤링) | 솜식봇(챗봇) 이렇게 세가지로 구성되어 있다.

아키텍처 및 사용언어

사실 서버를 이틀만에 구축해서 좀 부족한 점이 많았다... 가상화 넘 어렵다.
 

챗봇 - 솜식봇

실제 코드는 아래처럼 프롬포트를 입력하도록 했다. 

프롬프트 엔지니어링을 접하고, 조금 더 개선하여 추가해둔 상태이다. 위는 이전의 프롬프트이다.

 

솜보드

간단한 CRUD이다. 이전에 들었던 김영한님 spring 강의 코드를 거의 유사하게 사용하였다. 시간이 없었다보니 디자인도 이쁘지 않고, form에서 받는 정보도 너무 간단하다. enum으로 태그라도 좀 만들껄 그랬다....!

이번주 학식 페이지

실제 페이지

이번주 학식은 이번주의 학식을 확인할 수 있는 페이지이다. 

위 이미지처럼 실제 학교의 웹사이트를 통해 날짜 정보, 학식 정보를 가져오고 있다. 전체 코드는 아래와 같다.

from flask import Blueprint, Flask
from bs4 import BeautifulSoup
import json

from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.chrome.service import Service

app = Flask(__name__)
bp = Blueprint("crawling", __name__)

def get_today_menu(li_element):
    menu_info = []

    dl_elements = li_element.find_all("dl")

    for dl in dl_elements:
        dd_elements = dl.find_all("dd", class_="ddCafeTeriaInfo")

        # dd 태그에서 정보를 가져와서 줄바꿈 문자로 분할
        for dd in dd_elements:
            text = dd.get_text(strip=False)
            text = text.replace("\n\n", "-")
            items = text.split("-")

            if items:
                for i in range(len(items)):
                    menu_name = items[i].strip()  # 메뉴 이름

                    # Null 값인 경우 무시
                    if not menu_name:
                        continue

                    # 결과 리스트에 추가
                    menu_info.append(menu_name)

    return menu_info


# 일주일 동안의 식단 정보를 가져오는 함수
def get_weekly_menus(soup):
    weekly_menus = {}
    ul_element = soup.select_one("ul#ulWeekDtInfo")  # ul 태그 선택

    if ul_element:
        li_elements = ul_element.find_all("li")  # 모든 li 태그 선택

        for li_element in li_elements:
            # 날짜 정보 가져오기
            span = li_element.select_one("p span").get_text(strip=True)
            day = li_element.select_one("p b").get_text(strip=True)
            date_info = f"{span} {day}"  # 날짜 정보 형식 수정
            menus = get_today_menu(li_element)
            weekly_menus[date_info] = menus
            print(date_info)  # 날짜 정보 출력
            print(menus)  # 메뉴 정보 출력

    return weekly_menus


# 해당 URL의 HTML을 BeautifulSoup 객체로 반환하는 함수
def get_html(url: str) -> BeautifulSoup:
    options = webdriver.ChromeOptions()
    options.add_argument("--headless")  # 헤드리스 모드로 실행 (선택 사항)

    # 웹 드라이버 초기화
    driver = webdriver.Chrome(options=options)

    driver.get(url)
    soup = BeautifulSoup(driver.page_source, "html.parser")
    return soup


@bp.route("/crawling")
def crawling():
    website_url = "https://www.dongduk.ac.kr/kor/life/cafeteria.do"

    soup = get_html(website_url)
    weekly_menus = get_weekly_menus(soup)

    return json.dumps(weekly_menus, ensure_ascii=False, indent=4)

 

'Etc > Side' 카테고리의 다른 글

[모바일 소프트웨어] 최종 과제 "오늘 일기"  (0) 2023.06.15
Contents

포스팅 주소를 복사했습니다

이 글이 도움이 되었다면 공감 부탁드립니다.