Westagram Endpoint

BLAKE KIM·2020년 8월 17일
0

Westagram Django Project Tree

총 6개의 엔드포인트를 구현했으며 1.회원가입, 2.로그인, 3.게시물 등록, 4.게시물에 댓글 등록, 5.게시물 '좋아요' 기능 구현, 6.다른 계정 'Follow' 기능 구현 등이 해당 된다. django를 이용해서 구현하였으며 project라는 하나의 프로젝트 안에 UserPosting이라는 두 개의 app으로 이루어져 있다. 각각의 app의 파일을 보기 전에 project에 해당하는 파일들을 먼저 살펴보도록 한다.

project/my_settings.py

토큰을 발행하고 확인하는 SECRET_KEY와 프로젝트의 데이터가 저장될 DB의 정보를 my_settings.py에 따로 저장하여 .gitignore에 추가하여 원격저장소에 해당 정보가 올라가지 않도록 해주었다.

project/settings.py

ALLOWED_HOST는 현재 여러 프론트엔드들이 접속할 수 있도록 모든 주소를 허용해 놓은 것이다. 또한 외부에서도 접속을 허용하게 하는 corsheaders와 직접 만든 UserPostingINSTALLED_APPS에 추가하여 django에서 앱을 인식할 수 있게 하였다.

project/urls.py

Port번호 이후에 user가 보이면 User.urls.py로, posting이 보이면 Posting.urls.py로 가라는 뜻이다.

회원가입 엔드포인트

회원가입 엔드포인트는 회원정보를 DB에 등록하기 위한 것으로 DB의 테이블을 어떤 식으로 구성할 지 모델링해야 하고 views.py를 작성할 때는 어떤 정보가 필수적으로 들어올 지에 대한 것을 정해야한다. 또한 passwordemail의 형식이 올바르게 들어왔는지 판단해줄 필요가 있으며 각각의 필수적인 것들에 대해 잘못된 요청이 들어왔을 때 적절한 에러메세지를 응답해줘야하며 성공했을 때는 DB에 저장하고 회원가입에 성공했다는 응답을 보내주어야 한다. 먼저 User/urls.py를 살펴보자.

User/urls.py

from .views import SignUpView, SignInView, FollowPost, FollowGet

위 코드는 각각의 endpoint에 접근하면 실행될 함수들이다. 이 중 회원가입 엔드포인트로 접근하면 실행될 함수에 해당하는 것은 SignUpView이다. 회원가입 엔드포인트는 signup이다. project/urls.py에서 살펴보았듯 path함수를 사용했으며 이번에는 다른 urls.py로 연결하는 것이 아닌 실행될 view를 연결한다.

User/models.py

이번에 살펴볼 것은 models.py이다. 실제 DB에 형성될 tableclass에 해당되고 각 attributefield이다. 즉 하나의 column에 해당한다. email, password, name, phone_number라는 4개의 column을 선언하였으며, Primary_Key가 지정되지 않았기 때문에 Django에서 자동으로 id라는 column으로 Primary_Key에 해당하는 field를 자동으로 생성해준다.

아래 \_\_str\_\_ 함수는 classinstance들을 표현할 때 email field에 해당하는 값으로 표현하고자 하는 것이다. 해당 함수가 선언되지 않는다면 Primary_Key에 해당하는 값으로 표현된다. 즉 여기서는 id값으로 표현된다.

User/views.py

위 코드에 해당하는 것이 회원가입 기능을 구현하는 코드이다. 먼저 엔드포인트에 접근할 때 입력된 정보들을 data라는 변수에 담는다. 이 data의 자료구조는 dictionary에 해당한다.

emailpassword는 필수적으로 입력되야하는 Key이기 때문에 들어오지 않는다면 KEY_ERROR를 반환해주고 phone_numbername은 필수적인 요소는 아니기 때문에 있다면 post_변수에 저장하고 아니면 빈 값을 저장해준다.

다음에 해당하는 코드는 각각의 입력된 값의 형식이나 중복된 값이 존재하는지를 검사하는 것으로 helper.py에 따로 함수를 선언 후 import해서 사용하는 것이다. helper.py는 다음과 같다.

User/helper.py

순서대로 name 중복, email 중복, phone_number 중복, email 형식, password 형식 검사에 해당하는 함수이다. email형식과 password 형식 검사는 정규표현식을 사용하였다.

post_password = bcrypt.hashpw(post_password.encode('utf-8'), bcrypt.gensalt())

위의 코드는 입력한 패스워드를 암호화하는 작업이다. bcrypt 라이브러리를 사용했으며 이 결과값은 bytes타입이기 때문에 다음 코드를 살펴보면 DB에 저장하는 코드인데 decode 후에 저장하는 것을 볼 수 있다. 그 이유는 현재 models.py를 보면 field 타입이 문자열이기 때문에 bytes타입이 들어가더라도 문자열로 저장되고 후에 로그인 시에 암호화된 코드를 비교할 때 문제가 생기기 때문에 decode후에 패스워드를 저장하도록 했다.

그리고 마지막으로 성공적으로 저장이 완료되면 성공했다는 메세지를 status 코드와 함께 보내준다.

로그인 엔드포인트

로그인 엔드포인트는 위의 User/urls.py를 참고하면 signin에 해당하고 SignInView가 실행되는 함수이다. views.py에서 해당 코드를 살펴보자.

역시나 들어올 때 입력된 정보들을 data라는 dictionary 형태의 변수에 담고 각각의 key가 존재하는지 검사를 진행한다. 로그인 시에 필요한 값은 name, email, phone_number 중에 하나 그리고 password이다. 역시나 필수적인 키가 입력되지 않았을 시 KEY_ERROR를 반환하게 된다.

그 후 각각의 들어온 키에 해당하는 조건문으로 코드를 구현하였다. 키에 저장된 값을 통해 DB에 저장된 값을 조회 후 존재하지 않으면 회원가입이 선행되지 않았으므로 에러를 반환하고 존재할 시 DB에 저장된 암호화된 password와 입력된 password를 비교한다. bcrypt.checkpwTrue/False로 값을 반환하며 일치할 시 jwt를 생성하여 토큰을 반환한다.

토큰 생성 시 담게 될 정보는 복호화하여 정보를 확인할 수 있기 때문에 누군지 식별가능하지만 공개되어도 문제 없는 정보를 담아야한다. 그렇기 때문에 다른 DB나 서비스에서 알아도 다른 값에 해당할 id를 담는다. 이 때 SECRET_KEY는 어떤 정보도 상관없다. 나의 경우는 my_settings.py에 담긴 SECRET_KEY를 사용하였다. 그렇게 만들어진 tokenbytes타입이기 때문에 Json 형식으로 반환할 때 decode하여 str형식으로 만들어서 보내주어야 한다. 그래서 decode하여 응답하였다.

게시물 등록 엔드포인트

먼저 게시물을 위한 models.py를 먼저 살펴보자.

Posting/models.py

게시물 등록에 필요한 fielduser, created_at, img_url, content에 해당한다. liked_user는 후에 설명할 좋아요 기능 구현과 관련해서 필요한 field값이다. user의 경우 회원가입과 로그인이 완료된 후에 게시물을 등록할 수 있어야 하므로 기존에 저장된 User 테이블과 연결되어야만 한다. 때문에 ForeignKey로 연결해주었다. created_at은 값이 저장될 때 자동으로 저장되도록 하였다. 다음은 posting app의 엔드포인트들을 살펴볼 posting/urls.py를 살펴보자.

Posting/urls.py

게시물 등록에 해당하는 엔드포인트는 post이다. get은 게시물을 정보를 요청하는 GET요청으로 들어왔을 때 처리할 엔드포인트이다.

Posting/views.py

이제 게시물 등록에 대한 views.py를 살펴보도록 한다.

이 때 데코레이터 함수가 먼저 실행되도록 하는 것을 살펴볼 수 있는데 이 함수는 로그인 시 발행한 토큰을 확인하는 데코레이터 함수다. 해당 코드를 먼저 살펴보도록 하자.

User/utils.py

먼저 데코레이터 함수 형식은 미리 써놓은 글이 있기 때문에 생략한다. try-except로 구문을 묶은 것은 토큰이 유효하지 않은 것이거나 토큰에 담긴 유저의 정보가 나의 DB에서 찾을 수 없는 에러가 발생할 시 처리하기 위한 것이다.

보통 토큰은 http 요청에 있어서 headerAuthorization이라는 Key에 담겨 전달되기 때문에 토큰을 해당 위치에서 get하고 토큰을 encode했던 동일한 정보와 방식으로 decode하고 해당 토큰에 담긴 userDB에서 찾고 해당 user의 정보를 최종적으로 request.user 정보에 담고 후에 실행될 함수를 return에 위치시켜 실행되도록 한다.

이 때 img_urlcontent는 필수적으로 전달되어야 할 Key이므로 전달되지 않았을 시 KEY_ERROR를 반환해준다. 그 후 Post에 저장을 해준다. 이 때 user 정보는 앞의 데코레이터 함수에서 토큰을 통해 확인한 request.user를 입력해준다.

그 다음은 GetView는 등록된 게시물 정보를 요청하는 GET 요청이 들어왔을 경우 처리하는 class이다. 이 때 post에 담긴 Post.objects.all()Post 테이블에 담긴 모든 정보를 가져오는 것으로 typeQuerySet이다. Json 형식으로 전달하기 위해서 serializers를 사용한다.

QuerySet이란?

QuerySet이란 데이터베이스에서 전달 받은 객체의 목록이다.(Django ORM에서 발생한 자료형) 리스트와 구조는 같지만 파이썬 기본 자료구조가 아니기 때문에 파이썬에서 읽고 쓰기 위해서 자료형 변환을 해줘야 한다.

게시물 댓글 등록 엔드포인트

댓글과 연관된 엔드포인트는 commentpostcommentget이다. commentpost는 댓글 등록, commentget은 등록된 댓글 정보를 가져오기 위한 엔드포인트이다.

Posting/models.py

위에서 살펴본 파일의 아랫 부분으로 댓글에 해당하는 모델이다. user는 어떤 사용자가 댓글을 작성했는지, post는 어떤 게시물에 달린 댓글인지, commet는 댓글 내용, created_at은 댓글이 달린 시점이다.

Posting/views.py

역시나 토큰을 확인하는 데코레이터 함수가 먼저 실행되고 필수적인 KEY를 확인한다. 또한 댓글을 달고자 하는 게시물이 존재하는지 먼저 확인한다. 그 후 별 문제가 없다면 해당 게시물에 댓글이 달리도록한다.

get요청에 대한 함수는 현재 id1인 게시물의 댓글 정보만 전달되도록 코드를 구현해두었다.

게시물 좋아요 기능 구현 엔드포인트

좋아요 기능과 관련된 엔드포인트는 likepostlikeget이다. 해당 정보가 저장되는 모델은 Postliked_user이다. 즉 좋아요를 누른 user의 정보가 각 게시물과 연결되는 것이다. views.py를 살펴보면

전달되는 정보는 postlike이다. user의 정보는 데코레이터 함수를 통해서 전달 받는다. 이 때 like에 대한 정보는 0또는 1로 전달받도록 하였는데 0이면 좋아요를 취소한 것이고, 1이면 좋아요를 누른 것으로 처리하였다.

get요청을 통한 것은 좋아요 갯수에 대한 것으로 해당 게시물과 연결된 user의 수를 count메소드를 통해서 구한 후 전달해준다.

다른 계정 'Follow' 기능 구현 엔드포인트

해당 정보가 저장되는 테이블은 User앱의 models.py에 구현되어 있으며 해당 필드는 위와 같다. Follow 정보는 Follow를 하는 것과 당하는 것으로 두 가지 정보가 필요하므로 다른 필드로 구현되어 있다.

Follow 기능 역시 회원가입과 로그인이 선행되어야 하므로 데코레이터 함수를 통해 토큰을 검사한다. 그 후 Follow하고자 하는 email의 키가 필수적이므로 KEY 검사를 한다. 또한 입력된 emailFollow를 당하는 것이므로 followed_user에 저장되고 해당 user의 정보를 User 테이블에서 가져와서 저장한다. following_user의 경우 Follow를 하는 주체로 토큰 검사에서 구할 수 있는 request.user를 통해 저장한다.

이 때 get_or_created를 통해서 새로운 row가 생성된 것인지 기존에 존재하는지를 알아낼 수 있는데 기존에 존재하는 값이라면 해당 요청은 Follow를 취소하는 UnFollow요청으로 해당 row를 삭제하도록 한다. 각각의 요청에 대한 응답으로 메세지를 보내주도록 한다.

Follow의 수에 대한 정보를 얻기위한 get 요청에 대한 기능은 역시나 email이 필수적으로 입력되어야 하며 이는 로그인한 user의 것이여도 반드시 들어와야한다. 해당 userfollowing, followed 정보를 count를 통해서 수를 반환해준다.

profile
BackEnd

0개의 댓글