개발

[JavaScript] JavaScript Meta-framework란?

dohye1 2023. 1. 2. 20:54
반응형

remix, next등 여러 프레임워크들에 관한 아티클이나 영상을 보면서 메타프레임워크라는 키워드를 종종 봤었다.

그래서 메타프레임워크에 대해 구글링을 하던 중 내가 찾던 답이 잘 정리되어있는 글을 발견해서 정리를 해보려고 한다.

https://www.ombulabs.com/blog/javascript/what-is-a-javascript-meta-framework.html

 

What Is a JavaScript Meta-Framework? - The Lean Software Boutique

No, not that Meta What most developers call JavaScript frameworks (React, Vue, Svelte, etc) can more accurately be thought of as UI Libraries. While they can make writing the front end of websites and apps simpler, they have no opinions at all regarding wh

www.ombulabs.com

이 글을 변역해보고자 한다. 파파고 고마워!


What is a Meta-framework?

대부분의 개발자가 자바스크립트 프레임워크라고 부르는것들(React, Vue, Svelte, etc)은 사실은 UI 라이브러리라고 더 정확하게 생각할지도 모른다. 이 라이브러리들은 웹사이트와 앱의 프론트엔드작성을 더 간단하게 할 수 있지만, 그들의 stack(프론트)보다 더 뒤에서 발생하는 일들에 대해서는 고려하지 않는다. 그리고 프로젝트의 폴더와 파일을 구성하는 규정된 방법조차 없다.

 

반면에 완전한 프레임워크(Rails, Django, etc)는 일반적으로 매우 opinionated(독단적)이고, 코드가 특정한 방식으로 구성되기를 예상한다. 그리고 이는 Analysis paralysis(분석마비)와 bikeshedding을 제거하여 개발시간을 단축에도 도움이 된다.

Analysis paralysis is an inability to make a decision due to over-thinking a problem
분석마비는 생각이 너무 많아서 전혀 행동하지 못하게 되어 결정을 내릴 수 없는 지경까지 이르게 되는 현상을 의미한다.
Bikeshedding 중요한 안건을 미뤄둔 채 덜 중요한 일에 대해 깊이 의논하고 시간을 보내는 것

 

고맙게도 자바스크립트 생태계에서 위와같은 역할을 할 수 있는 라이브러리가 있다. 대부분의 UI 라이브러리를 "프레임워크"라고 부르기때문에, 완전한 기능을 갖춘 라이브러리를 "메타 프레임워크"라고 부른다.

 

간단히 말해서, 자바스크립트 개발자가 "what"에 집중하고, "how"에 대해 신경쓰도록 해준다. 즉, 자잘한것들에 대한 고민없이 중요한것들에 집중할수있도록 해준다는 의미라고 이해했다.

 

Do I need a Meta-framework?  메타프레임워크가 필요한가?

상황에 따라 다르다. 만약 몇 페이지만 있는 간단한 프로젝트를 만든다면 필요하지않을수도 있다. 하지만 매우 복잡한 사이트나 앱을 만드는 경우, 메타프레임워크를 사용하면 개발자 대신 많은 조직적 결정을 관리하기때문에 도움이 될 수 있다.

 

아래의 질문을 보고, 이 중 하나라도 "yes"일때는 메타프레임워크가 적합한 도구일것이다.

  • 풀스택 애플리케이션을 만들어야하고, 프론트엔드 이외의 부분에 대한 가이드,지침이 필요한가?
  • 당신의 앱에 SEO가 중요한가?
  • 배포전에 앱을 빌드할수도 있나?(예: static site)
  • 중대한 라우팅 요구가 있나?
  • SPA가 충족시켜주지못하는 성능 요구 사항이 있나?
  • Do opinionated tools typically improve development velocity for you and your team? (eg, less time making arbitrary decisions means more time actually building things)
    만약 독자적인 툴(메타 프레임워크)를 쓰면 당신과 당신 팀의 개발 속도가 개선되나?(예를들면, 임의의 결정을 내리는데에 시간을 적게쓰면 실제로 무언가를 만드는데에 시간을 더 쓸수있다.)

Typical Features  전형적인 특징

대부분의 메타 프레임워크는 서로서로  다양한방식으로 다르긴하지만, 유사한 특정 주요 기능이 있다.

인기있는 메타프레임워크들이 제공하는 것들을 살펴보자!

1. Static-Site Generation and/or Server-Side Rendering

SPA를 빌드할 때, 사이트에대한 client request에 앞서 HTML은 미리 빌드되지 않는다. 대신 서버는 비어있는 HTML파일을 보낸다.

<!DOCTYPE html>
<html lang="en">
  <head>
    <!-- import your app bundle -->
    <script src="./my-js-bundle.js"></script>
  </head>
  <body>
    <!--
      the app bundle will have a reference to this element
      and insert the HTML into the DOM here
    -->
    <div id="root">
  </body>
</html>

SEO가 중요한경우 이러한 종류의 웹사이트는 최선이 아니다.

검색엔진이 웹 사이트를 인덱싱할때, 자바스크립트가 로드되기전에 제공되는 HTML을 읽는데, 위와 같은 HTML은 비어있는 페이지이기때문에 당신의 앱을 분류하지않는다.

 

이 문제에 대한 2개의 일반적인 해결책이 있다. SSR(Server-Side Rendering)과 SSG(Static Site Generetion)

당신의 애플리케이션의 타입에 따라 두가지중 선택할 수 있다.

SSR

방문하는 사람에 따라 앱이 변경되는경우(예: 사용자가 로그인하는 앱) SSR 앱을 사용하는것이 좋다.
이러한 타입의 앱에서 페이지는 요청시 서버에서 구축되므로 클라이언트에 완전한 형식의 HTML 파일이 도착하게 된다.

SSG

만약 당신의 사이트가 모든 방문자에게 동일하게 보인다면(즉, 블로그나 포트폴리오) 정적으로 생성된 사이트를 선택하는것이 좋다.
이러한 종류의 앱은 다른 자바스크립트 프로젝트와 다를것없이 코드를 작성하지만, 빌드를 할때 프레임워크는 당신이 정의한 각각의 Route에 따라 static HTML페이지를 생성한다. 이렇게 하면 클라이언트로 전송되는 데이터의 양을 줄이고, 사용자의 로드 타임을 개선할 수 있다.

2. Routing

기존의 웹 사이트는 서버 측 라우팅을 사용한다. 즉, 클라이언트는 서버로 특정 URL에 대한 리소스를 요청하고, 서버는 그 리소스를 반환한다. 주목해야할 중요한 점은 각 페이지가 일반적으로 서버에 대한 새로운 요청을 한다는것이다.

 

최신 자바스크립트 기반 사이트는 일반적으로 클라이언트 측 라우팅이라는것을 사용한다. 요청당 한 페이지를 가져오는 대신, 초기 요청에서 사이트의 모든 페이지에 대한 데이터를 가져온다. 내부 링크를 클릭하면 브라우저의 History API를 호출하고, 그것은 URL을 변경한다. 그리고 그 변경된 URL과 관련된 페이지가 보여지게 된다. 여기서 주목해야할 점은 프로젝트 내부적으로 URL이 변경될때 서버로 새로운 요청이 가지않는다는것이다.

프로그래밍의 모든것과 마찬가지로, 이것은 트레이드오프이다. 페이지간의 더 빠른 네비게이팅 VS 초기 로딩시간의 추가

 

메타프레임워크가 사용하지 않는경우, 많은 자바스크립트 프로젝트에서는 컴포넌트기반의 라우팅을 한다.

import { BrowserRouter, Routes, Route } from 'react-router-dom';

const MyApp = () => {
  return (
    <BrowserRouter>
      <Routes>
        <Route path='/' element={<HomePage />} />
        <Route path='/about' element={<AboutPage />} />
        <Route path='/contact' element={<ContactPage />} />
      </Routes>
    </BrowserRouter>
  );
};

이러한 종류의 라이브러리는 추론하기 쉽고(사용하기 간단하다는 뜻?) API를 가진다. 그러나 이것들은 boilerplate같은 경향이 있으며, 관리해야하는 또다른 종속성이다.

 

현재 메타프레임워크의 인기있는 추세는 파일기반 라우팅이다. 컴포넌트를 사용하여 라우트를 선언하는 루트파일 대신, 폴더 및 파일의 구조가 사이트의 경로를 결정한다. 이들은 일반적으로  routes  나 pages같은 특별한 이름의 폴더이며 다음과 같은 구조를 갖는다.

── pages
    ├── about
    │   └── index.js
    ├── contact
    │   └── index.js
    └── index.js # the '/' path

대부분의 메타 프레임워크는 dynamic route names도 지원한다. 

pages/about/[id].js 이러한 경로의 파일이 있다면 프레임워크는 빌드시 해당 매개변수(id)를 삽입할 수 있는 방법을 제공한다.

3. Data Fetching

위의 예시처럼, 만약 당신이 dynamic route를 가지고있다면 프레임워크에게 어떤 id의 게시물을 보여줘야할지 알려주기위해 id 데이터를 가져오는 방법이 궁금할것이다. server-side routing이 있는 앱에서는 /about/:id 같은 요청을 처리하는 함수를 가지고있다.

 

  • :id 파라미터를 parse
  • 올바른 리소스 fetch
  • 해당 리소스를 클라이언트에 돌려보냄

그러나 많은 자바스크립트 메타 프레임워크는 클라이언트측 라우팅을 사용하므로 그들은 fetch request를 처리하는 API를 제공한다. 그래서 buildtime(SSG)나 runtime(SSR)에 사이트에 데이터를 채울 수 있다.

 

React 메타 프레임워크인 Next.js는 외부 리소스를 가져오는 로직을 페이지 컴포넌트에 선언할 수 있는 특별한 함수를 사용한다. 

getServerSideProps, getStaticPaths, getStaticProps

 

아래 예시는 서버측에서 페이지를 렌더링할때 데이터를 가져오는 방식을 보여준다.

export async function getServerSideProps() {
  // Fetch data from external API
  const res = await fetch(`https://my-cms.com/data`);
  const data = await res.json();

  // Pass data to the page via props
  return { props: { data } };
}

// automatically available in your page component
const MyApp = ({ data }) => {...};

그러면 메타프레임워크가 우리를 위해 라우팅과 데이터페칭을 처리한다.

그러나 이것은 우리의 사이트가 어떻게 사용자에게 serve되는지에대해서는 설명되지않는다.

routes/pages 폴더의 파일은 UI 및 API로직만 정의한다.

 

서버 로직이 없는경우 이러한 파일이 사용자에게 어떻게 전달될것인가?

4. "Serverless" Architecture

Rails 또는 Django와 같은 웹 프레임워크에서는 일반적으로 뷰와 함께 제공되는 서버로직을 작성한다.
modern 메타 프레임워크는 "Serverless"로 알려진 새로운 스타일의 아키텍처에 초점을 맞추는 경향이 있다.
당신은 "JAM Stack"에 대해 들어봤을것이다.(JavaScript + API + Markup) 

 

이러한 스타일의 주요한 목적은 개발자가 앱이 클라이언트에 어떻게 서빙되는것이아닌(not how), 무엇(what)을 서빙하는가에 대해 집중하게 하는것이다. 메타 프레임워크는 당신이 구성한 routes/pages에 맞게 요청을 처리하거나, 클라이언트측에서 라우팅을 처리하는 Single Page를 제공하기위해 빌드시 필요한 코드를 포함시킨다.

 

자신도 모르게 이미 JAM Stack을 사용하고 있었을지도 모른다. vercerl 또는 Netlify에 배포된 프로젝트가 있다면 이미 "Serverless"를 수행하고 있는것이다. 이와같은 서비스를 사용하면 앱을 매우 쉽게 배포하고 호스팅할 수 있다. 이것들은 일반적으로 모든 configurations을 처리하기위한 GUI나 CLI 방법이 있다.

 

또한, 이들중 다수는 GitHub이나 GitLab같은 인기있는 repo 호스팅 사이트와 통합되어 간단한 CI/CD 파이프라인을 가질 수 있다.

Additional Goodies

각 메타프레임워크는 일반적으로 다른것들로부터 돋보이기위해 다른 프레임워크와 차별화되는 추가기능을 제공한다.

Next.js는 <Image />같은 framework-specific 컴포넌트를 제공한다. <Image />는 lazy loading과 dynamic sizing을 위한 추상화를 포함하도록 기존의 img 태그를 확장한것이다.

Nuxt.js는 Vue의 transition 컴포넌트를 사용하여 페이지간의 transition을 커스텀하게 만든다.

SvelteKit는 links에 sveltekit:prefetch 속성을 가진다. 이 속성은 유저가 remote data가 필요한 링크에 마우스를 hover하는 경우 프레임워크에게 미리 데이터를 페치하도록 알려준다.

 

그리고 이것들은 빙산의 일각에 불과하다. 이러한 메타프레임워크들은 꾸준히 개선되고있다.

Find the right tool for your project

현재 인기있는 메타프레임워크의 몇가지 예

React

Vue

Svelte