엘리스 두번째 데이터분석 웹서비스 프로젝트

박주현·2023년 3월 30일
0

1. 반딧불이

엘리스AI 트랙에서 배운 내용으로 진행한 두번째 데이터분석 웹서비스 프로젝트

  • 서울시 이재민 임시거주 시설 분석
  • 서울시 화재발생 현황(구별) 통계 분석
  • 서울시 강우량 정보 분석
  • 프로젝트 팀명 : Chilling
  • 프로젝트 기간 : 2023.03.06 ~ 2023.03.24
  • 프로젝트 역할 분담 : 프론트엔드 3명 + 백엔드 3명 ( 백엔드 담당 )
  • 기술 스택
    - Front : JavaScript , React , Styled-Components, Figma
    • Backend : Node.js , Express , MySQL , AWS
    • DataAnalysis : Jupyter-Notebook

2. 프로젝트 목표

  • 프로젝트 아이디어 동기
    재난 상황이 닥쳤을 때, 대피소를 잘 알지 못하는 사람이 많은데 현재 정부에서 운영하는 국민 재난 안전 포털에서는 수용시설에 대한 일부 정보만 제공하기 때문에 추가적인 정보 제공을 위해 해당 서비스를 기획하였음
  • 문제를 해결하기 위한 특정 질문 명시
    화재, 강우량같은 재난 발생빈도 대비 국가가 제공하는 수용시설이 충분히 확보되어 있는가?

2. 서비스 주요 기능 설명

  • 주요 기능 (주된 활용성) 및 서브 기능
    주요기능:
    1. 구 단위 별로 수용시설 분포 지도 제공
    2. 시설 정보 제공(시설명, 위치, 수용인원, 시설구분, 전화번호)
    서브기능:
    1. 이재민 관련 추가 사이트 제공
    2. 지역별 안전도 표시
    3. 이재민 소통을 위한 익명 게시판 제공

  • 프로젝트만의 차별점, 기대 효과
    1. 기존 국민 재난 안전 포털 사이트 대비 사용자를 위한 시각화 자료를 통해 이해가 쉽도록 도와줌
    2. 이재민 관련 정보 한번에 찾을 수 있도록 함
    3. 재난에 대한 지역 안전도 표시

    1. 이재민들이 어려운 시기에 서로가 힘이되고 정보를 공유할 수 있도록 익명 게시판 제공

3. 프로젝트 구성도

4. 나의 responsibility

  • 백엔드 & 데이터분석 담당
    1. 기획 단계: 기획 데이터 분석을 통해 해결하고자 하는 문제를 정의
    2. 개발 단계: 웹 서버 사용자가 직접 백엔드에 저장할수 있는 기능 구현, 데이터 베이스 구축 및 API 활용, 데이터 분석 개념 총동원하기
    3. 수정 단계: 코치님 피드백 반영해서 분석/ 시각화 방식 수정

5. 백엔드 폴더 구조

  • services: API와 통신하는 로직을 처리하는 서비스(데이터베이스와 상호작용)
  • controllers: API 호출과 관련된 로직을 처리하는 컨트롤러(클라이언트로부터 요청을 받아, 서비스 계층의 함수를 호출하여 데이터를 가져오고, 응답을 반환하는 역할)
  • routes: API와 관련된 라우팅 로직을 처리하는 라우터
  • models: 데이터베이스와 관련된 모델 코드
  • databases: 데이터베이스에 연결하는 코드
  • config: API를 호출하기 위해 필요한 매개변수를 저장
  • app.js: API를 정의하고 서버를 시작하는 역할
  • migrations: 기존 테이블에서 데이터 변경 시 마이그레이션

6. 백엔드 기능 코드

  1. 정제화한 화재데이터(CSV 파일) 을 데이터베이스와 알맞게 모델 코드 작성.
// models/Fire.js
const { DataTypes } = require('sequelize');
const sequelize = require('../databases/sequelize');

const Fire = sequelize.define("Fire", {
  union_district: {
    type: DataTypes.TEXT,
    primaryKey: true,
    allowNull: false,
  },
  year_total: {
    // '2년치 합계'
    type: DataTypes.INTEGER,
    allowNull: false,
  },
  year_avg: {
    // '2년치 평균'
    type: DataTypes.DOUBLE,
    allowNull: false,
  },
}, {
  timestamps: false // timestamps 비활성화
});
module.exports = Fire;
  1. App.js
    포트를 8000번으로 사용하고 데이터베이스에 연결하는 과정을 초기에 구현
const PORT = process.env.PORT || 8000;

app.listen(PORT, async () => {
  try {
    await sequelize.authenticate();
    console.log("데이터베이스 연결 성공");
    await sequelize.sync(); //모델 구조 동기화
  } catch (error) {
    console.error("데이터베이스 연결 실패");
  }
  console.log(`Server is running at ${PORT}`);
});
  1. 공공데이터 통계데이터 정제화

-- 데이터 테이블 정의 및 입력입니다. 총합과 평균의 경우 데이터를가지고계산가능하므로 제외했습니다.
CREATE TABLE district_summary(
    distict_name VARCHAR(10),
    year_2020_value INT,
    year_2021_value INT
);
INSERT INTO district_summary values 
('금천구',108,108  )
,('동대문구',120,131)
,('동작구',136,121)
,('도봉구',136,125)
,('양천구',137,138)
,('구로구',142,147)
,('성북구',147,153)
,('노원구',152,154)
,('성동구',155,163)
,('강북구',165,130)
,('은평구',169,145)
,('광진구',169,187)
,('중구',170,136)
,('용산구',176,160)
,('종로구',179,169)
,('강서구',193,197)
,('서대문구',194,236)
,('관악구',195,224)
,('영등포구',203,176)
,('강동구',203,188)
,('중랑구',204,191)
,('서초구',205,215)
,('마포구',213,212)
,('송파구',292,237)
,('강남구',360,356);


-- 통합 구를 이용해 뽑기위해, 통합 구를 정의하는 인라인뷰를 만들고, 이를 통해 결과값을구했습니다.
SELECT 
union_district, 
SUM(year_2020_value + year_2021_value) as 2_year_total,
AVG(year_2020_value + year_2021_value/2) as 2_year_avg
FROM 
(
SELECT CASE 
WHEN distict_name IN ('은평구', '서대문구','마포구') THEN '서북생활권'	
WHEN distict_name IN ('종로구', '중구','용산구') THEN '도심권'	
WHEN distict_name IN ('성북구', '강북구','도봉구','노원구') THEN '동북2생활권'	
WHEN distict_name IN ('동대문구', '성동구','중랑구','광진구') THEN '동북1생활권'	
WHEN distict_name IN ('강서구','양천구') THEN '서남1생활권'	
WHEN distict_name IN ('영등포구', '금천구','구로구') THEN '서남2생활권'	
WHEN distict_name IN ('관악구','동작구') THEN '서남3생활권'	
WHEN distict_name IN ('강남구', '서초구') THEN '동남1생활권'	
WHEN distict_name IN ('송파구','강동구') THEN '동남2생활권'	
END as union_district, distict_name, year_2020_value, year_2021_value  FROM district_summary
) as a
GROUP BY union_district;

7. 프로젝트 회고

처음해보는 백엔드 파트라 정말 많은 어려움을 느꼈고, 어쩌다보니 백엔드 리더가 되서 더더욱 부담이 되었다.
하지만, 백엔드 팀원중에 수정님께서 너무나도 감사하게 설명해주시고 틈틈히 공유를 해주셔서 많이 배우면서 할 수 있었다.
이번 프로젝트를 진행하면서, 데이터 분석과 기획이 너무나도 어렵게 느껴졌고, 나같은 경우에는 백엔드의 흐름을 이해하는데에도 어려움이 있었지만,
팀원의 끊임없는 공유와 설명들이 금방 익숙하게 만들어줬고, 코치님께서 기획을 보시고난뒤 AWS와 Sequelize를 사용하면 생기는 장단점을 설명해주시고, 해당 내용을 팀원들과 공유하고 모여서 열심히 찾아보고 공부하다보니 금방 적응할 수 있었다.
중간에 기능이 추가되면서, 프론트엔드분들이 기능구현을 해야하는게 늘었는데, 포기하지않고 배포 마지막날 한시간전까지 최대한 구현하는 모습에 너무나도 감사했다.

이번 프로젝트를 진행하면서, 내가 백엔드 분야의 취업하기에 필요한 것들이 무엇인지, 혼자서 어떠한 기능을 프로젝트처럼 만들어볼지를 정하게 되었고, 현재 이 회고록을 쓰는 시점에도 열심히 백엔드를 공부하고 있다.
데이터분석 프로젝트는 경험이 없어서 어려웠지만, 팀원들로인해 긍정적인 부분을 배우고, 모두가 공통적인 뜻을 바탕으로 프로젝트를 진행하며 서로가 소통을 잘하다보니, 만족스러운 프로젝트였다고 생각한다.

7팀 정말 너무나 감사하고 수고하셨습니다!

8. Github

profile
빌드업 막 시작하는 개발자

0개의 댓글