프론트엔드 및 백엔드를 호스팅하는 방법은 무엇인가요?
이 튜토리얼에서는 애플리케이션의 프론트엔드 및 백엔드 호스팅에 대한 포괄적인 가이드를 제공합니다.
이를 위해 Back4app에서 풀스택 앱을 호스팅하겠습니다. 먼저 백엔드에서 작업한 다음 프론트엔드로 이동하고 마지막으로 두 구성 요소를 연결합니다.
Contents
목표
이 글이 끝날 무렵에는 이렇게 할 수 있을 것입니다:
- 프론트엔드와 백엔드의 차이점 설명하기
- Back4app의 BaaS 솔루션을 사용하여 백엔드 구축하기
- 백4앱 컨테이너에 프론트엔드 앱 배포하기
- 프론트엔드 앱과 백엔드 앱 연결하기
프론트엔드와 백엔드의 차이점은 무엇인가요?
백엔드와 프론트엔드는 최신 웹 및 모바일 애플리케이션을 구축할 때 고려해야 할 사항을 분리하는 것을 의미합니다. 이 둘의 차이점을 이해하는 가장 쉬운 방법은 빙산을 시각화하는 것입니다.
프론트엔드(또는 클라이언트 측)는 사용자가 보고 상호 작용할 수 있는 모든 것을 의미합니다. 프론트엔드는 모바일 애플리케이션, 웹 애플리케이션, 웹 인터페이스 또는 기타 모든 유형의 클라이언트 등 다양한 형식으로 제공됩니다.
이 애플리케이션 파트는 UI/UX, 디자인, 애니메이션, 그래픽 및 기타 미디어 유형을 담당합니다. 클라이언트 측은 프로젝트 작업의 20%를 차지하며 반복적이지 않습니다.
반면에 백엔드(또는 서버 측)는 사용자가 볼 수 없는 모든 것을 의미합니다. 백엔드는 프론트엔드와 데이터베이스를 연결하는 다리 역할을 합니다.
비즈니스 로직, 백그라운드 작업, 데이터 저장, 확장, 타사 통합 등을 담당합니다. 사용자가 직접 상호작용할 수는 없지만 애플리케이션의 품질에 큰 영향을 미칩니다.
프로젝트 작업의 약 80%를 차지하며 사용자 관리, 인증, 암호화 등과 같은 반복적인 작업을 포함하는 경우가 많습니다.
이 튜토리얼에서는 프론트엔드 및 백엔드를 Back4app에 배포하는 방법을 무료로 배워보세요! 백엔드 및 프론트엔드 배포 방법을 알아보려면 계속 읽어보세요.
프로젝트 소개
백4앱에 프론트엔드와 백엔드를 배포하는 방법을 보여드리기 위해 풀스택 애플리케이션을 준비했습니다.
이 앱은 간단한 마크다운 블로그 역할을 합니다. 관리자는 글을 추가, 편집, 삭제할 수 있고 사용자는 글을 읽을 수 있습니다.
최종 프로젝트는 다음과 같은 모습입니다:
위에서 언급했듯이 앱은 프론트엔드와 백엔드의 두 부분으로 구성됩니다. 앱의 아키텍처를 시각화하면 다음과 같이 보일 것입니다:
백엔드는 Back4app에, 프론트엔드 앱은 Back4app 컨테이너에 배포하겠습니다. 마지막으로 Parse SDK를 통해 두 컴포넌트를 연결합니다.
먼저 이 앱을 따라 해보고 나중에 풀스택 애플리케이션을 배포하여 지식을 테스트하는 것이 좋습니다.
백엔드 및 프론트엔드 호스팅 방법을 알아보려면 계속 읽으세요.
백엔드를 호스팅하는 방법은 무엇인가요?
이 섹션에서는 애플리케이션의 백엔드 부분을 처리합니다.
목표
- Back4app 애플리케이션 구축
- 데이터베이스 클래스 정의
- 데이터베이스 ACL/CLP 설정하기
- 데이터베이스 채우기
- 관리자 앱 활성화
Back4app 앱 만들기
따라가려면 무료 백4앱 계정이 필요합니다. 아직 등록하지 않으셨다면 지금 무료로 가입하세요!
Back4app으로 작업하려면 먼저 애플리케이션을 만들어야 합니다. Back4app에서 인증하면 앱 보기로 리디렉션됩니다. “새 앱 만들기” 버튼을 클릭합니다.
다음으로 백엔드를 배포하는 것이므로 ‘서비스형 백엔드’를 선택합니다.
앱 이름을 지정하고 “NoSQL” 데이터베이스를 선택한 다음 “만들기”를 클릭합니다.
플랫폼이 모든 것(예: 데이터베이스, 확장, 백업, 애플리케이션 계층)을 준비하는 데 시간이 조금 걸립니다. 그 동안 잠시 커피를 마시며 휴식을 취하시기 바랍니다.
앱이 준비되면 데이터베이스 탐색기가 표시됩니다.
데이터베이스 정의
이 섹션에서는 데이터베이스 클래스에 대해 알아보겠습니다.
간단한 애플리케이션을 만드는 것이므로 클래스는 하나만 필요합니다. 사이드바에서 “클래스 만들기”를 클릭하고 이름을 기사로
지정한 다음 다른 항목은 기본값으로 그대로 두고 “클래스 만들기 및 열 추가”를 클릭합니다.
여기에 다음 다섯 개의 열을 추가합니다:
+-----------+--------------+----------------+----------+
| Data type | Name | Default value | Required |
+-----------+--------------+----------------+----------+
| String | slug | <leave blank> | 1 |
+-----------+--------------+----------------+----------+
| String | title | <leave blank> | 1 |
+-----------+--------------+----------------+----------+
| File | cover | <leave blank> | 0 |
+-----------+--------------+----------------+----------+
| String | shortContent | <leave blank> | 1 |
+-----------+--------------+----------------+----------+
| String | content | <leave blank> | 1 |
+-----------+--------------+----------------+----------+
저장하려는 추가 데이터에 대해 열을 추가해야 합니다.
기본적으로 데이터베이스 클래스는 “보호 모드”입니다. 프론트엔드 앱에서 이 클래스와 상호 작용하려면 클래스 수준 권한(CLP)을 약간 수정해야 합니다. 화면 상단의 자물쇠 아이콘을 클릭하고 다음과 같이 CLP를 수정합니다:
다음 문서를 검토하여 Parse 보안에 대해 자세히 알아보세요.
마지막으로 몇 가지 샘플 기사로 데이터베이스를 채웁니다.
아이디어가 떠오르지 않는다면 이 데이터베이스 덤프를 가져와 보세요. 가져오려면 화면 오른쪽 상단의 더 보기 옵션을 클릭한 다음 ‘가져오기 > 클래스 데이터’를 클릭한 다음 JSON을 가져옵니다.
훌륭합니다, 그거예요!
이제 작업할 테스트 데이터가 생겼습니다.
관리자 앱
현재 문서를 관리하는 유일한 방법은 Back4app 데이터베이스 보기를 이용하는 것입니다. 이는 백4앱 자격 증명을 공유하거나 기술 전문가가 아닌 사람을 백4앱 대시보드에 추가하고 싶지 않은 경우 최적이 아닙니다.
다행히도 Back4app에는 데이터베이스 모델을 위한 동적 관리자 인터페이스가 제공됩니다. 이를 활성화하려면 사이드바에서 “더보기 > 관리자 앱”을 선택한 다음 “관리자 앱 활성화”를 클릭합니다.
사용자 아이디, 비밀번호, 관리자 앱 하위 도메인을 선택합니다. 저는 다음과 같이 하겠습니다:
username: admin
password: verystrongpassword123
admin url: https://fullstack.admin.back4app.com/
이제 선택한 관리자 URL에서 관리자 패널에 액세스할 수 있습니다.
새 탭을 열고 관리자 패널로 이동합니다. 자격 증명을 사용하여 로그인하고 인터페이스를 탐색합니다. 문서를 작성하고 업데이트한 다음 삭제할 수 있습니다.
백4앱의 관리자 앱에 대해 자세히 알아보려면 문서를 확인하세요.
코드 없이도 완전한 백엔드를 성공적으로 만들었습니다.
프론트엔드를 호스팅하는 방법은 무엇인가요?
이 섹션에서는 프론트엔드 앱을 다루겠습니다.
목표
- 로컬 개발 환경 설정
- 애플리케이션 도커화
- 로컬에서 Docker 이미지 테스트
- 소스 코드를 GitHub에 푸시
- 애플리케이션을 Back4app 컨테이너에 배포합니다.
로컬 설정
먼저 이 리포지토리의 모든 브랜치를 포크한 다음 로컬 머신에 포크를 복제합니다:
$ git clone <fork_remote_git_url> --branch dummy
$ cd back4app-heroku-deploy && git branch -m master
더미
브랜치에는 백엔드 코드가 포함되어 있지 않기 때문에 복제했습니다. 백엔드 코드는 다음 섹션에서 작업하겠습니다.
다음으로 프로젝트의 종속 요소를 설치합니다:
$ npm install
마지막으로 개발 서버를 시작합니다:
$ npm run dev
즐겨찾는 웹 브라우저를 열고 http://localhost:3000 으로 이동합니다. 블로그 색인 페이지가 표시되어야 합니다. 글을 클릭하여 글 세부정보 페이지로 리디렉션되는지 확인합니다.
현재 글 세부정보 페이지는 하드코딩되어 있습니다. 나중에 수정할 예정이니 걱정하지 마세요.
도커라이즈
Back4app 컨테이너에 앱을 배포하려면 먼저 앱을 도커화해야 합니다.
도커화는 코드를 어디에나 배포할 수 있는 컨테이너에 패키징하는 프로세스입니다. 애플리케이션을 도커라이즈하는 가장 쉬운 방법은 Docker파일을 사용하는 것입니다.
도커파일
Docker파일 스크립트에는 Docker 컨테이너 이미지를 만들기 위한 지침이 포함되어 있습니다. 이 파일을 사용하여 환경을 정의하고, 종속성을 설치하고, 애플리케이션을 빌드하고 실행하는 데 필요한 명령을 실행할 수 있습니다.
프로젝트 루트에 다음 내용으로 Docker파일을 생성합니다:
# Dockerfile
FROM node:18-alpine
WORKDIR /app
COPY package*.json ./
RUN npm ci
COPY . .
RUN npm run build
RUN npm install -g next
EXPOSE 3000
CMD ["next", "start", "-p", "3000"]
이 도커파일은 node:18-alpine
이미지를 기반으로 합니다. 작업 디렉터리를 설정하고, 종속성을 처리하고, 프로젝트를 복사하고, 앱을 빌드합니다.
앱이 빌드되면 포트 3000을
노출하고 해당 포트에서 수신 대기 중인 Next.js 서버를 시작합니다.
Docker파일에 대해 자세히 알아보려면 공식 문서를 확인하세요.
.dockerignore
Docker 이미지의 크기는 최소한으로 유지해야 합니다. Docker 이미지 크기를 줄이는 가장 쉬운 방법은 .dockerignore 파일을 만드는 것입니다. 이 파일을 사용하면 최종 이미지에서 제외할 파일과 폴더를 지정할 수 있습니다.
예를 들어 이미지에 IDE 파일, 빌드, .git 또는 node_modules를 포함하지 않으려는 경우입니다.
다음은 사용할 수 있는 .dockerignore 파일 예시입니다:
# .dockerignore
.idea/
/node_modules
/.next/
/out/
/build
.vercel
필요에 따라 .dockerignore 파일을 수정해야 합니다.
빌드, 실행, 테스트
클라우드에 푸시하기 전에 항상 로컬에서 Docker 프로젝트를 테스트하는 것이 좋습니다. Docker파일을 테스트하는 가장 쉬운 방법은 Docker Desktop을 설치하는 것입니다.
설치가 완료되면 이미지를 만들 수 있습니다:
$ docker build -t blog-frontend:1.0 .
이미지를 나열하여 이미지가 성공적으로 생성되었는지 확인합니다:
$ docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
blog-frontend 1.0 d361534a68da 2 minutes ago 1.08GB
방금 빌드한 이미지를 사용하여 컨테이너를 실행합니다:
$ docker run -p 3000:3000 --name blog-frontend blog-frontend:1.0
즐겨찾는 웹 브라우저를 열고 http://localhost:3000 으로 이동합니다. 앱이 있을 것입니다!
컨테이너를 종료하려면 키보드에서
CTRL + c를
누릅니다.
GitHub로 푸시
Back4pp 컨테이너는 GitHub와 긴밀하게 통합되어 있습니다. 각 커밋마다 앱을 재배포하는 자동 CI/CD 시스템을 제공합니다. 다음 섹션에서 코드를 배포하려면 먼저 변경 사항을 VCS에 푸시해야 합니다.
모든 변경 사항을 커밋하고 클라우드에 푸시합니다:
$ git add .
$ git commit -m "dockerized the application"
$ git push origin master
GitHub 리포지토리로 이동하여 리포지토리에 Docker파일이 있는지 확인합니다.
앱 배포
먼저 Back4app 대시보드로 이동하여 “새 앱 만들기”를 클릭합니다.
도커화된 애플리케이션을 배포하는 것이므로, “서비스형 컨테이너”를 선택합니다.
Back4app 컨테이너를 처음 사용하는 경우, GitHub 계정을 Back4app 계정과 연결하라는 메시지가 표시됩니다. 배포하려는 모든 리포지토리에 대한 액세스를 활성화해야 합니다.
그런 다음, back4app-full-stack
리포지토리를 찾아 “선택”을 클릭하여 선택합니다.
배포하는 애플리케이션에는 특별한 구성이 필요하지 않습니다. 설명적인 “앱 이름”만 제공하면 됩니다. 정리된 상태를 유지하기 위해 back4app-full-stack을
사용하겠습니다.
마지막으로 ‘배포’를 클릭합니다.
Back4app 컨테이너는 Docker 이미지를 빌드하고 배포하는 데 몇 분 정도 걸립니다. 앱이 성공적으로 배포되면 앱의 상태가 “준비됨”으로 변경됩니다.
애플리케이션을 방문하려면 아래 이미지와 같이 녹색 URL을 클릭합니다.
백4앱 컨테이너에 더미 프론트엔드 앱을 성공적으로 배포했습니다.
프론트엔드와 백엔드를 연결하는 방법은 무엇인가요?
이 섹션에서는 프론트엔드를 Back4app 백엔드에 연결해 보겠습니다.
목표
- Parse SDK 설치
- 구문 분석 SDK 구성
- 데이터 가져오기(예:
ParseQuery
사용)
Parse SDK 설치
먼저 Parse SDK를 설치합니다:
$ npm install parse
구문 분석 SDK 구성
Parse SDK를 초기화하려면 Back4app “애플리케이션 ID”와 “JavaScript 키”를 제공해야 합니다. 이를 얻으려면 Back4app 애플리케이션으로 이동하여 사이드바에서 “앱 설정 > 보안 및 키”를 선택하세요.
소스 코드에서 이러한 비밀을 노출하고 싶지 않으므로 .env.local 파일을 만듭니다:
# .env.local
NEXT_PUBLIC_PARSE_APPLICATION_ID=<your_parse_app_id>
NEXT_PUBLIC_PARSE_JAVASCRIPT_KEY=<your_parse_js_key>
자리 표시자를 실제 값으로 바꾸어야 합니다.
구문 분석 SDK 초기화
그런 다음 providers.js로 이동하여 다음과 같이 Parse를 초기화합니다:
// src/app/providers.js
// ...
import Parse from "parse/dist/parse";
const PARSE_APPLICATION_ID = process.env.NEXT_PUBLIC_PARSE_APPLICATION_ID;
const PARSE_JAVASCRIPT_KEY = process.env.NEXT_PUBLIC_PARSE_JAVASCRIPT_KEY;
Parse.initialize(PARSE_APPLICATION_ID, PARSE_JAVASCRIPT_KEY);
Parse.serverURL = "https://parseapi.back4app.com/";
export function Providers({children}) {
return (
// ...
);
}
모든 뷰에서 Parse 인스턴스에 액세스할 수 있습니다. React 컨텍스트를 사용하겠습니다.
context/parseContext.js라는 새 파일을 만들고 그 안에 다음 코드를 붙여넣습니다:
// src/app/context/parseContext.js
"use client";
import {createContext} from "react";
const ParseContext = createContext();
export default ParseContext;
다음으로, 전체 앱을 ParseContext로
래핑하고 Parse
인스턴스를 제공합니다:
// src/app/providers.js
// ...
import ParseContext from "@/app/context/parseContext";
export function Providers({children}) {
return (
<CacheProvider>
<ColorModeScript initialColorMode={theme.config.initialColorMode} />
<ChakraProvider theme={theme}>
<ParseContext.Provider value={Parse}>
{children}
</ParseContext.Provider>
</ChakraProvider>
</CacheProvider>
);
}
끝났습니다! 이제 useContext()
훅을 사용하여 Parse 인스턴스에 액세스할 수 있습니다.
데이터 가져오기
마지막으로 해야 할 일은 백엔드에서 데이터를 가져오는 것입니다. 이를 위해 Parse.Query를
사용하겠습니다. 이 클래스는 기본적으로 Parse 기반 데이터베이스를 위한 ORM입니다.
먼저 src/app/page.jsx를 다음으로 바꿉니다:
// src/app/page.jsx
"use client";
import NextLink from "next/link";
import {useContext, useEffect, useState} from "react";
import ParseContext from "@/app/context/parseContext";
import {Card, CardBody, Heading, Link, Spinner, Stack, Text} from "@chakra-ui/react";
export default function Home() {
const parse = useContext(ParseContext);
const [loading, setLoading] = useState(true);
const [error, setError] = useState("");
const [articles, setArticles] = useState([]);
useEffect(() => {
(async () => {
try {
const query = new parse.Query("Article");
query.descending("createdAt");
const articles = await query.find();
setArticles(articles);
} catch (error) {
setError(error);
} finally {
setLoading(false);
}
})();
}, [parse.Query]);
if (loading) {
return <Spinner size="lg"/>;
}
if (error) {
return <Text color="red">{error}</Text>;
}
return (
<>
<Stack>
{articles.map((article) => (
<Card key={article.get("slug")}>
<CardBody>
<Stack>
<Heading size="lg">
<Link as={NextLink} href={article.get("slug")}>
{article.get("title")}
</Link>
</Heading>
<Text>{article.get("shortContent")}</Text>
</Stack>
</CardBody>
</Card>
))}
</Stack>
</>
);
}
useContext()
훅을 통해 Parse 인스턴스를 얻었습니다.로딩
,오류
,문서
등 몇 가지 상태를 만들었습니다.- 페이지가 열릴 때
Parse.Query를
실행하기 위해useEffect()
훅을 사용했습니다. Parse.Query는
createdAt으로
정렬된 모든 문서를 가져옵니다.- 데이터를 렌더링하기 위해 반환 문을 수정했습니다.
그런 다음 src/app/[slug]/page.js를 이 파일로 대체합니다:
// src/app/[slug]/page.js
"use client";
import {formatDate} from "@/app/util/date-util";
import {useContext, useEffect, useState} from "react";
import ParseContext from "@/app/context/parseContext";
import {Card, CardBody, Heading, Image, Spinner, Stack, Text} from "@chakra-ui/react";
import ReactMarkdown from "react-markdown";
import ChakraUIRenderer from "chakra-ui-markdown-renderer";
export default function Article({params}) {
const parse = useContext(ParseContext);
const [loading, setLoading] = useState(true);
const [error, setError] = useState("");
const [article, setArticle] = useState(null);
useEffect(() => {
(async () => {
try {
const query = new parse.Query("Article");
query.equalTo("slug", params.slug);
const article = await query.first();
if (!article) {
setError("This article does not exist.");
} else {
setArticle(article);
}
} catch (error) {
setError(error);
} finally {
setLoading(false);
}
})();
}, [params.slug, parse.Query]);
if (loading) {
return <Spinner size="lg"/>;
}
if (error) {
return <Text color="red">{error}</Text>;
}
return (
<>
{article && (
<Stack>
<Card>
<CardBody>
<Stack>
<Heading as="h2" size="lg">{article.get("title")}</Heading>
<Text>Posted on {formatDate(article.get("createdAt"))}</Text>
{article.get("cover") && (
<Image
src={article.get("cover").url()}
alt={`${article.get("title")} cover`}
borderRadius="lg"
/>
)}
<ReactMarkdown
components={ChakraUIRenderer()}
children={article.get("content")}
skipHtml
/>
</Stack>
</CardBody>
</Card>
</Stack>
)}
</>
);
}
위의 코드에서와 같이 아날로그 개념을 사용했습니다. 두 코드 조각의 가장 큰 차이점은 이 코드에서는 모든 문서가 아닌 특정 문서를 가져온다는 점입니다.
이제 끝났습니다! 이제 로컬에서 프로젝트를 테스트해 보세요:
$ next dev
모든 것이 정상적으로 작동한다고 확인되면 VCS로 푸시합니다:
$ git add .
$ git commit -m "connected the frontend with the backend"
$ git push origin master
Back4app 컨테이너는 최신 변경 사항으로 애플리케이션을 자동으로 다시 배포합니다.
결론
결론적으로 백4앱에 풀스택 앱을 성공적으로 배포했습니다. 이 과정을 통해 애플리케이션의 프론트엔드 및 백엔드 호스팅에 대한 귀중한 경험을 얻었습니다. 이제 자체 풀스택 앱을 배포하는 데 아무런 문제가 없을 것입니다.
최종 소스 코드는 back4app-풀스택 리포지토리에서 확인할 수 있으며 프론트엔드 및 백엔드를 호스팅할 위치를 배웠습니다.