다운로드 링크가 정상적으로 보이지 않는 경우 애드블록을 해제해 주세요.
본문 바로가기
  • 혜음우리말화연구소
잡담/사이트개발

개발 일지 정리 11월~3월

by WindowsTiger 2024. 3. 11.

*  사이트의 개발에 관련한 일지가 난잡하게 정리되어있던것을 다시 정리해 보았다.

 

설명하기 전에 EZ2ON, DJMAX, BMS, 평면채보란

EZ2ON의 이미지

우선 이 사이트를 설명하기 전에 EZ2ON이라는 리듬 게임이 있다. EZ2ON은 위에서 내려오는 리듬에 맞춰 내려오는 막대(노트)들을 각 라인에 맞게 타이밍에 맞춰 눌러 높은 점수를 얻는 것이 목적인 게임이다.

DJMAX도 비슷한 류의 게임이라고 생각하면 된다.

BMS의 경우 게임플레이 방식은 비슷하지만, 위의 두 게임은 상업게임인데 반해, BMS는 일종의 규격이라고 보는 편이 가까우며 따라서 유저가 여러 패턴을 직접 만들수 있다. 해당 게임에 대한 규격은 표준은 없지만 어느정도 통일된 규격이 존재한다.

노트를 언제 처리해야하는지 알수 있게 패턴을 악보처럼 한줄로 만든 그림을 해당 게임 유저들은 '평면채보'라고 말한다.

그리고 EZ2PATTERN은 이 평면 채보를 제공하는 일종의 게임 공략 사이트다.

유사한 사이트로 textage.ccsdvx.in 등이 있다.


개요

  • 제작기간: 2023-11-23 ~ 2024-03-11(글작성일 기준)
  • 참여인원: 3명

프로젝트 제작: 1명

데이터 제공: 2명

기술 스택

  • 사용 언어: Python
  • 왭프레임워크: Django
  • DB: SQLite
  • 클라우드: Oracle Cloud
  • 기타: Nginx, uWSGI 등등....

사이트 연혁

  • 2023년 12월 03일: EZ2ON 사이트 오픈
  • 2023년 12월 16일: DJMAX 자식 사이트 오픈
  • 2024년 03월 04일: BMS 자식 사이트 오픈

주소 및 코드

추가예정


개발 내용

해당 프로젝트는 원래 EZ2DB라는 EZ2ON의 데이터를 손으로 수집후 정리해둔 사이트의 클론을 만드려는 프로젝트로 시작하였다. 이유는 해당 사이트가 도중에 사이트를 닫아버렸기 때문이다.

문을 닫은지 약 2주쯤 됐을때, 갑자기 흥미가 생겨서 웹개발에 대해 알아보고 사이트를 클론 사이트를 만들고 있었으나, 프로젝트 진행중에 사이트가 문을 열어버렸고, 프로젝트의 기능이 중복이 되는데다가, 이미 만들고 있던 프로젝트를 중단하는 것은 아쉬워 가지고, 방향성을 바꾸어서 패턴을 보여주는 사이트로 만들었다.

 

각 패턴에 대한 데이터는 내가 만든 것이 아닌 다른 유저가 만들어 줬었으며, 사이트 없이 커뮤니티에서 ZIP파일을 공유해 해당 자료를 다른 유저와 공유하고 있었다. 해당 자료는 위에서 언급한 BMS의 포맷을 이용해 배포되고 있었다.

BMS포맷에 대한 정보는 다음 자료를 참고바란다.


프레임워크

웹 프레임워크로는 장고(Django)를 선택하였다.

웹 개발은 이번이 처음이었으며, 어떤 프레임워크가 좋을지 고민하던 중에 Python을 사용하여 위키를 구현한 openNAMU 프로젝트를 이용해 봤던 경험이 떠올랐다. 따라서 비슷하게 Python으로 웹사이트를 만드는 어떤 방법론이 있을 것이라고 추정하였고 검색결과 Django라는 프레임워크를 찾을 수 있었다. 최근에 Python을 자주 이용하여 익숙한 상태였고, 또한 관련 자료가 많이 있었기 때문에 Django를 이용하여 개발하기로 정했다.

 

Django의 특이한점은 서버를 돌리는 중에 코드를 변경후 저장하면, 자동으로 반영이 되어 새로고침이 된다는 점이었다. 파이썬이기에 가능한 점이겠지만, 그래도 바로바로 상태변화를 인지하고 새로고침한다는 점은 특이하였다.

 

프로젝트 안에 어플리케이션이라는 것을 만들어서 시작하는데 각각 하나의 페이지를 의마한다 보면 편하다. 해당 앱 내에서 SQL 테이블을 정의하는 모델을 만들고, 유저에게 보여지는 화면인 템플릿과, 템플릿에 전달할 데이터를 만드는 뷰로 나누어 진다. 이를 MVT 패턴 개발이라고 한다. 단 장고의 경우 여기에 URL을 매핑하는 단계가 추가된다.


프레임워크내에서 URL해석이 가능하기 때문에 백엔드의 view에서 하술할 페이지의 CSS를 생성하도록 하고 있다. CSS를 생성하면 html 템플릿 내에서 <style></style>문 안에 끼워넣고 있다. 해당 부분이 백엔드에서 처리하는게 맞는가 하는 생각은 확실히 있긴 하지만, URL 처리가 너무 좋고 파이썬이 편해서 이렇게 쓰고있다.

정상적인 개발 방법이라면 키워드 값만 템플릿으로 전송하게 하고, 왭페이지에서 자바스크립트를 통해 CSS를 생성하는 것이 맞을 것이다.


최근에 BMS 페이지를 만들었다. 해당 페이지의 모티브는 

최근 BMS용으로 사이트를 하나 만들었다. 지금은 없어진 ribbit이라는 유저 제작 BMS를 올릴 수 있는 사이트가 있었는데 이를 어느정도 카피한 모양새로 만들었다.

기존의 다른 페이지와 달리 해당 사이트는 파일을 입력으로 받아야 한다. 또한 내가 DB에 입력하는게 아니라 입력받은 파일을 토대로 판단뒤, DB에 직접 입력을 해야했다. 해당 부분은 크게 어렵지 않았으며, 컨버터 코드를 찾아서 (bemusicscript/bms2bmson-python) 컨버팅 기능만 제거해버리고 정보를 읽는 부분만 가져왔었다. 이후 데이터는 pyGithub모듈을 이용해 Github로 업로드 하도록 구현하였다. 파일 하나당 크기가 그리 크지 않고, 자바스크립트에서 get요청을 하도록 읽어도면 되기 때문이다. 다만 백엔드 쪽은 이렇게 구현하기 쉬웠지만, DB에 문제가 있었고 이건 DB절에 서술한다.


DB

DB는 Django에서 기본적으로 지원하는 SQLite를 사용하였다.

DB를 사용하는 법을 배운것은 컴퓨터활용능력1급 시험때였고, 해당 시험은 MSSQL을 사용하기에 SQLite와 차이가 많이 났지만 Django의 강력한 ORM 덕에 SQL문을 직접 입력하기 위해 해맬 필요는 적었다. 그래도 각 Table의 필드, 외래키 및 기본키의 개념들은 잘 알고 있어야 했다.

 

DB의 구조는

1. 곡(노래)의 정보를 저장한 테이블

2. 1을 외래키로 가지는 곡의 패턴의 개수와 난이도 값을 저장한 테이블

3. 1을 외래키로 가지는 곡의 패턴에 대한 정보를 저장한 테이블

4. 코스(곡을 연속으로 플레이하는 모드)의 정보를 저장한 테이블

5. 1과 4를 외래키로 가지는 코스의 곡의 정보를 저장한 테이블

 

위는 EZ2ON 페이지의 DB에 해당되며, DJMAX, BMS 페이지도 크게 다르지는 않다.

 

DB의 모델을 정하는 과정에서 사이트 용도의 개발도중 변경도 문제였겠지만, 관련 경험의 부재로 인해 좀 DB의 구조가 좋지 않게 되었다. 그중에서 내가 제일 불만이 있는 부분은 어떤 패턴이 존재하는지에 대한 boolean 필드 값이 여러 테이블에 중복되어있으며, 또한 이 값을 내가 수동으로 각각 수정하고 있다는 점이다. 이는 테이블을 CSV로 추출후 액셀의 함수를 이용해 LOOKUP해서 값을 바꿔준뒤에 업로드 해서 처리하고 있다. 작성하면서 생각난 것은 이는 나중에 python 스크립트로 작성을 할수 있다는 것을 깨닳았다. 이후에 해당 코드를 작성해야 겠다.


위에 프레임워크측에서 BMS사이트가 문제가 있었다고 했었다. 그 문제는 DB 레코드의 양이었다.

이전까지의 페이지는 상업용 게임이기 때문에 들어갈수 있는 DB의 양이 아무리 어림잡아도 1만개 이하의 레코드 정도밖에 안된다. BMS는 유저가 만들기 때문에 매우 많은 패턴 파일이 존재할수 있으며, 이때문에 대충 파일수를 간추려 보니 집계만 30만개, 아마 추산 50만개 정도 레코드를 처리해야한다는 문제점이 존재했다. 

SQLite에서 해당 수의 DB를 처리하기 쉽지 않을 거라 판단하여 현재는 해당 페이지를 어느정도 개발 중단한 상태이다. 웹개발 경험이 별로 없다보니 DB의 양의 정도에 대한 감이 없고, 그렇다고 선적용을 해서 성능테스트를 해서 판단하기에도 데이터가 너무 많기 때문에 어렵기 때문이다.

때문에 이 페이지를 다시 개발한다면 해당 페이지만 따로 분리를 해서 다른 DB(MySQL등?) 을 알아보고 개발을 할것 같다. 일단 지금은 업로드 가능한 DB 레코드 수를 총 1000개로 제한하고 임시로 열어놓은 상태이다.


프론트엔드(채보 뷰어)

 

위의 스크린샷에서 보여지고 있는 페이지는 자바스크립트를 통해  BMS라는 파일 포맷을 글의 맨 처음에서 언급한 평면채보 형태로 출력한 모습이다. 해당 구현는 Snack-X/web-bms-viewer에서 가져온 자바스크립트를 이용하였으며, 초기에는 원본의 드래그 & 드롭으로 파일을 컴퓨터에서 불러오도록 되어 있던것을, xmlhttprequest()를 이용해서 GET요청으로 서버내에서 가져오도록 수정하였다.

 

하지만 GET요청의 경우 해당 주소로 접속을 하면 그대로 파일을 가져올수 있기에, 유출의 위험이 크므로 POST요청으로 다시 고쳤었다. GET요청의 경우 Django의 Static 폴더에 데이터를 넣고 가져와도 되지만, post의 경우 view에서 python코드를 작성해서 반환해야했다. 또한 자바스크립트쪽도 수정해야 했는데, django프레임워크에서 csrf 코드를 요구했고, 해당 코드를 자바스크립트로 얻어오는 예제가 잘 통하지 않아 좀 애를 먹었었다.

 

POST 요청으로 변경을 한 뒤에도 여전히 크롬의 개발자 도구에서 네트워크 감시를 통해 파일을 추출할수 있는 문제가 있었기에 파일에 xor암호화를 걸었으며, 자바스크립트 코드에도 난독화를 걸었었다.

 

이후 완전히 갈아고쳐 먼저 BMS 데이터를 전부 html로 컨버팅하여 저장한 뒤, 해당 html코드를 템플릿에 그대로 넣는 것으로 바꾸었다. 원래는 pythonmonkey라는 파이썬에서 자바스크립트를 실행할수 있는 모듈을 찾아서 페이지에서 요청할 때 바로 바꾸도록 구현하려고 했었으나, django랑 맞물리면 어떠한 오류도 없이 서버가 종료되버리는 문제가 발생하였다. 디버깅 했을때 split() 또는 map()에서 발생했으나, 단독으로 실행할때는 문제가 없어서 원인이 뭔지 알 수 없었다. 그래서 어쩔수 없이 미리 다 html 코드로 변환하는 식으로 구현하였다.

 

이후 GET요청방식은 BMS를 볼수 있게 하는 자식 사이트에서 다시 구현하여 사용하고 있다.


web-bms-viewer에서 일부 버그도 고쳐서 사용하고 있다.

주요 버그내역와 수정방법은 다음과 같다.

  • 맨 처음 마디만 올바르게 노트 배치를 처리하지 못하는 문제 : 마디값이 0일때 배열의 -1인덱스를 읽어 값이 undefine된 문제였다. 0일때 예외를 추가해 줘서 해결했다.
  • 일반적인 롱노트(세로로 길쭉한 노트)를 정상적으로 출력하지 못하는 문제 : 롱노트에 대한 끝점 데이터가 잘못 들어가는 문제가 있었다.

 

그외에 일부 가독성을 위해 여러 수정이 있었다. 세로 줄무늬를 이미지에서 CSS로 바꾸고, 각 노트의 세로 위치를 상수 픽셀 값이 아니라 calc 를 이용한 식으로 바꾸어 길이 배율을 바꿀수 있도록 하였으며(노트간 간격이 늘어날 경우 가독성이 좋아지기에 해당 기능을 요구했던 유저가 몇명 있었다), django측에서 CSS만 수정하여 출력하는 것으로 노트의 가로 위치를 섞을수 있도록 수정하였다. (미러/랜덤이라고 부른다)

기존에 랜덤방식은 자바스크립트에 순서값을 넣은뒤 해당 위치에 따라 픽셀값을 바꾸어서 출력하도록 했었으나, html로 바꾼 뒤에는 위의 방식을 사용하고 있다.


디자인

html/css의 디자인에는 부트스트랩을 이용하였다. 부트스트랩이 없었으면 디자인 하는데 오랜 시간이 걸렸을 것이다.


서버

서버는 Oracle Cloud의 free tier 서버를 이용하였다. 극초기에는 python 프로젝트를 왭서버에서 구동할수 있는 pythoneverywhere 서비스를 이용하였으나 pythoneverywhere의 경우 이미지를 호스팅 하기위한 용량을 충분히 주지 않고 또한 느리기 때문에 pythoneverywhere에서 그나마 무료로 사용할 수 있는 Oracle cloud로 옮겨오게 되었다.

그러는 과정에서 pythoneverywhere에서는 기본적으로 지원하는  WSGI(Web server gateway Interface)를 수동을 직접 세팅해야 했었다. 해당 프로그램은 nginX와 uWSGI를 이용하였다.


기타

502 Bad gateway

사이트가 간헐적으로 502 Bad gateway를 반환하는 문제를 확인했다.

해당 문제는 uWSGI의 문제이다. 원인은 불명이나, 페이지 자체가 뜨는 이유는 uWSGI가 Nginx에 페이지를 전달하지 않아 문제가 발생한 것이다. 다른사람에게도 문제가 뜨는것 같지만, 전부 해결법이 다양하다는게 문제다.

디버깅을 하고 싶어도 문제가 너무 가끔 나타나서 이게 해결됐는지 안됐는지 확인하는 것도 힘들다.

https://github.com/unbit/uwsgi/issues/1623

 

Unexplainable timeout error when using uwsgi behind nginx · Issue #1623 · unbit/uwsgi

Hi everyone, I'm using uwsgi (version 2.0.13.1) behind nginx (version 1.10.3) to run a Flask application on Python 3 on Ubuntu 14.04.03. The connection to nginx is done via https, but nginx connect...

github.com

gunicorn이라는 WSGI에서는 문제가 발생하지 않는다는 얘기가 있어, 나중에 해당 WSGI로 갈아탈 예정이지만, 일단 돌아간다는 느낌이라서 후순위로 밀려난 상태이다.

 

데이터 생성 자동화

이 사이트에서 가장 큰 문제점은 데이터다. 데이터는 사람이 직접 만들어야한다는 점이 문제다.

해당 데이터를 만드는 법은 위의 오른쪽과 같은 툴로 영상을 보면서 직접 똑같이 배끼면 된다.

영상을 보면서 하는 작업은 너무 힘들기 때문에 왼쪽과 같이 opencv를 간단히 이용해 영상을 전부 이은 사진을 변환하는 툴을 만들었다. 그러나 이러한 툴을 만듦에도 데이터 하나당 시간이 약 1시간 정도 걸리는 문제가 있었다.

 

https://universe.roboflow.com/djmax/djmax-note-detection-3

 

djmax note detection 3 Object Detection Dataset and Pre-Trained Model by djmax

962 open source notes images plus a pre-trained djmax note detection 3 model and API. Created by djmax

universe.roboflow.com

이를 해결하기 위해 자동화를 할 수 없을까 하는 생각이 들었고, 인터넷을 찾아본 결과, 영상을 보고 노트 위치를 반환하도록 학습한 데이터가 있다는 것을 찾았다. 해당 결과물은 꽤 정확했었던것 같다. 미리 학습된 결과를 사용할 경우 API 사용수 제한이 영상에 이용하기에는 너무 작게 있기 때문에 직접 컴퓨터에서 학습해서 실행해야 할것 같지만, 라벨링이 잘 되어있어서 문제 없을 것 같다.

 

다만 문제는 이걸 이용하더라도 컨버팅을 잘 짤 자신이 없다는 것이다. 시도도 해보지않고 문제를 정의하는 태도가 문제일 수도 있지만, 개인적으로 생각하는 문제는 다음과 같다.

  • 데이터 라벨링 방법을 잘 모름(움직임을 따라 노트 라벨링을 어떻게 하는지 모름)
  • 1마디당 192박자까지 처리를 해야하는데 이 배치에 대한 정확성이 떨어질수 있음(1/16박을 11/192박등 매우 애매한 박자로 처리한다던지)
  • 각 패턴의 경우 BPM에 따라 한 마디의 길이가 달라지는데 이를 프로그램에서 자동으로 처리할 방법의 부재

그리고 우선순위가 떨어져서 해당 부분에 대해 진행하고 있지 않다. 하지만 장기적인 서비스를 위해서는 해결해야 할 문제로 보인다.

차후계획

  • 검색기능 추가
  • 로그인 기능 추가 + 댓글기능 추가

 


참조사이트

점프 투 장고 - https://wikidocs.net/book/4223

 

점프 투 장고

**점프 투 장고 종이 책 출간 !! (2020.12)** * [책 구입 안내](https://wikidocs.net/105844) 점프 투 장고는 파이보라는 …

wikidocs.net

오라클 클라우드 가입 - https://it.gwangtori.com/40

 

무료 VPS!? 오라클 클라우드를 사용해 보자! [1]

서론 안녕하세요 광토리입니다. 요즘 오라클 클라우드를 쓰는 분들이 많습니다. 그 이유는 바로 오라클이 꽤 좋은 성능을 무료로 쓸 수 있게 해줬기 때문입니다. 트래픽 제한은 무려 10TB, 스토리

it.gwangtori.com

오라클 클라우드 방화벽 설정 - https://kibua20.tistory.com/124

 

Oracle Cloud 방화벽 설정 (http/https 특정 포트 열기)

오라클 클라우드에서 VM Instance를 Web server에 활용하기 위해서는 http/https 포트를 개방해야 합니다. 또는 네트워크를 사용하는 애플리케이션에 따라서 특정 포트를 허용해야 합니다. 오라클 클라

kibua20.tistory.com

파이선 가상환경 설정 - https://stackoverflow.com/questions/46210934/importerror-couldnt-import-django

 

ImportError: Couldn't import Django

I've already configured virtualenv in pycharm, when using the python manage.py command, this is error shown: E:\video course\Python\code\web_worker\MxOnline>python manage.py runserver Traceback...

stackoverflow.com

장고 static 파일 자체 서빙 - https://stackoverflow.com/questions/5836674/why-does-debug-false-setting-make-my-django-static-files-access-fail

 

Why does DEBUG=False setting make my django Static Files Access fail?

Am building an app using Django as my workhorse. All has been well so far - specified db settings, configured static directories, urls, views etc. But trouble started sneaking in the moment I wante...

stackoverflow.com

장고 nginx 연동 - https://nachwon.github.io/django-deploy-3-nginx/

 

[Deploy] Django 프로젝트 배포하기 - 3. Nginx

지금까지 구축한 구조는 아래와 같다.

nachwon.github.io

https://jinmay.github.io/2019/03/14/django/django-uwsgi/

 

django와 uwsgi 연동하기

uwsgi 사용해보기nginx - uwsgi - django를 연동해서 배포하는 걸 AWS EC2를 통해 연습하고 있다. 그 중에서 어플레케이션 컨테이너라는 uWSGI를 사용하여 일단 nginx 없이 배포하는 걸 정리해보려고 한다. uW

jinmay.github.io

서비스로그확인 - https://jinmay.github.io/2019/03/27/linux/linux-how-to-log/

 

ubuntu에서 서비스 로그 확인하기

리눅스에서 로그 확인하는 법로그 메세지를 확인함으로써 에러에 어떻게 대처할지 고민하기 시작하는 것 같다. 로그 메세지를 확인하는 방법은 여러가지가 있다. 대표적으로 nginx를 사용할때 ac

jinmay.github.io

쿼리포함 django 리다이렉트 구현 - https://stackoverflow.com/questions/19784810/redirect-to-a-url-with-query-string-in-django

 

Redirect to a url with query string in Django

How can I go to a specific URL with parameters like if I have view def search(request): and in urls.py ^search/$ and what I need to do is to redirect like search/?item=4 c = {} render_to_response(&

stackoverflow.com

pygithub 파일 업로드 - https://stackoverflow.com/questions/63427607/python-upload-files-directly-to-github-using-pygithub

 

Python - Upload files directly to github using PyGithub

I have a public repo and want to upload files to that repo using python (PyGithub library). I referred the below code from SO: import base64 from github import Github from github import

stackoverflow.com

 

'잡담 > 사이트개발' 카테고리의 다른 글

다음은 Django 대신 Spring Boot으로...(2024-03-19)  (0) 2024.03.19
오늘 추가한것(2024-03-13)  (0) 2024.03.13
패턴 사이트 현황  (0) 2024.02.20
최근 만든 사이트 현황  (0) 2023.12.09
최근에 만든 사이트  (1) 2023.12.04

댓글