๋‚ด์žฅ ๋ธŒ๋ผ์šฐ์ € <style> ์ปดํฌ๋„ŒํŠธ๋ฅผ ์‚ฌ์šฉํ•˜๋ฉด ๋ฌธ์„œ์— ์ธ๋ผ์ธ CSS ์Šคํƒ€์ผ์‹œํŠธ๋ฅผ ์ถ”๊ฐ€ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

<style>{` p { color: red; } `}</style>

๋ ˆํผ๋Ÿฐ์Šค

<style>

๋ฌธ์„œ์— ์ธ๋ผ์ธ ์Šคํƒ€์ผ์„ ์ถ”๊ฐ€ํ•˜๋ ค๋ฉด, ๋‚ด์žฅ ๋ธŒ๋ผ์šฐ์ € <style> ์ปดํฌ๋„ŒํŠธ๋ฅผ ๋ Œ๋”๋งํ•˜์„ธ์š”. ์–ด๋–ค ์ปดํฌ๋„ŒํŠธ์—์„œ๋“  <style>์„ ๋ Œ๋”๋งํ•  ์ˆ˜ ์žˆ์œผ๋ฉฐ, React๋Š” ํŠน์ • ๊ฒฝ์šฐ์— ํ•ด๋‹น DOM ์š”์†Œ๋ฅผ ๋ฌธ์„œ์˜ <head>์— ๋ฐฐ์น˜ํ•˜๊ณ  ๋™์ผํ•œ ์Šคํƒ€์ผ์„ ์ค‘๋ณต ์ œ๊ฑฐํ•ฉ๋‹ˆ๋‹ค.

<style>{` p { color: red; } `}</style>

์•„๋ž˜ ์˜ˆ์‹œ๋ฅผ ์ฐธ๊ณ ํ•˜์„ธ์š”.

Props

<style>์€ ๋ชจ๋“  ๊ณตํ†ต ์—˜๋ฆฌ๋จผํŠธ Props๋ฅผ ์ง€์›ํ•ฉ๋‹ˆ๋‹ค.

  • children: ๋ฌธ์ž์—ด ํƒ€์ž…. ํ•„์ˆ˜ ํ•ญ๋ชฉ. ์Šคํƒ€์ผ์‹œํŠธ์˜ ๋‚ด์šฉ.
  • precedence: ๋ฌธ์ž์—ด ํƒ€์ž…. ๋ฌธ์„œ์˜ <head> ๋‚ด ๋‹ค๋ฅธ ์š”์†Œ๋“ค์— ๋น„ํ•ด <style> DOM ๋…ธ๋“œ์˜ ์ˆœ์œ„๋ฅผ ์ง€์ •ํ•˜์—ฌ, ์–ด๋–ค ์Šคํƒ€์ผ์‹œํŠธ๊ฐ€ ๋‹ค๋ฅธ ์Šคํƒ€์ผ์‹œํŠธ๋ฅผ ๋ฎ์–ด์“ธ ์ˆ˜ ์žˆ๋Š”์ง€๋ฅผ ๊ฒฐ์ •ํ•ฉ๋‹ˆ๋‹ค. React๋Š” ๋จผ์ € ๋ฐœ๊ฒฌํ•œ ์šฐ์„ ์ˆœ์œ„๋ฅผ โ€œ๋‚ฎ๊ฒŒโ€, ๋‚˜์ค‘์— ๋ฐœ๊ฒฌํ•œ ์šฐ์„ ์ˆœ์œ„๋ฅผ โ€œ๋†’๊ฒŒโ€ ์ถ”๋ก ํ•ฉ๋‹ˆ๋‹ค. ๋งŽ์€ ์Šคํƒ€์ผ ์‹œ์Šคํ…œ์€ ์Šคํƒ€์ผ ๊ทœ์น™์ด ์›์ž์ ์ด๊ธฐ ๋•Œ๋ฌธ์— ๋‹จ์ผ ์šฐ์„ ์ˆœ์œ„ ๊ฐ’์„ ์‚ฌ์šฉํ•ด๋„ ์ž˜ ์ž‘๋™ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ๋™์ผํ•œ ์šฐ์„ ์ˆœ์œ„๋ฅผ ๊ฐ€์ง€๋Š” ์Šคํƒ€์ผ์‹œํŠธ๋Š” <link> ํƒœ๊ทธ์ธ์ง€ ์ธ๋ผ์ธ <style> ํƒœ๊ทธ์ธ์ง€ preinit ํ•จ์ˆ˜๋กœ ๋กœ๋“œ๋œ ๊ฒƒ์ธ์ง€์™€ ๋ฌด๊ด€ํ•˜๊ฒŒ ํ•จ๊ป˜ ์ ์šฉ๋ฉ๋‹ˆ๋‹ค.
  • href: ๋ฌธ์ž์—ด ํƒ€์ž…. ๋™์ผํ•œ href๋ฅผ ๊ฐ€์ง„ ์Šคํƒ€์ผ์˜ ์ค‘๋ณต ์ ์šฉ์„ ์ œ๊ฑฐํ•ฉ๋‹ˆ๋‹ค.
  • media: ๋ฌธ์ž์—ด ํƒ€์ž…. ์Šคํƒ€์ผ์‹œํŠธ๋ฅผ ํŠน์ • ๋ฏธ๋””์–ด ์ฟผ๋ฆฌ๋กœ ์ œํ•œํ•ฉ๋‹ˆ๋‹ค.
  • nonce: ๋ฌธ์ž์—ด ํƒ€์ž…. ์—„๊ฒฉํ•œ ์ฝ˜ํ…์ธ  ๋ณด์•ˆ ์ •์ฑ…์„ ์‚ฌ์šฉํ•  ๋•Œ ๋ฆฌ์†Œ์Šค๋ฅผ ํ—ˆ์šฉํ•˜๊ธฐ ์œ„ํ•œ ์•”ํ˜ธํ™” ๋‚œ์ˆ˜์ž…๋‹ˆ๋‹ค.
  • title: ๋ฌธ์ž์—ด ํƒ€์ž…. ๋Œ€์ฒด ์Šคํƒ€์ผ์‹œํŠธ์˜ ์ด๋ฆ„์„ ์ง€์ •ํ•ฉ๋‹ˆ๋‹ค.

๋‹ค์Œ React ์†์„ฑ๋“ค์€ ๊ถŒ์žฅํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค.

  • blocking: ๋ฌธ์ž์—ด ํƒ€์ž…. "render"๋กœ ์„ค์ •ํ•˜๋ฉด ์Šคํƒ€์ผ์‹œํŠธ๊ฐ€ ๋กœ๋“œ๋  ๋•Œ๊นŒ์ง€ ๋ธŒ๋ผ์šฐ์ €๊ฐ€ ํŽ˜์ด์ง€๋ฅผ ๋ Œ๋”๋งํ•˜์ง€ ์•Š๋„๋ก ์ง€์‹œํ•ฉ๋‹ˆ๋‹ค. React๋Š” Suspense๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋” ์„ธ๋ฐ€ํ•˜๊ฒŒ ์ œ์–ดํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

ํŠน๋ณ„ํ•œ ๋ Œ๋”๋ง ๋™์ž‘

React๋Š” <style> ์ปดํฌ๋„ŒํŠธ๋ฅผ ๋ฌธ์„œ์˜ <head>๋กœ ์ด๋™์‹œํ‚ค๊ณ , ๋™์ผํ•œ ์Šคํƒ€์ผ์‹œํŠธ์˜ ์ค‘๋ณต์„ ์ œ๊ฑฐํ•˜๋ฉฐ, ์Šคํƒ€์ผ์‹œํŠธ๊ฐ€ ๋กœ๋”ฉ๋˜๋Š” ๋™์•ˆ ์„œ์ŠคํŽœ์Šคํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์ด ๋™์ž‘์„ ์‚ฌ์šฉํ•˜๋ ค๋ฉด href์™€ precedence ์†์„ฑ์„ ์ œ๊ณตํ•˜์„ธ์š”. React๋Š” ๋™์ผํ•œ href๋ฅผ ๊ฐ€์ง„ ์Šคํƒ€์ผ์˜ ์ค‘๋ณต์„ ์ œ๊ฑฐํ•ฉ๋‹ˆ๋‹ค. precedence ์†์„ฑ์€ ๋ฌธ์„œ์˜ <head> ๋‚ด ๋‹ค๋ฅธ ์š”์†Œ์— ๋น„ํ•ด <style> DOM ๋…ธ๋“œ์˜ ์ˆœ์œ„๋ฅผ ์ง€์ •ํ•˜๋ฉฐ, ์–ด๋–ค ์Šคํƒ€์ผ์‹œํŠธ๊ฐ€ ๋‹ค๋ฅธ ์Šคํƒ€์ผ์‹œํŠธ๋ฅผ ๋ฎ์–ด์“ธ ์ˆ˜ ์žˆ๋Š”์ง€๋ฅผ ๊ฒฐ์ •ํ•ฉ๋‹ˆ๋‹ค.

This special treatment comes with three caveats:

  • React will ignore changes to props after the style has been rendered. (React will issue a warning in development if this happens.)

  • React will drop all extraneous props when using the precedence prop (beyond href and precedence).

  • React may leave the style in the DOM even after the component that rendered it has been unmounted.

  • ์Šคํƒ€์ผ์ด ๋ Œ๋”๋ง๋œ ํ›„์—๋Š” React๊ฐ€ Props ๋ณ€๊ฒฝ์„ ๋ฌด์‹œํ•ฉ๋‹ˆ๋‹ค. (๊ฐœ๋ฐœ ์ค‘์— ์ด ์ƒํ™ฉ์ด ๋ฐœ์ƒํ•˜๋ฉด React๋Š” ๊ฒฝ๊ณ ๋ฅผ ํ‘œ์‹œํ•ฉ๋‹ˆ๋‹ค.)

  • React๋Š” precedence Prop์„ ์‚ฌ์šฉํ•  ๋•Œ ๋ถˆํ•„์š”ํ•œ Props๋ฅผ ์ œ๊ฑฐํ•ฉ๋‹ˆ๋‹ค. (๋‹จ, href์™€ precedence๋Š” ์ œ์™ธ.)

  • ์Šคํƒ€์ผ์„ ๋ Œ๋”๋งํ•œ ์ปดํฌ๋„ŒํŠธ๊ฐ€ ๋งˆ์šดํŠธ ํ•ด์ œ๋œ ํ›„์—๋„ DOM์— ์Šคํƒ€์ผ์ด ์œ ์ง€๋  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.


์‚ฌ์šฉ๋ฒ•

์ธ๋ผ์ธ CSS ์Šคํƒ€์ผ์‹œํŠธ ๋ Œ๋”๋งํ•˜๊ธฐ

์ปดํฌ๋„ŒํŠธ๊ฐ€ ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ํ‘œ์‹œ๋˜๊ธฐ ์œ„ํ•ด ํŠน์ • CSS ์Šคํƒ€์ผ์— ์˜์กดํ•˜๋Š” ๊ฒฝ์šฐ, ์ปดํฌ๋„ŒํŠธ ๋‚ด์—์„œ ์ธ๋ผ์ธ ์Šคํƒ€์ผ์‹œํŠธ๋ฅผ ๋ Œ๋”๋งํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

React๋Š” ๋™์ผํ•œ href๋ฅผ ๊ฐ€์ง„ ์Šคํƒ€์ผ์‹œํŠธ์˜ ์ค‘๋ณต์„ ์ œ๊ฑฐํ•˜๋ฏ€๋กœ href ์†์„ฑ์€ ์Šคํƒ€์ผ์‹œํŠธ๋ฅผ ๊ณ ์œ ํ•˜๊ฒŒ ์‹๋ณ„ํ•ด์•ผ ํ•ฉ๋‹ˆ๋‹ค. precedence Prop์„ ์ œ๊ณตํ•˜๋ฉด React๋Š” ์ปดํฌ๋„ŒํŠธ ํŠธ๋ฆฌ์—์„œ ํ•ด๋‹น ๊ฐ’์ด ํ‘œ์‹œ๋˜๋Š” ์ˆœ์„œ์— ๋”ฐ๋ผ ์ธ๋ผ์ธ ์Šคํƒ€์ผ์‹œํŠธ์˜ ์ˆœ์„œ๋ฅผ ๋‹ค์‹œ ์ง€์ •ํ•ฉ๋‹ˆ๋‹ค.

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

import ShowRenderedHTML from './ShowRenderedHTML.js';
import { useId } from 'react';

function PieChart({data, colors}) {
  const id = useId();
  const stylesheet = colors.map((color, index) =>
    `#${id} .color-${index}: \{ color: "${color}"; \}`
  ).join();
  return (
    <>
      <style href={"PieChart-" + JSON.stringify(colors)} precedence="medium">
        {stylesheet}
      </style>
      <svg id={id}>
        โ€ฆ
      </svg>
    </>
  );
}

export default function App() {
  return (
    <ShowRenderedHTML>
      <PieChart data="..." colors={['red', 'green', 'blue']} />
    </ShowRenderedHTML>
  );
}