๋ณธ๋ฌธ ๋ฐ”๋กœ๊ฐ€๊ธฐ
IT

BFF(Backend For Frontend) ๊ฐœ๋… ๋ฐ ํ™œ์šฉ

by ๐Ÿ’ฒ๐ŸŽตโœ–๏ธโœ”๏ธโ˜ผ 2024. 3. 1.
728x90

BFF(Backend For Frontend) ๊ฐœ๋… ๋ฐ ํ™œ์šฉ

BFF๋ž€ ๋ฌด์—‡์ธ๊ฐ€?

BFF(Backend For Frontend)๋Š” ํด๋ผ์ด์–ธํŠธ์™€ ์„œ๋ฒ„ ์‚ฌ์ด์˜ ํ†ต์‹ ์„ ํšจ์œจ์ ์œผ๋กœ ๊ด€๋ฆฌํ•˜๊ธฐ ์œ„ํ•ด ๋„์ž…๋œ ๊ฐœ๋…์ž…๋‹ˆ๋‹ค. ํด๋ผ์ด์–ธํŠธ ๊ฐœ๋ฐœ์ž๋“ค์ด ์„œ๋ฒ„์—์„œ ํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ๋ฅผ ํšจ์œจ์ ์œผ๋กœ ๊ฐ€์ ธ์˜ค๊ณ  ์ œ์–ดํ•˜๊ธฐ ์œ„ํ•œ ์ค‘๊ฐ„ ๊ณ„์ธต์œผ๋กœ ์ž‘๋™ํ•ฉ๋‹ˆ๋‹ค.

BFF์˜ ์œ ๋ž˜

BFF๋ผ๋Š” ์šฉ์–ด๋Š” ํ”„๋ก ํŠธ์—”๋“œ์™€ ๋ฐฑ์—”๋“œ ์‚ฌ์ด์˜ ๊ฒฝ๊ณ„๋ฅผ ์•ฝํ™”์‹œํ‚ค๊ณ ์ž Facebook์—์„œ ์ฒ˜์Œ ์†Œ๊ฐœ๋˜์—ˆ์Šต๋‹ˆ๋‹ค. Facebook์€ ๋‹ค์–‘ํ•œ ํ”Œ๋žซํผ์—์„œ ๋™์ž‘ํ•˜๋Š” ์•ฑ์„ ๊ฐœ๋ฐœํ•˜๋ฉด์„œ ํด๋ผ์ด์–ธํŠธ์™€ ์„œ๋ฒ„ ๊ฐ„์˜ ํ†ต์‹ ์„ ํšจ๊ณผ์ ์œผ๋กœ ๊ด€๋ฆฌํ•˜๊ธฐ ์œ„ํ•ด BFF๋ฅผ ๋„์ž…ํ–ˆ์Šต๋‹ˆ๋‹ค.

BFF์˜ ์—ญํ• 

  1. ํด๋ผ์ด์–ธํŠธ ํŠนํ™” ๋ฐ์ดํ„ฐ ์ œ๊ณต: ํด๋ผ์ด์–ธํŠธ์— ํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ๋ฅผ ํšจ์œจ์ ์œผ๋กœ ๊ฐ€์ ธ์™€ ์ œ๊ณตํ•จ์œผ๋กœ์จ ๋ถˆํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ ์ „์†ก์„ ์ตœ์†Œํ™”ํ•ฉ๋‹ˆ๋‹ค.
  2. ํ”„๋ก ํŠธ์—”๋“œ ๊ฐœ๋ฐœ์ž ๊ฒฝํ—˜ ํ–ฅ์ƒ: ํด๋ผ์ด์–ธํŠธ ๊ฐœ๋ฐœ์ž๊ฐ€ ์„œ๋ฒ„์™€์˜ ์ƒํ˜ธ ์ž‘์šฉ์„ ๋” ์‰ฝ๊ฒŒ ๊ด€๋ฆฌํ•  ์ˆ˜ ์žˆ๋„๋ก ๋•์Šต๋‹ˆ๋‹ค.
  3. ๋งˆ์ดํฌ๋กœ์„œ๋น„์Šค์™€์˜ ํ†ตํ•ฉ: ๊ฐ ๋งˆ์ดํฌ๋กœ์„œ๋น„์Šค์˜ API๋ฅผ ์ ์ ˆํ•˜๊ฒŒ ์กฐํ•ฉํ•˜์—ฌ ํด๋ผ์ด์–ธํŠธ์— ํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ๋ฅผ ์ œ๊ณตํ•ฉ๋‹ˆ๋‹ค.

BFF ์‚ฌ์šฉ ์ƒํ™ฉ

  1. ๋‹ค์–‘ํ•œ ํด๋ผ์ด์–ธํŠธ ์ง€์›: ๋ชจ๋ฐ”์ผ ์•ฑ, ์›น ์•ฑ, ๋ฐ์Šคํฌํ†ฑ ์•ฑ ๋“ฑ ์—ฌ๋Ÿฌ ํ”Œ๋žซํผ์—์„œ ๋™์ž‘ํ•˜๋Š” ํด๋ผ์ด์–ธํŠธ๋ฅผ ์ง€์›ํ•  ๋•Œ BFF๊ฐ€ ํšจ๊ณผ์ ์ž…๋‹ˆ๋‹ค.
  2. ์„œ๋ฒ„๋ฆฌ์Šค ์•„ํ‚คํ…์ฒ˜์™€์˜ ์ ํ•ฉ์„ฑ: ์„œ๋ฒ„๋ฆฌ์Šค ํ™˜๊ฒฝ์—์„œ ์—ฌ๋Ÿฌ ์„œ๋น„์Šค ๊ฐ„์˜ ํ†ต์‹ ์„ ๊ด€๋ฆฌํ•˜๊ธฐ ์œ„ํ•ด BFF๋ฅผ ๋„์ž…ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
  3. ๋งˆ์ดํฌ๋กœ์„œ๋น„์Šค ์•„ํ‚คํ…์ฒ˜: ๊ฐ ๋งˆ์ดํฌ๋กœ์„œ๋น„์Šค๊ฐ€ ์ œ๊ณตํ•˜๋Š” API๋ฅผ ์กฐํ•ฉํ•˜์—ฌ ํด๋ผ์ด์–ธํŠธ์— ํšจ์œจ์ ์œผ๋กœ ์ „๋‹ฌํ•  ๋•Œ BFF๋ฅผ ์‚ฌ์šฉํ•ฉ๋‹ˆ๋‹ค.

BFF์˜ ์žฅ๋‹จ์ 

์žฅ์ 

  1. ํด๋ผ์ด์–ธํŠธ ๊ฐœ๋ฐœ์ž ํŽธ์˜์„ฑ: ์„œ๋ฒ„์™€์˜ ํ†ต์‹ ์„ ๊ด€๋ฆฌํ•จ์œผ๋กœ์จ ํด๋ผ์ด์–ธํŠธ ๊ฐœ๋ฐœ์ž๋“ค์ด ๋” ์‰ฝ๊ฒŒ ์ž‘์—…ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
  2. ๋ฐ์ดํ„ฐ ํšจ์œจ์„ฑ: ํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ๋งŒ์„ ๊ฐ€์ ธ์™€ ์ œ๊ณตํ•˜๋ฏ€๋กœ ๋ถˆํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ ํŠธ๋ž˜ํ”ฝ์„ ์ตœ์†Œํ™”ํ•ฉ๋‹ˆ๋‹ค.

๋‹จ์ 

  1. ์ถ”๊ฐ€์ ์ธ ๊ณ„์ธต: BFF ๋„์ž…์œผ๋กœ ์ถ”๊ฐ€์ ์ธ ์„œ๋ฒ„ ๊ณ„์ธต์ด ๋ฐœ์ƒํ•˜๋ฏ€๋กœ ๊ด€๋ฆฌ์™€ ์œ ์ง€๋ณด์ˆ˜๊ฐ€ ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค.
  2. ํด๋ผ์ด์–ธํŠธ ์ข…์†์„ฑ: ํด๋ผ์ด์–ธํŠธ์™€ ๊ฐ•ํ•˜๊ฒŒ ๊ฒฐํ•ฉ๋  ์ˆ˜ ์žˆ์–ด, ํด๋ผ์ด์–ธํŠธ์™€์˜ ์ข…์†์„ฑ์„ ๊ณ ๋ คํ•ด์•ผ ํ•ฉ๋‹ˆ๋‹ค.

BFF๋ฅผ ์ดํ•ดํ•˜๋Š” ์˜ˆ์ œ

์˜ˆ์ œ 1: Express๋ฅผ ์ด์šฉํ•œ BFF ๊ตฌํ˜„

const express = require('express');
const axios = require('axios');

const app = express();
const port = 3000;

app.get('/bff/data', async (req, res) => {
  try {
    // ์„œ๋ฒ„์—์„œ ํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ๋ฅผ ๊ฐ€์ ธ์˜ด
    const response = await axios.get('http://backend-api/data');

    // ํด๋ผ์ด์–ธํŠธ์— ํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ๋งŒ ์ถ”์ถœํ•˜์—ฌ ์‘๋‹ต
    const responseData = {
      clientData: response.data.clientData,
      additionalInfo: 'Some additional information',
    };

    res.json(responseData);
  } catch (error) {
    console.error(error);
    res.status(500).send('Internal Server Error');
  }
});

app.listen(port, () => {
  console.log(`BFF server is running at http://localhost:${port}`);
});

์˜ˆ์ œ 2: React ์•ฑ์—์„œ BFF ์‚ฌ์šฉ

import React, { useEffect, useState } from 'react';
import axios from 'axios';

const App = () => {
  const [data, setData] = useState(null);

  useEffect(() => {
    const fetchData = async () => {
      try {
        // BFF๋ฅผ ํ†ตํ•ด ํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ๋ฅผ ๊ฐ€์ ธ์˜ด
        const response = await axios.get('http://localhost:3000/bff/data');
        setData(response.data);
      } catch (error) {
        console.error(error);
      }
    };

    fetchData();
  }, []);

  return (
    <div>
      {data ? (
        <div>
          <h1>{data.clientData}</h1>
          <p>{data.additionalInfo}</p>
        </div>
      ) : (
        <p>Loading...</p>
      )}
    </div>
  );
};

export default App;

์—ฐ๊ด€๋œ ๊ธฐ์ˆ 

GraphQL

GraphQL์€ ํด๋ผ์ด์–ธํŠธ๊ฐ€ ํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ๋ฅผ ๋ช…์‹œ์ ์œผ๋กœ ์š”์ฒญํ•  ์ˆ˜ ์žˆ๋Š” ์ฟผ๋ฆฌ ์–ธ์–ด๋กœ, BFF์™€์˜ ํšจ์œจ์ ์ธ ํ†ต์‹ ์— ํ™œ์šฉ๋  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ํด๋ผ์ด์–ธํŠธ๊ฐ€ ํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ๋งŒ์„ ์š”์ฒญํ•˜์—ฌ ๋ถˆํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ๋ฅผ ๋ฐ›์ง€ ์•Š๋„๋ก ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

RESTful API

BFF๊ฐ€ ์—ฌ๋Ÿฌ ๋งˆ์ดํฌ๋กœ์„œ๋น„์Šค์˜ ๋ฐ์ดํ„ฐ๋ฅผ ์กฐํ•ฉํ•˜์—ฌ ์ œ๊ณตํ•  ๋•Œ, ๊ฐ ๋งˆ์ดํฌ๋กœ์„œ๋น„์Šค๋Š” RESTful API๋ฅผ ํ†ตํ•ด ํ‘œ์ค€ํ™”๋œ ๋ฐฉ์‹์œผ๋กœ ๋ฐ์ดํ„ฐ๋ฅผ ์ œ๊ณตํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

Serverless

BFF๋ฅผ ์„œ๋ฒ„๋ฆฌ์Šค ์•„ํ‚คํ…์ฒ˜์— ์ ์šฉํ•  ๋•Œ, AWS Lambda, Azure Functions, Google Cloud Functions์™€ ๊ฐ™์€ ์„œ๋ฒ„๋ฆฌ์Šค ํ•จ์ˆ˜๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ BFF๋ฅผ ๊ตฌํ˜„ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

๊ฒฐ๋ก 

BFF๋Š” ํด๋ผ์ด์–ธํŠธ์™€ ์„œ๋ฒ„ ๊ฐ„์˜ ํ†ต์‹ ์„ ํšจ์œจ์ ์œผ๋กœ ๊ด€๋ฆฌํ•˜๊ธฐ ์œ„ํ•œ ์ค‘๊ฐ„ ๊ณ„์ธต์œผ๋กœ, ํด๋ผ์ด์–ธํŠธ ๊ฐœ๋ฐœ์ž๋“ค์ด ๋” ํšจ๊ณผ์ ์œผ๋กœ ์ž‘์—…ํ•  ์ˆ˜ ์žˆ๋„๋ก ๋„์™€์ค๋‹ˆ๋‹ค. ํŠนํžˆ ์—ฌ๋Ÿฌ ํ”Œ๋žซํผ์—์„œ ๋™์ž‘ํ•˜๋Š” ํด๋ผ์ด์–ธํŠธ๋ฅผ ์ง€์›ํ•˜๊ฑฐ๋‚˜, ์„œ๋ฒ„๋ฆฌ์Šค ๋ฐ ๋งˆ์ดํฌ๋กœ์„œ๋น„์Šค ์•„ํ‚คํ…์ฒ˜์™€ ํ†ตํ•ฉํ•  ๋•Œ BFF์˜ ํ™œ์šฉ์ด ํšจ๊ณผ์ ์ž…๋‹ˆ๋‹ค.

๋Œ“๊ธ€