CORS(Cross-Origin Resource Sharing) 란?

- 교차 출처 자원 공유라는 말로 서로 다른 출처간에 리소스를 공유하는 것을 허용하는 정책을 의미한다.

- 서로 다른 출처 공유에 대해서는 기본적으로 제한되어있다. (이를 SOP라 한다.)

 

*SOP (Same-Origin Policy) : 같은 출처끼리만 리소스를 공유할 수 있다는 정책
HTML태그를 통한 이미지, CSS, Script 요청은 SOP에 제한이 되지 않음

 

 

Origin : 출처를 의미하며, URL구조 / 프로토콜 + 호스트 + 포트를 합친 것을 말함

Port가 다른 경우에 다른 출처로 인식한다.

HTTP 포트 : 80 / HTTP 포트 : 443 생략 가능

 

CORS가 정의된 이유

SOP(Same-Origin Policy)의 장점

동일 출처 정책을 지키면 외부 리소스를 가져오지 못해 불편하지만, 동일 출처 정책은 보안 취약점을 노린 공격을 방어할 수 있다.

그런데 이런 SOP에도 한계가 있다.

 

SOP의 한계

현실적으로는 외부 리소스를 참고하는 것은 필요하기 때문에 외부 리소스를 가져올 수 있는 방법이 존재해야 한다.

외부 리소스를 사용하기 위한 SOP의 예외 조항이 CORS다.

 

1. Simple request (단순 요청 방법은 서버에게 바로 요청을 보내는 방법)

단순 요청은 서버에 API를 요청하고, 서버는 Access-Control-Allow-Origin 헤더를 포함한 응답을 브라우저에 보낸다. 브라우저는 Access-Control-Allow-Origin 헤더를 확인해서 CORS 동작을 수행할지 판단한다.

 

단순 요청으로 동작하기 위해서 서버로 전달하는 요청(request)이 만족해야하는 조건

1) 요청 메서드는 GET, HEAD, POST 중 하나여야 한다.

2) Accept, Accept-Language, Content-Language, Content-type, DPR, DOwnlink, Save-Data, Viewport-Width, Width 의의 헤더를 사용하면 안된다.

3) Content-type 헤더는 application/x-www-form-urlencoded, multipart/form-data, text/plain 중 하나를 사용해야 한다.

 

Preflight request

서버에 예비 요청을 보내서 안전한지 판단한 후 본 요청을 보내는 방법

실제 리소스를 요청하기 전에 OPTIONS이라는 메서드를 통해 실제 요청을 전송할지 판단한다.

OPTIONS 메서드로 서버에 예비 요청을 먼저 보내고, 서버는 이 예비 요청에 대한 응답으로 Access-Control-Allow-Origin 헤더를 포함한 응답을 브라우저에 보낸다. 브라우저는 단순 요청과 동일하게 Access-Control-Allow-Origin 헤더를 확인해서 CORS 동작을 수행할지 판단한다.

 

Preflight를 날리는 이유

브라우저가 CORS를 지원하지 않은 서버에 도달하면 요청에 대한 응답을 보내지 않아 실제 요청이 수행되지 않도록 보호하기 위함.

먼저 OPTIONS 메서드를 통해 다른 도메인의 리소스로 HTTP 요청을 보내 실제 요청이 전송하기에 안전한지 확인한다. cross-origin 요청은 유저 데이터에 영향을 줄 수 있기 때문에 이와같이 미리 전송(preflighted)합니다.

 

CORS 에러 해결 방법

- 서버에서 응답 헤더에 특정 헤더를 포함하는 방식으로 해결할 수 있다.

Access-Control-Allow-Origin : 특정 origin이 리소스에 접근이 가능하도록 허용한다.

Access-Control-Allow-Method : 특정 HTTP Method만 리소스에 접근이 가능하도록 허용한다.

Access-Control-Expose-Headers : JavaScript에서 헤더에 접근할 수 있도록 허용한다.

 

credentials request에 대해서는 추후에 추가 예정.

 

https://jakapark.tistory.com/68

 

[디자인 패턴] MVC 패턴에 대해서 간단히 알아보는 글

들어가기 전백엔드와 DB 기본을 공부하던 중 기초 디자인 패턴중인 MVC 패턴에 대해서 알게 됐다. 디자인 패턴이란 기존 환경 내에서 반복적으로 일어나는 제들을 어떻게 풀어나갈 것인가에 대

jakapark.tistory.com

 

며칠 전에 MVC 패턴에 대해서 알아보았다. (윗글 참고)

오늘은 MVC 패턴 예제 코드를 작성해보려고 한다.

 

MVC에 대해서 간단히 알아보자면

Model : 데이터를 처리
View : 유저가 보이는 화면
Controller : Model과 View를 이어주며 유저의 요청을 담당한다

 

.env 파일

DB_CONNECT = "MongoDBURI"

Config.js [./config/dbConnect.js]

// mongoose를 이용하여 MongoDB 연결
const dbConfigure = async () => {
  try {
    const connect = await mongoose.connect(process.env.DB_CONNECT);
    console.log("DB Connection Success")
  } catch(err) {
    console.log("DB Connection Fail")
  }
}

module.exports = dbConfigure;

app.js (엔드포인트 파일)

const express = require("express");
const dbConnect = require("./config/dbConnect")
const mongoose = require("mongoose");

const app = express();
const router = express.Router();

require("dotenv").config();

// view engine 사용
app.set("view engine", "ejs");
app.set("views", "./views");

// mongoDB 연결
dbConnect();

// routing
app.get("/", (req, res) => {
  res.send("Hello World");
});

// Middleware 추가
app.use(express.json()); // body에서 json 데이터를 추출하여 사용 가능
app.use(express.urlencoded({extended: true}));

// 라우팅 미들웨어
app.use("/contacts", require("./routes/contactRoutes"));

// Server 연결
app.listen(3000, () => {
  console.log("Server On~~~");
});

라우트 처리 / routes.js [./routes/routes.js]

const express = require("express");
const { getAllContacts, createContact } = require("../controllers/Controller");
const router = express.Router();

router.route("/").get(getAllContacts).post(createContact);
router.route("/:id").get((req, res) => {
  res.send(`${req.params.id} 리스트 확인`);
});

module.exports = router;

모델 / model.js [./models/models.js]

const mongoose = require("mongoose");

const shema = new mongoose.Schema(
  {
    name: {
      type: String,
      required: true
    },
    email: {
      type: String
    },
    phone: {
      type: String,
      required: [true, "전화번호를 꼭 입력해주세요!"]
    },
  },
  { timestamps: true }
);

// 스키마 -> 모델
const Contact = mongoose.model("Contact", schema);

module.exports = Contact;

 

컨트롤러 / controller.js [./controller/controller.js]

const Contact = require("../models/Model");

const getAllContacts = async (req, res) => {
  res.send("Contacts Page");
};

const createContact = async (req, res) => {
  const { name, email, phone} = req.body;
  
  if( !name || !email || !phone ){
    return res.send("필수 값이 입력되지 않았다.");
  }
  const contact = await Contact.create({ name, email, phon });
  res.send("Create Contacts");
};

module.exports = { getAllContacts, createContact };

 

View (ejs 파일 생략)

'BackEnd > Express' 카테고리의 다른 글

CORS (Cross-Origin Resource Sharing)에 대해서  (0) 2025.02.24
[NodeJS/Express] Express에 대해서  (0) 2024.06.29
const http = require("http");

// createServer 메서드가 생성한 서버를 변수나 상수로 지정해야함
const server = http.createServer((req, res) => {
  const { url, method, headers } = req;
  
  console.log(url, method, headers);
  
  // 서버에 요청을 보내지 않으면 안됨
  // res (response : 응답) 우리가 반송해야할 데이터
  res.setHeader('Content-type', 'text/html');
  // setHeader : 새로운 헤더 설정 / Content-type은 브라우저가 알고 이해하며 받아들이는 디폴트 헤더
  // 응답에 헤더를 붙이게 되고, 컨텐츠 유형은 html이라는 일련의 메타 정보를 전달하게 된다.
  
  // 데이터를 기록
  res.write("<html>");
  res.write("<head><title>My First Page</title></head>");
  res.write("<body><h1>Hello from my Node.js Server!!</h1></body>");  
  res.write("</html>");
  res.end(); // 응답 종료
});

server.listen(3000, () => {
  console.log('Server On~~~~');
});

 

req (요청)

url, method, headers 출력

 

res (응답)

MongoDB

MacOS 터미널에서 MongoDB Homebrew tap을 추가한다.

brew tap mongodb/brew

 

1. brew로 MongoDB 설치

brew install mongodb-community@8.0

 

CLI에서 MongoDB를 처리하여 싶으면 아래 명령어도 입력한다

bre install mongodb-community-shell

 

2. MongoDB 실행

brew services start mongodb-community@8.0

 

MongoDB의 포트는 27017

아래의 주소로 들어가서 하단에 문구가 뜨면 성공적으로 켜진것이다.

 

3. MongoDB 정지

brew services stop mongodb-community@8.0

 

 

'Database > MongoDB' 카테고리의 다른 글

[MongoDB] MongoDB 란 무엇인가?  (0) 2025.02.19

들어가기 전

간단한 프로젝트로 프론트와 백을 구축하고 무료로 이용할 수 있는 DB를 찾던 중 MongoDB를 알게 되서 공부하게 됐다. 이번 글에는 MongoDB가 어떤건지에 대해서 알아보는 시간을 가지려고 한다.

 

[출처] : https://velopert.com/436

 

[MongoDB] 강좌 1편: 소개, 설치 및 데이터 모델링 | VELOPERT.LOG

소개 MongoDB는 C++로 작성된 오픈소스 문서지향(Document-Oriented) 적 Cross-platform 데이터베이스이며, 뛰어난 확장성과 성능을 자랑합니다. 또한, 현존하는 NoSQL 데이터베이스 중 인지도 1위를 유지하

velopert.com

 

1. MongoDB란?

MongoDB는 테이블 형태가 아닌 document(JSON)의 형태로 데이터를 저장하며 스키마형 DB다.

SQL 보다 쉽고 빠른 장점을 가지고 있고, NoSQL방식 중 가장 인기가 많다.

 

2. NoSQL?
우리가 DB 하면 흔히 생각 나는 것이 MySQL과 같은 SQL일 것이다. 그렇다면 NoSQL은 무엇일까?

NoSQL 'Not only SQL'의 의미를 가졌으며 기존의 RDBMS의 한계를 극복하기 위해 만들어진 새로운 형태의 데이터 저장소이다.

관계형이 아닌 NoSQL은 Join이 존재하지 않는다.

 

MongoDB는 Document Oriented(문서지향) DB다. Document는 일반적으로 문서라는 뜻이다. 여기서 말하는 Document는 RDMS의 레코드와 비슷한 개념이다. 이 데이터 구조는 한 개 이상의 key-value pair으로 이루어져 있다.

MongoDB 샘플
{
   "_id" : "123",
  "username" : "Jaka",
  "name" : "Jaka_Park"
}

왼쪽이 Key, 오른쪽이 Value다.

 

Document는 동적(dynamic)의 schema 를 갖고있다. 같은 Collection 안에 Document 끼리 다른 schema를 갖고 있을 수 있다.

(즉, 서로 다른 데이터들을 가지고 있을 수 있다.)

 

3. Collection

Collection은 MongoDB Document의 모음이다. Doucment들이 Collection내부에 위치하고 있다. RDMS의 비슷한 개념이지만 RDMS와 달리 따로 Schema를 가지고 있지 않다. Document 부분 설명에 나와있듯이 각 Document들이 동적인 schema를 가지고 있다.

 

RDMS와의 비교

RDBMS MongoDB
Database Database
Table Collection
Tuple / Row Document
Column Key / Field
Table Join Embeded Documents
Primary Key Primay Key (_id)
mysqld mongod
mysql mongo

 

4. 장점

- Schema-less (Schma 가 없다. 같은 Collection 안에 있을지라도 다른 Schema를 가지고 있을 수 있다.)

- 각 객체의 구조가 뚜렷하다

- 복잡한 Join이 없다

- Deep Query ability 문서 지향적 Query Language 를 사용하여 SQL 만큼 강력한 Query 성능을 제공한다.

'Database > MongoDB' 카테고리의 다른 글

[MongoDB] MongoDB 설치 (Mac Homebrew)  (0) 2025.02.19

들어가기 전

백엔드와 DB 기본을 공부하던 중 기초 디자인 패턴중인 MVC 패턴에 대해서 알게 됐다.

 

디자인 패턴이란 기존 환경 내에서 반복적으로 일어나는 제들을 어떻게 풀어나갈 것인가에 대한 일종의 솔루션이다.

패턴이라는 의미는 반복된 현상이나 무늬라 디자인 패턴에 대해 알아볼 필요성을 느꼈다.

오늘 디자인 패턴 중 하나인 'MVC 패턴'에 대해 적어보려고 한다.

 

(얕은 지식이라 부족한 부분이나 추가할 부분은 나중에 추가 수정하겠다.)

출처

https://www.youtube.com/watch?v=2VkUyxgnFf4

https://mundol-colynn.tistory.com/147

 

MVC (Model-View-Controller) 패턴

오늘은 MVC 패턴에 대해서 정리해보겠습니다. MVC (Model-View-Controller) 패턴이란? MVC (Model-View-Controller) 패턴은 컴퓨터공학에서 소프트웨어 설계와 아키텍처를 위한 디자인 패턴 중 하나입니다. 이 패

mundol-colynn.tistory.com

 

목차

1.  MVC 패턴이란?

2. Model, View, Controller 에 대해서

3. MVC 패턴의 설계원칙 및 장점

1.  MVC 패턴이란?

MVC'Model-View-Controller' 의 약자로 컴퓨터공학에서 소프트웨어 설계와 아키텍처를 위한 디자인 패턴 중 하나다. 이 패턴은 주로 사용자 인터페이스(UI)를 가진 응용 프로그램에 사용되며, 애플리케이션의 개발과 유지 보수를 쉽게 만들어준다.

 

2. Model, View, Controller

- Model (모델)

Model은 애플리케이션의 핵심 데이터와 비즈니스 로직을 나타낸다. 데이터 저장소와의 상호 작용, 데이터 처리 및 유효성 검사와 같은 작업을 수행한다.  (외부객체로 어떤 입력 데이터를 입력 받아 데이터베이스에 넣어준다)

웹 프론트에서의 모델은 데이터베이스에 직접 접근하지 않고 API 형태로 접근한다.

 

- View

사용자에게 보여지는 애플리케이션의 UI 부분이다.

애플리케이션의 데이터 표시와 관련된 모든 작업 처리한다.

그 데이터를 가지고 화면에 그려주는 역할을 한다 html css js로 구현되어 있다

입력받은 데이터 값을 이벤트로 받아서 컨트롤러에게 전달하는 역할을 한다

 

- Controller

사용자의 입력을 처리하고, 애플리케이션의 흐름을 관리하며 모델과 뷰를 이어주는 역할을 한다.

모델로 부터 데이터를 가져오고 뷰에게 전달하는 역할 및 반대로 뷰로부터 입력 받은 값을 모델에게 전달하기도한다.

 

3. MVC 패턴의 설계원칙 및 장점

1) 각 구성 요소의 역할과 책임을 명확하게 구분

-> 각 구성 요소의 역할이 명확하게 분리되어 있어, 코드의 가독성과 유지 관리하기 좋다.

 

2) 구성 요소간의 결합도 최소화

-> 구성 요소간의 낮은 결합도로 인해, 코드의 재사용성이 높아지며, 개별 구성 요소를 독립적으로, 수정 및 테스트할 수 있다.

 

3) 코드의 재사용성 확장성과 고려

-> 동일한 모델을 여러 뷰에서 사용할 수 잇으므로, 애플리케이션의 유연성이 향상

 

들어가기 전

평소에 React를 사용할 때 CRA(Create React App) 라는 CLI 도구가 사용됐다.

React로 TailwindCss를 적용하기 위해서 공식문서를 확인하던 중 Vite에 대해서 알게 됐다.

Vite가 무엇이며 CRA (Create React App)가 있는데 왜 Vite를 사용하는지 알아보자.

 

https://ko.vite.dev/guide/

 

Vite

Vite, 프런트엔드 개발의 새로운 기준

ko.vite.dev

 

Vite란?

Vite빠르고 간결한 모던 웹 프로젝트 개발 경험에 초점을 맞춰 탄생한 빌드 도구이다.

(Vite : 프랑스어로 "빠르다"를 의미)

 

CRA (Create React App) 대신 Vite를 사용하는 이유

1. CRA로 만든 프로젝트에 node_module은 많은 용량을 차지한다.

2. CRA는 JavaScript로 구성된 Webpack(웹팩)을 사용하는데, 라이브러리가 많으면 번들링 시간이 길다.

3. Vite는 Esbuild 사용한다. (Esbuild : Go언어로 작성된 JavaScript 빌드툴, 속도가 빠른 것이 특징.) 그렇기 때문에 CRA 보다 빠르다.

Vite로 React 프로젝트 설치

1. Vite 최신버전 설치

npm install vite@latest

 

2. 프로젝트 이름 설정

나는 react-practice 라는 이름으로 생성했다.

 

3. 프레임워크 설정 (React를 설정)

 

4. variant 설정

아직은 JavaScript가 더 편하다..

 

5. cd [프로젝트 이름]

 

6. 의존성 모듈 설치

npm install

 

7. npm run dev 로 코드 실행

npm run dev

 

코드가 실행되면 아래와 같은 화면이 실행된다.

 

CRA 가 React 프로젝트 생성의 전부인줄 알았었다. 이 기회에 Vite라는 새로운 빌드 도구를 알게된 좋은 시간이었다.

앞으로는 CRA가 아닌 Vite를 더 많이 사용하게 될 것 같다.

들어가기 전

필자는 발전을 갈망하지만 갈망하기 위해서 앞만 봤지 뒤를 본 적이 없다.

"나는 왜 발전이 없을까?" 라는 생각이 종종 들기 시작했다.

여러 이유가 있겠지만 스스로를 되돌아 보는 시간이 많이 적었다고 생각한다.

그래서 내가 발전하기 위한 방법으로 '회고록'이라는 것을 선택했다.

 

뒤만 돌아봐서는 사람은 발전하지 않다.

그래서 '이렇게 했으면 더 좋았을텐데' 라는 아쉬움이 더 기억에 짙게

배기려고 노력할 것이다.

 

그러면 학문(코딩)에 있어서도 인생에 있어서도

내가 좀 더 나은 사람이 되지 않을까?

 

들어가기 전

C++, JAVA 같은 클래스 기반 객체지향 프로그래밍 언어의 특징인 클래스와 상속, 캡슐화를 위한 키워드인 public, private, protected 등이 없어서 JavaScript는 객체지향 언어가 아니라고 오해하는 경우도 있다. 하지만 JavaScript는 클래스 기반 객체지향 프로그래밍 언어보다 효율적이며 더 강력한 객체지향 프로그래밍 능력을 지니고 있는 프로토타입 기반의 객체지향 프로그래밍 언어다.

자바스크립트는 객체 기반의 프로그래밍 언어이며 자바스크립트를 이루고 있는 거의 '모든 것'이 객체다. (원시타입 제외)

 

객체지향 프로그래밍

프로그래밍에서 필요한 데이터를 추상화시켜 속성과 메서드를 가진 객체를 만들고

객체 간의 상호작용을 통해 로직을 구성하는 프로그래밍 패러다임

 

객체지향 프로그래밍 4가지 특징

1. 추상화

2. 상속

3. 캡슐화

4. 다형성

 

1. 추상화

- 객체들이 공통적으로 필요로 하는 속성이나 행위를 추출

- 불필요한 정보는 숨기고 중요한 정보만을 표현함으로써 프로그램을 간단하게 만드는 것

2. 상속

- 클래스의 속성과 행위를 하위 클래스에게 물려주거나 하위 클래스가 상위 클래스의 속성과 행위를 물려 받는 것

- 새로운 클래스가 기존의 클래스의 데이터와 연산을 이용할 수 있게 하는 기능

3. 캡슐화

- 데이터 구조와 데이터를 다루는 방법들을 결합시켜 묶는 것 (변수와 함수를 하나로 묶는 것)

- 낮은 결합도를 유지할 수 있도록 설계하는 것

4. 다형성

- 하나의 변수명, 함수명이 상황에 따라 다른 의미로 해석 될 수 있는 것

- 요소에 여러 개념을 넣어 놓는 것

하나의 클래스 내부에 같은 이름의 행위를 여러개 정의하거나 상위 클래스의 행위를 하위 클래스에서 재정의하여 사용할 수 있기 때문에 다형성을 갖게 될 수 있다.

 

오버라이딩 : 상위 클래스가 가지고 있는 메서드를 하위 클래스가 재정의해서 사용
오버로딩 : 같은 이름의 메서드가 인자의 개수나 자료형에 따라 다른 기능을 하는 것

 

 

객체 지향 프로그래밍의 장단점

장점 단점
클래스 단위로 수정이 가능하기 때문에 유지 보수가 편리 객체의 수가 많아짐에 따라 용량이 커질 수 있음
클래스를 재사용하거나 상속을 통해 확장함으로써 코드 재사용이 용이 처리 속도가 상대적으로 느림 (절차지향과 비교)
클래스 단위로 모듈화시켜서 개발하기 때문에 업무 분담이 편리하고 대규모 소프트웨어 개발에 적합 설계시 많은 시간과 노력이 필요하게 될 수 있음

 

SOLID (객체 지향 설계 원칙)

1. 단일 책임 원칙 (SRP, Single Resposibility Principle)

- 하나의 클래스는 단 하나의 책임만 질 것

- 지키지 않으면 변경에 의해 다른 책임과 관련된 코드에 영향이 갈 수 있다

 

2. 개방-폐쇄 원칙 (OCP, Open/Closed Principle)

- 소프트웨어 요소는 확장에는 열려 있으나 변경에는 닫혀 있어야 한다

- 기능을 변경하거나 확장할 수 있으면서 기능을 사용하는 코드는 수정하지 않는다

 

3. 리스코프 치환 원칙 (LSP, Liskov Substitution Principle)

- 프로그램 객체는 프로그램의 정확성을 깨뜨리지 않으면서 하위 타입의 인스턴스로 바꿀 수 있어야 함

- 상위 타입의 객체를 하위 타입의 객체로 치환해도, 상위 타입을 사용하는 프로그램은 정상적으로 동작해야한다.

 

4. 인터페이스 분리 원칙 (ISP, Interface Segregation Principle)

- 범용 인터페이스 하나보다 클라이언트를 위한 여러 개의 인터페이스로 구성하는 것이 좋다

- 인터페이스는 인터페이스를 사용하는 클라이언트를 기준으로 분리해야 한다

- 클라이언트가 필요로 하는 인터페이스로 분리함으로써 각 클라이언트가 사용하지 않는 인터페이스에 변경이 있어도 영향을 받지 않도록 만들어야 한다

 

5. 의존관계 역전 원칙 (DIP, Dependency Inversion Principle)

- 추상화에 의존

- 고수준 모듈은 저수준 모듈의 구현에 의존해서는 안되고 저수준 모듈은 고수준 모듈에서 정의한 추상 타입에 의존해야한다.

 

객체지향 OOP에 대해서 간단히 포스팅했는데 부족한 부분에 대한 보충 설명은 추후에 하겠습니다.

 

https://jongminfire.dev/%EA%B0%9D%EC%B2%B4%EC%A7%80%ED%96%A5-%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%B0%8D%EC%9D%B4%EB%9E%80

https://www.yes24.com/Product/Goods/9274256

 

 

모던 자바스크립트 Deep Dive - 예스24

『모던 자바스크립트 Deep Dive』에서는 자바스크립트를 둘러싼 기본 개념을 정확하고 구체적으로 설명하고, 자바스크립트 코드의 동작 원리를 집요하게 파헤친다. 따라서 여러분이 작성한 코드

www.yes24.com

 

'Javascript' 카테고리의 다른 글

[JS] Class 작동원리  (0) 2024.11.15
[JS] 클로저와 스코프  (0) 2024.10.17
[JS] reduce() 에 대해서  (0) 2024.06.20
[JS] 동기(synchronous) 비동기(asynchronous)  (0) 2024.05.13
[JS] 구조 분해 할당  (0) 2024.04.24

출처 : https://www.yes24.com/Product/Goods/92742567

 

모던 자바스크립트 Deep Dive - 예스24

『모던 자바스크립트 Deep Dive』에서는 자바스크립트를 둘러싼 기본 개념을 정확하고 구체적으로 설명하고, 자바스크립트 코드의 동작 원리를 집요하게 파헤친다. 따라서 여러분이 작성한 코드

www.yes24.com

 

Class 란 무엇인가?

- 프로토타입객체를 생성하기 위한 템플릿

- ES6 생긴 문법 (ES6 이전에도 생성자 함수로 프로토타입 객체를 생성할 수 있었음)

- 새로운 객체를 생성하는 메커니즘

- 읽는 사람 or 작성하는 사람이 편하게 디자인 된 문법(문법적 설탕)으로 직관적인 특징을 지님

객체지향
프로그램을 객체들로 구성하고 서로 상호작용을 통해 구현하는 방법 (방법론)

프로토타입
코드를 그들의 클래스들에 의존시키지 않고 기존 객체들을 복사할 수 있도록 하는 생성 디자인 패턴
프로토타입을 통해 객체지향 언어의 상속을 구현

프로토타입 기반 언어
모든 객체들이 메소드와 속성들을 상속 받기 위한 템플릿으로써 프로토타입 객체를 가진다

 

Class의 특징

- new 연산자가 있어야 호출이 가능

- 상속을 지원하는 extends와 super 키워드를 제공 (상속 관계 구현을 간결하고 명료하게함)

- 생성자 함수 기반의 객체 생성방식보다 견고하고 명료

 

Class는 어떤 타입일까?

// 클래스 선언문
class Person {}

console.log(typeof Person); // function

클래스 선언문으로 정의한 클래스는 함수 선언문과 같이 소스코드 평과 과정, 즉 런타임 이전에 먼저 평가되어 함수 객체를 생성한다. 이 때 클래스가 평가되어 생성된 함수 객체는 생성자 함수로서 호출할 수 있는, 즉 constructor다. 생성자 함수로서 호출할 수 있는 함수는 함수 정의가 평가되어 함수 객체를 생성하는 시점에 프로토타입도 더불어 생성된다. 프로토타입과 생성자 함수는 단독으로 존재할 수 없고 언제나 쌍으로 존재하기 때문이다.

 

Class 클래스는 클래스 정의 이전에 참조가 불가능

console.log(Person);
// 참조 에러 ReferenceError : Cannot access 'Person' before initiailization

// 클래스 선언문
class Person {}

 

Class의 메서드의 종류

- Class 에 정의할 수 있는 메서드 3개

1. constructor (생성자)

2. 프로토타입 메서드

3. 정적 메서드

 

1. constructor (생성자)

> constructor는 인스턴스를 생성하고 초기화 하기 위한 특수한 메소드

class Person {
  // 생성자
  constructor(name){
    // 인스턴스 생성 및 초기화
    this.name = name;
  }
}

// class는 인스턴스를 생성하기 위한 생성자 함수
console.log(typeof Person); // function
console.dir(Person);

// 모든 함수 객체가 가지고 있는 prototype 프로퍼티가 가리키는 프로토타입 객체의
// constructor 프로퍼티는 클래스 자기 자신을 가리킴.
// 클래스가 인스턴스를 생성하는 생성자 함수를 의미

 

2. 프로토타입 메서드

> 생성자 함수를 사용하여 인스턴스를 생성하는 경우 프로토타입 메서드를 생성하기 위해서는 다음과 같이 명시적으로 프토타입 메서드를 추가해야한다.

class Person {
  // 생성자
  consturctor(name) {
  	// 인스턴스 생성 및 초기화
    this.name = name;
  }
  
  // 프로토타입 메서드
  sayHello(){
  	console.log(`Hello! My name is ${this.name}`);
  }
}

const me = new Person('Jaka');
me.sayHello(); // Hello! My name is Jaka

 

3. 정적 메서드

> 정적 메서드는 인스턴스를 생성하지 않아도 호출할 수 있는 메서드를 의미.

class Person {
  // 생성자
  constructor(name){
    this.name = name;
  }
  
  // 정적 메서드 : class에서는 앞에 static을 붙여야함
  static sayHello() {
    console.log('Hello');
  }
}

Person.sayHello(); // Hello
// 인스턴스를 생성하면 TypeError가 뜬다.

 

 

클래스 인스턴스 생성과정

1. 인스턴스 생성과 this 바인딩

- new 연산자와 함께 클래스를 호출하면 constructor의 내부 코드가 실행되기 전 암묵적으로 빈객체가 생성

 (빈 객체는 미완성된 클래스가 생성한 인스턴스)

- 이때 클래스가 생성한 인스턴스의 프로토타입으로 클래스의 프로토타입 프로퍼티가 가리키는 객체가 설정

- 그리고 암묵적으로 생성된 비 객체, 즉 인스턴스는 this에 바인딩 됨

- 따라서 constructor 내부의 this는 클래스가 생성한 인스턴스를 가리킴

 

2. 인스턴스 초기화

- constructor의 내부 코드가 실행되어 this에 바인딩 되어 있는 인스턴스를 초기화.

(this 바인딩 되어 있는 인스턴스를 추가하고 constructor가 인수로 전달받은 초기값으로 인스턴스의 프로퍼티값을 초기화.)

 

3. 인스턴스의 반환

- 클래스의 모든 처리가 끝나며 완성된 인스턴스가 바인딩된 

class Person {
  // 생성자
  constructor(name) {
  	// 1. 암묵적으로 인스턴스가 생성되고 this에 바인딩
    console.log(this); // Person {}
    
    // 2. this에 바인딩되어 있는 인스턴스를 초기화
    this.name = name;
    
  	// 3. 완성된 인스턴스가 바인딩된 this가 암묵적으로 반환
  }
}

'Javascript' 카테고리의 다른 글

[JS] 객체 지향 프로그래밍 (OOP)  (0) 2024.11.28
[JS] 클로저와 스코프  (0) 2024.10.17
[JS] reduce() 에 대해서  (0) 2024.06.20
[JS] 동기(synchronous) 비동기(asynchronous)  (0) 2024.05.13
[JS] 구조 분해 할당  (0) 2024.04.24

+ Recent posts