[TIL] 220321

dev·2022년 3ė›” 21ėž
0

TIL

ëŠĐ록 ëģīęļ°
200/204
post-thumbnail

📝 ė˜Ī늘 한 ęēƒ

  1. react rendering

📖 학ėŠĩ ėžë̌

  1. react ëŽļė„œ

📚 ë°°ėšī ęēƒ

ėƒˆëĄ­ęēŒ ė•ŒęēŒ ëœ ë‚īėšĐėī거나 ėīí•ī하ęļ° ė–īë Īė› ë˜ ëķ€ëķ„ë§Œ ė •ëĶŽ

1. JSX ė†Œę°œ

1) XSS ęģĩęēĐ ë°Đė§€

[HTTP/ëģīė•ˆ] 큮로ėŠĪ ė‚ŽėīíŠļ ėŠĪ큎ëĶ―íŠļ ęģĩęēĐ( XSS : Cross-site Scripting Attacks ) ė°ļęģ 

XSS(cross-site-scripting) ęģĩęēĐėī란 ė›đė‚ŽėīíŠļ ęī€ëĶŽėžę°€ ė•„ë‹Œ ėī가 ė›đ 페ėī맀뗐 ė•…ė„ą ėŠĪ큎ëĶ―íŠļëĨž ė‚―ėž…í•˜ëŠ” ęēƒė„ 말한ë‹Ī.
ę·ļ런데 ęļ°ëģļė ėœžëĄœ React DOMė€ JSX뗐 ė‚―ėž…ëœ ëŠĻ든 ę°’ė„ 렌더링하ęļ° ė „ė— ėīėŠĪėž€ėī프 한ë‹Ī. (ėīėŠĪėž€ėī핑 ė°ļęģ )
ë”°ëžė„œ, ė• í”ŒëĶŽėž€ėīė…˜ė—ė„œ ëŠ…ė‹œė ėœžëĄœ ėž‘ė„ąë˜ė§€ ė•Šė€ ë‚īėšĐė€ ė‚―ėž…ë  눘 ė—†ë‹Ī.

ë‹Īė‹œ 말í•ī, JSX뗐 ė‚―ėž…ëœ ëŠĻ든 ę°’ė€ 렌더링 되ęļ° ė „ė— ëŽļėžė—ī로 ëģ€í™˜ë˜ęļ° ë•ŒëŽļ뗐 ė•…ė„ą ėŠĪ큎ëĶ―íŠļëĨž ė‚―ėž…í•˜ëŠ” XSS ęģĩęēĐė„ ë°Đė§€í•  눘 ėžˆëŠ” ęēƒėīë‹Ī.

2. JSX ėīí•ī하ęļ°

1) propė˜ ęļ°ëģļę°’ė€ 'true'ėīë‹Ī

<MyTextBox autocomplete />

// ėœ„ė™€ ė•„ëž˜ëŠ” ę°™ė€ 표현ėīë‹Ī.
// ėžë°˜ė ėœžëĄœ prop뗐 ę°’ė„ ė „ë‹Ží•˜ëŠ” ęēƒė„ ęķŒėžĨ한ë‹Ī. ES6 ëŽļëē•ęģž í—·ę°ˆëĶī 눘 ėžˆęļ° ë•ŒëŽļėīë‹Ī.

<MyTextBox autocomplete={true} />

2) ė†ė„ą 펾ėđ˜ęļ° - ė „ę°œ ė—°ė‚°ėž(...) ė‚ŽėšĐ

  • HEAD ėŧī폮넌íŠļ가 ė‚ŽėšĐ할 props뗐 í•īë‹đ하는 객ėēīëĨž ëķ€ëŠĻ ėŧī폮넌íŠļ(App2)가 ėīëŊļ 氀맀ęģ  ėžˆë‹ĪëĐī, ė „ę°œ ė—°ė‚°ėž(spread ė—°ė‚°ėž)ëĨž ė‚ŽėšĐí•ī ė „ėēī 객ėēīëĨž ėžė‹ ėŧī폮넌íŠļ(ė͉, HEAD ėŧī폮넌íŠļ Greeting)로 ę·ļ대로 넘ęēĻėĪ„ 눘 ėžˆë‹Ī.
function App1() {
  return <Greeting firstName="Ben" lastName="Hector" />;
}

// ėœ„ė™€ ė•„ëž˜ëŠ” ę°™ė€ 표현ėīë‹Ī.

function App2() {
  const props = {firstName: 'Ben', lastName: 'Hector'};
  return <Greeting {...props} />;
}
  • HEAD ėŧī폮넌íŠļė—ė„œ HEAD ėŧī폮넌íŠļ가 ė‚ŽėšĐ하ęēŒ ë  íŠđė • propė„ ė„ íƒí•˜ęģ , 나ëĻļė§€ propė€ ė „ę°œ ė—°ė‚°ėžëĨž í†ĩí•ī 넘ęļļ 눘 ėžˆë‹Ī. ėī는 HEAD ėŧī폮넌íŠļëĨž 뜠ėšĐ하ęēŒ ėžŽė‚ŽėšĐ할 눘 ėžˆë„ëĄ 한ë‹Ī.
const Button = props => {
  const { kind, ...other } = props;
  const className = kind === "primary" ? "PrimaryButton" : "SecondaryButton";
  return <button className={className} {...other} />;
};

const App = () => {
  return (
    <div>
      <Button kind="primary" onClick={() => console.log("clicked!")}>
        Hello World!
      </Button>
    </div>
  );
};

3) í•Ļ눘ëĨž ėžė‹ėœžëĄœ ė‚ŽėšĐ하ęļ°

ëģīí†ĩ JSX뗐 ė‚―ėž…ëœ JavaScript í‘œí˜„ė‹ė€ ëŽļėžė—īėī나 React element 또는 ėīë“Īė˜ ë°°ė—ī로 í™˜ė‚°ëœë‹Ī.

ę·ļ럮나, props.children 또한 ë‹ĪëĨļ propë“Īęģž ë§ˆė°Žę°€ė§€ëĄœ React가 렌더링 할 눘 ėžˆëŠ” 데ėīí„°ė˜ 형태ëŋ ė•„ë‹ˆëž (onClick ėīëēĪíŠļ ëĶŽėŠĪ너 í•Ļ눘ëĨž 넘ęļ°ëŠ” ęēƒėē˜ëŸž) ė–īë–Ī í˜•íƒœė˜ 데ėī터도 넘ęēĻ마 눘 ėžˆë‹Ī.

ė•„ëž˜ė˜ ė˜ˆė‹œė—ė„œëŠ” props.childrenė„ í†ĩí•īė„œ ė―œë°ąė„ 넘ęēĻë°›ė•„ 반ëģĩ렁ėļ ėŧī폮넌íŠļëĨž ėƒė„ąí•˜ęģ  ėžˆë‹Ī.

function Repeat(props) {
  // console.log(props); => {numTimes: 10, children: ƒ}

  let items = [];

  for (let i = 0; i < props.numTimes; i++) {
    items.push(props.children(i));
  }

  return <div>{items}</div>; {/* React elementë“Īė˜ ë°°ė—īė„ 반환한ë‹Ī */}
}

function ListOfTenThings() {
  return (
    <Repeat numTimes={10}>
      {(index) => <div key={index}>This is item {index} in the list</div>} {/* props.children */}
    </Repeat>
  );
}

const root = document.getElementById("root");
ReactDOM.render(<ListOfTenThings />, root);

4) ėĄ°ęąīëķ€ ë Œë”ë§

0ęģž ę°™ė€ falsy ę°’ė€ React가 렌더링하ęļ° ë•ŒëŽļ뗐 ėĢžė˜í•īė•ž 한ë‹Ī.

const falsy = 0;
const SomeComponent = () => <p>I am something else.</p>;
const Article = () => (
  <div className="something">
    {true && <SomeComponent />} {/* ëļŒëžėš°ė €ė— <SomeComponent /> 가 렌더링ëĻ */}
    {false && <SomeComponent />} {/* ëļŒëžėš°ė €ė— ė•„ëŽīęēƒë„ ë Œë”ë§ë˜ė§€ ė•ŠėŒ */}
    {falsy && <SomeComponent />} {/* ëļŒëžėš°ė €ė— 0ėī 렌더링ëĻ */}
  </div>
);

const root = document.getElementById("root");
ReactDOM.render(<Article />, root);

cf. true, false, undefined ę°™ė€ ę°’ė„ ėķœë Ĩ하ęģ  ė‹ķë‹ĪëĐī String(false) ėē˜ëŸž ëŽļėžė—ī로 바ęŋ”ė•ž 한ë‹Ī.

3. Components뙀 Props

1) props는 ė―ęļ° ė „ėšĐėž…ë‹ˆë‹Ī.

ëŠĻ든 React ėŧī폮넌íŠļ는 ėžė‹ ė˜ propsëĨž ë‹Īḛ̈ 때 ë°˜ë“œė‹œ 눜눘 í•Ļ눘ėē˜ëŸž ë™ėž‘í•œë‹Ī.
ėŧī폮넌íŠļ í•Ļ눘 ë‚īëķ€ė—ė„œ ėļėžëĄœ ë°›ė€ propsė˜ ę°’ė„ ėˆ˜ė •í•īė„œ ė‚ŽėšĐí•īė„œëŠ” ė•ˆëœë‹Ī.

2) ėŧī폮넌íŠļ ėķ”ėķœ

UIė˜ ėžëķ€ę°€ ė—ŽëŸŽ ëēˆ ė‚ŽėšĐ되거나(Button, Panel, Avatar) UIė˜ ėžëķ€ę°€ ėžėēīė ėœžëĄœ ëģĩėžĄí•œ ęē―뚰(App, FeedStory, Comment)ė—ëŠ” ëģ„ë„ė˜ ėŧī폮넌íŠļ로 만드는 ęēƒėī ėĒ‹ë‹Ī.

  • props
function Img(props) { // props.user === { avatarUrl: "...", name: "..." }
  return (
    <img className="Avatar" src={props.user.avatarUrl} alt={props.user.name} />
  );
}

function UserInfo(props) { // props.user === { avatarUrl: "...", name: "..." }
  return (
    <div className="UserInfo">
      <Img user={props.user} />
      <div className="UserInfo-name">
        {props.user.name}
      </div>
    </div>
  );
}

function Comment(props) { // props === { author: "...", text: "...", date: ... }
  const formatDate = (date) => date + "ė‹œ";

  return (
    <div className="Comment">
      <UserInfo user={props.author} />
      <div className="Comment-text">
        {props.text}
      </div>
      <div className="Comment-date">
        {formatDate(props.date)}
      </div>
    </div>
  );
}

function App() {
  const author = {
    name: "Syong",
    avatarUrl: "https://t1.daumcdn.net/cfile/tistory/24283C3858F778CA2E",
  };

  return (
    <div>
      <Comment author={author} text="댕댕ėīėž…ë‹ˆë‹Ī" date={new Date().getHours()} />
    </div>
  );
};

const root = document.getElementById("root");
ReactDOM.render(<App />, root);
  • ES6 ęĩŽėĄ° ëķ„í•ī 할ë‹đ
function UserInfo({user}) { // // props.user === { avatarUrl: "...", name: "..." }
  return (
    <div className="UserInfo">
      <Img user={user} />
      <div className="UserInfo-name">
        {user.name}
      </div>
    </div>
  );
}

function Img({user}) { // props.user === { avatarUrl: "...", name: "..." }
  return (
    <img className="Avatar" src={user.avatarUrl} alt={user.name} />
  );
}

function Comment({author, text, date}) { // props === { author: "...", text: "...", date: "..." }
  const formatDate = (date) => date + "ė‹œ";

  return (
    <div className="Comment">
      <UserInfo user={author} />
      <div className="Comment-text">
        {text}
      </div>
      <div className="Comment-date">
        {formatDate(date)}
      </div>
    </div>
  );
}

function App() {
  const author = {
    name: "Syong",
    avatarUrl: "https://t1.daumcdn.net/cfile/tistory/24283C3858F778CA2E",
  };

  return (
    <div>
      <Comment author={author} text="댕댕ėīėž…ë‹ˆë‹Ī" date={new Date().getHours()} />
    </div>
  );
};

const root = document.getElementById("root");
ReactDOM.render(<App />, root);

âœĻ ë‚īėž 할 ęēƒ

  1. react state
profile
dev log

0ę°œė˜ 댓ęļ€