OpenShift์˜ ์ตœ์‹  ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜, 2๋ถ€: ์ฒด์ธ ๋นŒ๋“œ

์•ˆ๋…•ํ•˜์„ธ์š” ์—ฌ๋Ÿฌ๋ถ„! ์ด๋Š” Red Hat OpenShift์—์„œ ์ตœ์‹  ์›น ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์„ ๋ฐฐํฌํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ๋ณด์—ฌ์ฃผ๋Š” ์‹œ๋ฆฌ์ฆˆ์˜ ๋‘ ๋ฒˆ์งธ ๊ฒŒ์‹œ๋ฌผ์ž…๋‹ˆ๋‹ค.

OpenShift์˜ ์ตœ์‹  ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜, 2๋ถ€: ์ฒด์ธ ๋นŒ๋“œ

์ด์ „ ๊ฒŒ์‹œ๋ฌผ์—์„œ๋Š” OpenShift ํ”Œ๋žซํผ์—์„œ ์ตœ์‹  ์›น ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์„ ๊ตฌ์ถ•ํ•˜๊ณ  ๋ฐฐํฌํ•˜๋„๋ก ์„ค๊ณ„๋œ ์ƒˆ๋กœ์šด S2I(์†Œ์Šค-์ด๋ฏธ์ง€) ๋นŒ๋” ์ด๋ฏธ์ง€์˜ ๊ธฐ๋Šฅ์— ๋Œ€ํ•ด ์•ฝ๊ฐ„ ๋‹ค๋ฃจ์—ˆ์Šต๋‹ˆ๋‹ค. ๊ทธ๋Ÿฐ ๋‹ค์Œ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์„ ๋น ๋ฅด๊ฒŒ ๋ฐฐํฌํ•˜๋Š” ์ฃผ์ œ์— ๊ด€์‹ฌ์ด ์žˆ์—ˆ๊ณ  ์˜ค๋Š˜์€ S2I ์ด๋ฏธ์ง€๋ฅผ "์ˆœ์ˆ˜ํ•œ" ๋นŒ๋” ์ด๋ฏธ์ง€๋กœ ์‚ฌ์šฉํ•˜๊ณ  ์ด๋ฅผ ๊ด€๋ จ OpenShift ์–ด์…ˆ๋ธ”๋ฆฌ์™€ ๊ฒฐํ•ฉํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ์‚ดํŽด๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค.

ํด๋ฆฐ ๋นŒ๋” ์ด๋ฏธ์ง€

XNUMX๋ถ€์—์„œ ์–ธ๊ธ‰ํ–ˆ๋“ฏ์ด ๋Œ€๋ถ€๋ถ„์˜ ์ตœ์‹  ์›น ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์—๋Š” ์ผ๋ฐ˜์ ์œผ๋กœ ์ฝ”๋“œ ๋ณ€ํ™˜, ๋‹ค์ค‘ ํŒŒ์ผ ์—ฐ๊ฒฐ ๋ฐ ์ถ•์†Œ์™€ ๊ฐ™์€ ์ž‘์—…์„ ์ˆ˜ํ–‰ํ•˜๋Š” ์†Œ์œ„ ๋นŒ๋“œ ๋‹จ๊ณ„๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค. ์ด๋Ÿฌํ•œ ์ž‘์—…์˜ ๊ฒฐ๊ณผ๋กœ ์–ป์€ ํŒŒ์ผ(์ •์  HTML, JavaScript ๋ฐ CSS)์€ ์ถœ๋ ฅ ํด๋”์— ์ €์žฅ๋ฉ๋‹ˆ๋‹ค. ์ด ํด๋”์˜ ์œ„์น˜๋Š” ์ผ๋ฐ˜์ ์œผ๋กœ ์‚ฌ์šฉ๋˜๋Š” ๋นŒ๋“œ ๋„๊ตฌ์— ๋”ฐ๋ผ ๋‹ค๋ฅด๋ฉฐ React์˜ ๊ฒฝ์šฐ ./build ํด๋”๊ฐ€ ๋ฉ๋‹ˆ๋‹ค(์ด์— ๋Œ€ํ•ด์„œ๋Š” ์•„๋ž˜์—์„œ ๋” ์ž์„ธํžˆ ์„ค๋ช…ํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค).

์†Œ์Šค-์ด๋ฏธ์ง€(S2I)

์ด ๊ฒŒ์‹œ๋ฌผ์—์„œ๋Š” "S2I๋ž€ ๋ฌด์—‡์ด๋ฉฐ ์–ด๋–ป๊ฒŒ ์‚ฌ์šฉํ•˜๋Š”๊ฐ€"๋ผ๋Š” ์ฃผ์ œ๋Š” ๋‹ค๋ฃจ์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ์—ฌ๊ธฐ์—) ๊ทธ๋Ÿฌ๋‚˜ Web App Builder ์ด๋ฏธ์ง€์˜ ๊ธฐ๋Šฅ์„ ์ดํ•ดํ•˜๋ ค๋ฉด ์ด ํ”„๋กœ์„ธ์Šค์˜ ๋‘ ๋‹จ๊ณ„๋ฅผ ๋ช…ํ™•ํ•˜๊ฒŒ ์ดํ•ดํ•˜๋Š” ๊ฒƒ์ด ์ค‘์š”ํ•ฉ๋‹ˆ๋‹ค.

์กฐ๋ฆฝ ๋‹จ๊ณ„

์กฐ๋ฆฝ ๋‹จ๊ณ„๋Š” ๋ณธ์งˆ์ ์œผ๋กœ docker build๋ฅผ ์‹คํ–‰ํ•˜๊ณ  ์ƒˆ๋กœ์šด Docker ์ด๋ฏธ์ง€๋กœ ๋๋‚  ๋•Œ ๋ฐœ์ƒํ•˜๋Š” ๊ณผ์ •๊ณผ ๋งค์šฐ ์œ ์‚ฌํ•ฉ๋‹ˆ๋‹ค. ๋”ฐ๋ผ์„œ ์ด ๋‹จ๊ณ„๋Š” OpenShift ํ”Œ๋žซํผ์—์„œ ๋นŒ๋“œ๋ฅผ ์‹œ์ž‘ํ•  ๋•Œ ๋ฐœ์ƒํ•ฉ๋‹ˆ๋‹ค.

Web App Builder ์ด๋ฏธ์ง€์˜ ๊ฒฝ์šฐ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์˜ ์ข…์†์„ฑ์„ ์„ค์น˜ํ•˜๊ณ  ๋นŒ๋“œ๋ฅผ ์‹คํ–‰ํ•˜๋Š” ์—ญํ• ์„ ๋‹ด๋‹นํ•ฉ๋‹ˆ๋‹ค. ์Šคํฌ๋ฆฝํŠธ ์กฐ๋ฆฝ. ๊ธฐ๋ณธ์ ์œผ๋กœ ๋นŒ๋” ์ด๋ฏธ์ง€๋Š” npm run ๋นŒ๋“œ ๊ตฌ์„ฑ์„ ์‚ฌ์šฉํ•˜์ง€๋งŒ ์ด๋Š” NPM_BUILD ํ™˜๊ฒฝ ๋ณ€์ˆ˜๋ฅผ ํ†ตํ•ด ์žฌ์ •์˜๋  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์•ž์„œ ๋งํ–ˆ๋“ฏ์ด ์ด๋ฏธ ๋นŒ๋“œ๋œ ์™„์„ฑ๋œ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์˜ ์œ„์น˜๋Š” ์‚ฌ์šฉํ•˜๋Š” ๋„๊ตฌ์— ๋”ฐ๋ผ ๋‹ค๋ฆ…๋‹ˆ๋‹ค. ์˜ˆ๋ฅผ ๋“ค์–ด React์˜ ๊ฒฝ์šฐ ./build ํด๋”๊ฐ€ ๋˜๊ณ  Angular ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์˜ ๊ฒฝ์šฐ project_name/dist ํด๋”๊ฐ€ ๋ฉ๋‹ˆ๋‹ค. ๊ทธ๋ฆฌ๊ณ  ์ด์ „ ๊ฒŒ์‹œ๋ฌผ์—์„œ ์ด๋ฏธ ๋ณด์—ฌ๋“œ๋ฆฐ ๊ฒƒ์ฒ˜๋Ÿผ ๊ธฐ๋ณธ์ ์œผ๋กœ ๋นŒ๋“œ๋˜๋„๋ก ์„ค์ •๋œ ์ถœ๋ ฅ ๋””๋ ‰ํ„ฐ๋ฆฌ์˜ ์œ„์น˜๋Š” OUTPUT_DIR ํ™˜๊ฒฝ ๋ณ€์ˆ˜๋ฅผ ํ†ตํ•ด ์žฌ์ •์˜๋  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์ถœ๋ ฅ ํด๋”์˜ ์œ„์น˜๋Š” ํ”„๋ ˆ์ž„์›Œํฌ๋งˆ๋‹ค ๋‹ค๋ฅด๊ธฐ ๋•Œ๋ฌธ์— ์ƒ์„ฑ๋œ ์ถœ๋ ฅ์„ ์ด๋ฏธ์ง€์˜ ํ‘œ์ค€ ํด๋”, ์ฆ‰ /opt/apt-root/output์— ๋ณต์‚ฌํ•˜๊ธฐ๋งŒ ํ•˜๋ฉด ๋ฉ๋‹ˆ๋‹ค. ์ด๋Š” ์ด ๊ธฐ์‚ฌ์˜ ๋‚˜๋จธ์ง€ ๋ถ€๋ถ„์„ ์ดํ•ดํ•˜๋Š” ๋ฐ ์ค‘์š”ํ•˜์ง€๋งŒ ์ง€๊ธˆ์€ ๋‹ค์Œ ๋‹จ๊ณ„์ธ ์‹คํ–‰ ๋‹จ๊ณ„๋ฅผ ๋น ๋ฅด๊ฒŒ ์‚ดํŽด๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค.

์‹คํ–‰ ๋‹จ๊ณ„

์ด ๋‹จ๊ณ„๋Š” ์–ด์…ˆ๋ธ”๋ฆฌ ๋‹จ๊ณ„์—์„œ ์ƒ์„ฑ๋œ ์ƒˆ ์ด๋ฏธ์ง€์— ๋Œ€ํ•ด docker run์ด ํ˜ธ์ถœ๋  ๋•Œ ๋ฐœ์ƒํ•ฉ๋‹ˆ๋‹ค. OpenShift ํ”Œ๋žซํผ์— ๋ฐฐํฌํ•  ๋•Œ๋„ ๋งˆ์ฐฌ๊ฐ€์ง€์ž…๋‹ˆ๋‹ค. ๊ธฐ๋ณธ ์Šคํฌ๋ฆฝํŠธ ์‹คํ–‰ ะธัะฟะพะปัŒะทัƒะตั‚ ์„œ๋ธŒ ๋ชจ๋“ˆ ์œ„์˜ ํ‘œ์ค€ ์ถœ๋ ฅ ๋””๋ ‰ํ„ฐ๋ฆฌ์— ์žˆ๋Š” ์ •์  ์ฝ˜ํ…์ธ ๋ฅผ ์ œ๊ณตํ•ฉ๋‹ˆ๋‹ค.

์ด ๋ฐฉ๋ฒ•์€ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์„ ๋น ๋ฅด๊ฒŒ ๋ฐฐํฌํ•˜๋Š” ๋ฐ ์ ํ•ฉํ•˜์ง€๋งŒ ์ผ๋ฐ˜์ ์œผ๋กœ ์ด ๋ฐฉ์‹์œผ๋กœ ์ •์  ์ฝ˜ํ…์ธ ๋ฅผ ์ œ๊ณตํ•˜๋Š” ๊ฒƒ์€ ๊ถŒ์žฅ๋˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ์‹ค์ œ๋กœ๋Š” ์ •์  ์ฝ˜ํ…์ธ ๋งŒ ์ œ๊ณตํ•˜๋ฏ€๋กœ ์ด๋ฏธ์ง€ ๋‚ด๋ถ€์— Node.js๋ฅผ ์„ค์น˜ํ•  ํ•„์š”๊ฐ€ ์—†์Šต๋‹ˆ๋‹ค. ์›น ์„œ๋ฒ„๋งŒ ์žˆ์œผ๋ฉด ์ถฉ๋ถ„ํ•ฉ๋‹ˆ๋‹ค.

์ฆ‰, ์กฐ๋ฆฝํ•  ๋•Œ ํ•œ ๊ฐ€์ง€๊ฐ€ ํ•„์š”ํ•˜๊ณ , ์‹คํ–‰ํ•  ๋•Œ ๋‹ค๋ฅธ ๊ฒƒ์ด ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค. ์ด๋Ÿฐ ์ƒํ™ฉ์—์„œ๋Š” ์ฒด์ธ์œผ๋กœ ์—ฐ๊ฒฐ๋œ ๋นŒ๋“œ๊ฐ€ ์œ ์šฉํ•ฉ๋‹ˆ๋‹ค.

์—ฐ๊ฒฐ๋œ ๋นŒ๋“œ

์ด๊ฒƒ์ด ๊ทธ๋“ค์ด ์“ด ๋‚ด์šฉ์ž…๋‹ˆ๋‹ค. ์ฒด์ธ ๋นŒ๋“œ OpenShift ๋ฌธ์„œ์—์„œ:

"๋‘ ๊ฐœ์˜ ์–ด์…ˆ๋ธ”๋ฆฌ๋ฅผ ํ•จ๊ป˜ ์—ฐ๊ฒฐํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ํ•˜๋‚˜๋Š” ์ปดํŒŒ์ผ๋œ ์—”ํ„ฐํ‹ฐ๋ฅผ ์ƒ์„ฑํ•˜๊ณ  ๋‹ค๋ฅธ ํ•˜๋‚˜๋Š” ํ•ด๋‹น ์—”ํ„ฐํ‹ฐ๋ฅผ ์‹คํ–‰ํ•˜๋Š” ๋ฐ ์‚ฌ์šฉ๋˜๋Š” ๋ณ„๋„์˜ ์ด๋ฏธ์ง€์—์„œ ํ•ด๋‹น ์—”ํ„ฐํ‹ฐ๋ฅผ ํ˜ธ์ŠคํŒ…ํ•ฉ๋‹ˆ๋‹ค."

์ฆ‰, Web App Builder ์ด๋ฏธ์ง€๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋นŒ๋“œ๋ฅผ ์‹คํ–‰ํ•œ ๋‹ค์Œ ๋™์ผํ•œ NGINX์ธ ์›น ์„œ๋ฒ„ ์ด๋ฏธ์ง€๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์ฝ˜ํ…์ธ ๋ฅผ ์ œ๊ณตํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

๋”ฐ๋ผ์„œ Web App Builder ์ด๋ฏธ์ง€๋ฅผ "์ˆœ์ˆ˜ํ•œ" ๋นŒ๋”๋กœ ์‚ฌ์šฉํ•˜๋Š” ๋™์‹œ์— ์ž‘์€ ๋Ÿฐํƒ€์ž„ ์ด๋ฏธ์ง€๋ฅผ ๊ฐ€์งˆ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์ด์ œ ๊ตฌ์ฒด์ ์ธ ์˜ˆ๋ฅผ ๋“ค์–ด ์ด๋ฅผ ์‚ดํŽด๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค.

ํ›ˆ๋ จ์„ ์œ„ํ•ด ์šฐ๋ฆฌ๋Š” ๊ฐ„๋‹จํ•œ ๋ฆฌ์•กํŠธ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜, create-react-app ๋ช…๋ น์ค„ ๋„๊ตฌ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์ƒ์„ฑ๋˜์—ˆ์Šต๋‹ˆ๋‹ค.

๊ทธ๊ฒƒ์€ ์šฐ๋ฆฌ๊ฐ€ ๋ชจ๋“  ๊ฒƒ์„ ํ•˜๋‚˜๋กœ ๋ชจ์œผ๋Š” ๋ฐ ๋„์›€์ด ๋  ๊ฒƒ์ž…๋‹ˆ๋‹ค OpenShift ํ…œํ”Œ๋ฆฟ ํŒŒ์ผ.

์ด ํŒŒ์ผ์„ ๋” ์ž์„ธํžˆ ์‚ดํŽด๋ณด๊ณ  ๋งค๊ฐœ๋ณ€์ˆ˜ ์„น์…˜๋ถ€ํ„ฐ ์‹œ์ž‘ํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค.

parameters:
  - name: SOURCE_REPOSITORY_URL
    description: The source URL for the application
    displayName: Source URL
    required: true
  - name: SOURCE_REPOSITORY_REF
    description: The branch name for the application
    displayName: Source Branch
    value: master
    required: true
  - name: SOURCE_REPOSITORY_DIR
    description: The location within the source repo of the application
    displayName: Source Directory
    value: .
    required: true
  - name: OUTPUT_DIR
    description: The location of the compiled static files from your web apps builder
    displayName: Output Directory
    value: build
    required: false

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

์ด์ œ ImageStreams ์„น์…˜์„ ์‚ดํŽด๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค.

- apiVersion: v1
  kind: ImageStream
  metadata:
    name: react-web-app-builder  // 1 
  spec: {}
- apiVersion: v1
  kind: ImageStream
  metadata:
    name: react-web-app-runtime  // 2 
  spec: {}
- apiVersion: v1
  kind: ImageStream
  metadata:
    name: web-app-builder-runtime // 3
  spec:
    tags:
    - name: latest
      from:
        kind: DockerImage
        name: nodeshift/ubi8-s2i-web-app:10.x
- apiVersion: v1
  kind: ImageStream
  metadata:
    name: nginx-image-runtime // 4
  spec:
    tags:
    - name: latest
      from:
        kind: DockerImage
        name: 'centos/nginx-112-centos7:latest'

์„ธ ๋ฒˆ์งธ์™€ ๋„ค ๋ฒˆ์งธ ์ด๋ฏธ์ง€๋ฅผ ์‚ดํŽด๋ณด์„ธ์š”. ๋‘˜ ๋‹ค Docker ์ด๋ฏธ์ง€๋กœ ์ •์˜๋˜์–ด ์žˆ์œผ๋ฉฐ ํ•ด๋‹น ์ด๋ฏธ์ง€์˜ ์ถœ์ฒ˜๋ฅผ ๋ช…ํ™•ํ•˜๊ฒŒ ํ™•์ธํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์„ธ ๋ฒˆ์งธ ์ด๋ฏธ์ง€๋Š” web-app-builder์ด๋ฉฐ 8.x ํƒœ๊ทธ๊ฐ€ ์ง€์ •๋œ nodeshift/ubi2-s10i-web-app์—์„œ ๊ฐ€์ ธ์˜จ ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๋„์ปค ํ—ˆ๋ธŒ.

๋„ค ๋ฒˆ์งธ๋Š” ์ตœ์‹  ํƒœ๊ทธ๊ฐ€ ์žˆ๋Š” NGINX ์ด๋ฏธ์ง€(๋ฒ„์ „ 1.12)์ž…๋‹ˆ๋‹ค. ๋„์ปค ํ—ˆ๋ธŒ.

์ด์ œ ์ฒ˜์Œ ๋‘ ์ด๋ฏธ์ง€๋ฅผ ์‚ดํŽด๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค. ๋‘˜ ๋‹ค ์‹œ์ž‘ ์‹œ ๋น„์–ด ์žˆ์œผ๋ฉฐ ๋นŒ๋“œ ๋‹จ๊ณ„์—์„œ๋งŒ ์ƒ์„ฑ๋ฉ๋‹ˆ๋‹ค. ์ฒซ ๋ฒˆ์งธ ์ด๋ฏธ์ง€์ธ React-web-app-builder๋Š” web-app-builder-runtime ์ด๋ฏธ์ง€์™€ ์†Œ์Šค ์ฝ”๋“œ๋ฅผ ๊ฒฐํ•ฉํ•˜๋Š” ์–ด์…ˆ๋ธ”๋ฆฌ ๋‹จ๊ณ„์˜ ๊ฒฐ๊ณผ์ž…๋‹ˆ๋‹ค. ์ด๊ฒƒ์ด ๋ฐ”๋กœ ์ด ์ด๋ฏธ์ง€ ์ด๋ฆ„์— "-builder"๋ฅผ ์ถ”๊ฐ€ํ•œ ์ด์œ ์ž…๋‹ˆ๋‹ค.

๋‘ ๋ฒˆ์งธ ์ด๋ฏธ์ง€(react-web-app-runtime)๋Š” nginx-image-runtime๊ณผ React-web-app-builder ์ด๋ฏธ์ง€์˜ ์ผ๋ถ€ ํŒŒ์ผ์„ ๊ฒฐํ•ฉํ•œ ๊ฒฐ๊ณผ์ž…๋‹ˆ๋‹ค. ์ด ์ด๋ฏธ์ง€๋Š” ๋ฐฐํฌ ์ค‘์—๋„ ์‚ฌ์šฉ๋˜๋ฉฐ ์›น ์„œ๋ฒ„์™€ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์˜ ์ •์  HTML, JavaScript, CSS๋งŒ ํฌํ•จํ•ฉ๋‹ˆ๋‹ค.

ํ˜ผ๋ž€์Šค๋Ÿฌ์šด? ์ด์ œ ๋นŒ๋“œ ๊ตฌ์„ฑ์„ ์‚ดํŽด๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค. ์ข€ ๋” ๋ช…ํ™•ํ•ด์ง‘๋‹ˆ๋‹ค.

์šฐ๋ฆฌ ํ…œํ”Œ๋ฆฟ์—๋Š” ๋‘ ๊ฐ€์ง€ ๋นŒ๋“œ ๊ตฌ์„ฑ์ด ์žˆ์Šต๋‹ˆ๋‹ค. ์ฒซ ๋ฒˆ์งธ๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™์Šต๋‹ˆ๋‹ค. ๋งค์šฐ ํ‘œ์ค€์ ์ž…๋‹ˆ๋‹ค.

  apiVersion: v1
  kind: BuildConfig
  metadata:
    name: react-web-app-builder
  spec:
    output:
      to:
        kind: ImageStreamTag
        name: react-web-app-builder:latest // 1
    source:   // 2 
      git:
        uri: ${SOURCE_REPOSITORY_URL}
        ref: ${SOURCE_REPOSITORY_REF}
      contextDir: ${SOURCE_REPOSITORY_DIR}
      type: Git
    strategy:
      sourceStrategy:
        env:
          - name: OUTPUT_DIR // 3 
            value: ${OUTPUT_DIR}
        from:
          kind: ImageStreamTag
          name: web-app-builder-runtime:latest // 4
        incremental: true // 5
      type: Source
    triggers: // 6
    - github:
        secret: ${GITHUB_WEBHOOK_SECRET}
      type: GitHub
    - type: ConfigChange
    - imageChange: {}
      type: ImageChange

๋ณด์‹œ๋‹ค์‹œํ”ผ, ๋ ˆ์ด๋ธ” 1์ด ์žˆ๋Š” ์ค„์€ ์ด ๋นŒ๋“œ์˜ ๊ฒฐ๊ณผ๊ฐ€ ์ด์ „์— ImageStreams ์„น์…˜์—์„œ ๋ณธ ๊ฒƒ๊ณผ ๋™์ผํ•œ React-web-app-builder ์ด๋ฏธ์ง€์— ๋ฐฐ์น˜๋  ๊ฒƒ์ž„์„ ๋‚˜ํƒ€๋ƒ…๋‹ˆ๋‹ค.

2๋กœ ํ‘œ์‹œ๋œ ์ค„์€ ์ฝ”๋“œ๋ฅผ ์–ด๋””์„œ ์–ป์„ ์ˆ˜ ์žˆ๋Š”์ง€ ์•Œ๋ ค์ค๋‹ˆ๋‹ค. ์šฐ๋ฆฌ์˜ ๊ฒฝ์šฐ ์ด๋Š” git ์ €์žฅ์†Œ์ด๋ฉฐ ์œ„์น˜, ์ฐธ์กฐ ๋ฐ ์ปจํ…์ŠคํŠธ ํด๋”๋Š” ์œ„์—์„œ ์ด๋ฏธ ๋ณธ ๋งค๊ฐœ๋ณ€์ˆ˜์— ์˜ํ•ด ๊ฒฐ์ •๋ฉ๋‹ˆ๋‹ค.

3์œผ๋กœ ํ‘œ์‹œ๋œ ์ค„์€ ๋งค๊ฐœ๋ณ€์ˆ˜ ์„น์…˜์—์„œ ์ด๋ฏธ ๋ณธ ๊ฒƒ์ž…๋‹ˆ๋‹ค. ์ด ์˜ˆ์ œ์—์„œ๋Š” build๋ผ๋Š” OUTPUT_DIR ํ™˜๊ฒฝ ๋ณ€์ˆ˜๋ฅผ ์ถ”๊ฐ€ํ•ฉ๋‹ˆ๋‹ค.
4๋ผ๊ณ  ํ‘œ์‹œ๋œ ์ค„์€ ImageStream ์„น์…˜์—์„œ ์ด๋ฏธ ๋ณธ web-app-builder-runtime ์ด๋ฏธ์ง€๋ฅผ ์‚ฌ์šฉํ•˜๋ผ๋Š” ์˜๋ฏธ์ž…๋‹ˆ๋‹ค.

5๋ฒˆ ์ค„์€ S2I ์ด๋ฏธ์ง€๊ฐ€ ์ง€์›ํ•˜๊ณ  Web App Builder ์ด๋ฏธ์ง€๊ฐ€ ์ง€์›ํ•˜๋Š” ๊ฒฝ์šฐ ์ฆ๋ถ„ ๋นŒ๋“œ๋ฅผ ์‚ฌ์šฉํ•˜๊ฒ ๋‹ค๋Š” ์˜๋ฏธ์ž…๋‹ˆ๋‹ค. ์ฒ˜์Œ ์‹คํ–‰ ์‹œ ์กฐ๋ฆฝ ๋‹จ๊ณ„๋ฅผ ์™„๋ฃŒํ•œ ํ›„ ์ด๋ฏธ์ง€๋Š” node_modules ํด๋”๋ฅผ ์•„์นด์ด๋ธŒ ํŒŒ์ผ์— ์ €์žฅํ•ฉ๋‹ˆ๋‹ค. ๊ทธ๋Ÿฐ ๋‹ค์Œ ํ›„์† ์‹คํ–‰ ์‹œ ์ด๋ฏธ์ง€๋Š” ์ด ํด๋”์˜ ์••์ถ•์„ ํ’€์–ด ๋นŒ๋“œ ์‹œ๊ฐ„์„ ์ค„์ž…๋‹ˆ๋‹ค.

๋งˆ์ง€๋ง‰์œผ๋กœ 6์œผ๋กœ ํ‘œ์‹œ๋œ ์ค„์€ ๋ฌด์–ธ๊ฐ€ ๋ณ€๊ฒฝ๋  ๋•Œ ์ˆ˜๋™ ๊ฐœ์ž… ์—†์ด ๋นŒ๋“œ๊ฐ€ ์ž๋™์œผ๋กœ ์‹คํ–‰๋˜๋„๋ก ํ•˜๋Š” ๋ช‡ ๊ฐ€์ง€ ํŠธ๋ฆฌ๊ฑฐ์ผ ๋ฟ์ž…๋‹ˆ๋‹ค.

์ „๋ฐ˜์ ์œผ๋กœ ์ด๊ฒƒ์€ ๊ฝค ํ‘œ์ค€์ ์ธ ๋นŒ๋“œ ๊ตฌ์„ฑ์ž…๋‹ˆ๋‹ค.

์ด์ œ ๋‘ ๋ฒˆ์งธ ๋นŒ๋“œ ๊ตฌ์„ฑ์„ ์‚ดํŽด๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค. ์ฒซ ๋ฒˆ์งธ ๊ฒƒ๊ณผ ๋งค์šฐ ์œ ์‚ฌํ•˜์ง€๋งŒ ํ•œ ๊ฐ€์ง€ ์ค‘์š”ํ•œ ์ฐจ์ด์ ์ด ์žˆ์Šต๋‹ˆ๋‹ค.

apiVersion: v1
  kind: BuildConfig
  metadata:
    name: react-web-app-runtime
  spec:
    output:
      to:
        kind: ImageStreamTag
        name: react-web-app-runtime:latest // 1
    source: // 2
      type: Image
      images:                              
        - from:
            kind: ImageStreamTag
            name: react-web-app-builder:latest // 3
          paths:
            - sourcePath: /opt/app-root/output/.  // 4
              destinationDir: .  // 5
             
    strategy: // 6
      sourceStrategy:
        from:
          kind: ImageStreamTag
          name: nginx-image-runtime:latest
        incremental: true
      type: Source
    triggers:
    - github:
        secret: ${GITHUB_WEBHOOK_SECRET}
      type: GitHub
    - type: ConfigChange
    - type: ImageChange
      imageChange: {}
    - type: ImageChange
      imageChange:
        from:
          kind: ImageStreamTag
          name: react-web-app-builder:latest // 7

๋”ฐ๋ผ์„œ ๋‘ ๋ฒˆ์งธ ๋นŒ๋“œ ๊ตฌ์„ฑ์€ React-web-app-runtime์ด๋ฉฐ ๋งค์šฐ ํ‘œ์ค€์ ์œผ๋กœ ์‹œ์ž‘๋ฉ๋‹ˆ๋‹ค.

1๋กœ ํ‘œ์‹œ๋œ ์ค„์€ ์ƒˆ๋กœ์šด ๊ฒƒ์ด ์•„๋‹™๋‹ˆ๋‹ค. ๋‹จ์ˆœํžˆ ๋นŒ๋“œ ๊ฒฐ๊ณผ๊ฐ€ ๋ฐ˜์‘ ์›น ์•ฑ ๋Ÿฐํƒ€์ž„ ์ด๋ฏธ์ง€์— ์ €์žฅ๋œ๋‹ค๋Š” ์˜๋ฏธ์ž…๋‹ˆ๋‹ค.

์ด์ „ ๊ตฌ์„ฑ์—์„œ์™€ ๊ฐ™์ด 2๋กœ ํ‘œ์‹œ๋œ ์ค„์€ ์†Œ์Šค ์ฝ”๋“œ๋ฅผ ๊ฐ€์ ธ์˜ฌ ์œ„์น˜๋ฅผ ๋‚˜ํƒ€๋ƒ…๋‹ˆ๋‹ค. ๊ทธ๋Ÿฌ๋‚˜ ์—ฌ๊ธฐ์„œ๋Š” ์ด๋ฏธ์ง€์—์„œ ๊ฐ€์ ธ์˜จ ๊ฒƒ์ด๋ผ๊ณ  ๋งํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ๋˜ํ•œ, ์šฐ๋ฆฌ๊ฐ€ ๋ฐฉ๊ธˆ ์ƒ์„ฑํ•œ ์ด๋ฏธ์ง€์—์„œ - React-web-app-builder(3์œผ๋กœ ํ‘œ์‹œ๋œ ์ค„์— ํ‘œ์‹œ๋จ)์—์„œ. ์‚ฌ์šฉํ•˜๋ ค๋Š” ํŒŒ์ผ์€ ์ด๋ฏธ์ง€ ๋‚ด๋ถ€์— ์žˆ์œผ๋ฉฐ ๊ทธ ์œ„์น˜๋Š” 4๋ฒˆ ์ค„์— ์„ค์ •๋˜์–ด ์žˆ์Šต๋‹ˆ๋‹ค. ์ด ๊ฒฝ์šฐ์—๋Š” /opt/app-root/output/์ž…๋‹ˆ๋‹ค. ๊ธฐ์–ตํ•˜์‹ ๋‹ค๋ฉด ์—ฌ๊ธฐ์— ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜ ๊ตฌ์ถ• ๊ฒฐ๊ณผ๋ฅผ ๊ธฐ๋ฐ˜์œผ๋กœ ์ƒ์„ฑ๋œ ํŒŒ์ผ์ด ์ €์žฅ๋˜๋Š” ๊ณณ์ž…๋‹ˆ๋‹ค.

๋ ˆ์ด๋ธ” 5๊ฐ€ ์žˆ๋Š” ์šฉ์–ด์— ์ง€์ •๋œ ๋Œ€์ƒ ํด๋”๋Š” ๋‹จ์ˆœํžˆ ํ˜„์žฌ ๋””๋ ‰ํ„ฐ๋ฆฌ์ž…๋‹ˆ๋‹ค(์ด ๋””๋ ‰ํ„ฐ๋ฆฌ๋Š” ๋ชจ๋‘ ๋กœ์ปฌ ์ปดํ“จํ„ฐ๊ฐ€ ์•„๋‹Œ OpenShift๋ผ๋Š” ๋งˆ๋ฒ• ๊ฐ™์€ ๊ฒƒ ๋‚ด์—์„œ ์‹คํ–‰๋œ๋‹ค๋Š” ์ ์„ ๊ธฐ์–ตํ•˜์„ธ์š”).

์ „๋žต ์„น์…˜(6๋ฒˆ ์ค„)๋„ ์ฒซ ๋ฒˆ์งธ ๋นŒ๋“œ ๊ตฌ์„ฑ๊ณผ ์œ ์‚ฌํ•ฉ๋‹ˆ๋‹ค. ์ด๋ฒˆ์—๋Š” ImageStream ์„น์…˜์—์„œ ์ด๋ฏธ ๋ณธ nginx-image-runtime์„ ์‚ฌ์šฉํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค.

๋งˆ์ง€๋ง‰์œผ๋กœ, 7๋ฒˆ ์ค„์€ React-web-app-builder ์ด๋ฏธ์ง€๊ฐ€ ๋ณ€๊ฒฝ๋  ๋•Œ๋งˆ๋‹ค ์ด ๋นŒ๋“œ๋ฅผ ํ™œ์„ฑํ™”ํ•˜๋Š” ํŠธ๋ฆฌ๊ฑฐ ์„น์…˜์ž…๋‹ˆ๋‹ค.

๊ทธ๋ ‡์ง€ ์•Š์œผ๋ฉด ์ด ํ…œํ”Œ๋ฆฟ์—๋Š” ๊ฝค ํ‘œ์ค€์ ์ธ ๋ฐฐํฌ ๊ตฌ์„ฑ๊ณผ ์„œ๋น„์Šค ๋ฐ ๊ฒฝ๋กœ์™€ ๊ด€๋ จ๋œ ์‚ฌํ•ญ์ด ํฌํ•จ๋˜์–ด ์žˆ์ง€๋งŒ ๋„ˆ๋ฌด ์ž์„ธํžˆ ์„ค๋ช…ํ•˜์ง€๋Š” ์•Š๊ฒ ์Šต๋‹ˆ๋‹ค. ๋ฐฐํฌ๋  ์ด๋ฏธ์ง€๋Š” React-web-app-runtime ์ด๋ฏธ์ง€์ž…๋‹ˆ๋‹ค.

์• ํ”Œ๋ฆฌ์ผ€์ด์…˜ ๋ฐฐํฌ

์ด์ œ ํ…œํ”Œ๋ฆฟ์„ ์‚ดํŽด๋ณด์•˜์œผ๋ฏ€๋กœ ์ด๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์„ ๋ฐฐํฌํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ์‚ดํŽด๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค.

oc๋ผ๋Š” OpenShift ํด๋ผ์ด์–ธํŠธ ๋„๊ตฌ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ํ…œํ”Œ๋ฆฟ์„ ๋ฐฐํฌํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

$ find . | grep openshiftio | grep application | xargs -n 1 oc apply -f

$ oc new-app --template react-web-app -p SOURCE_REPOSITORY_URL=https://github.com/lholmquist/react-web-app

์œ„ ์Šคํฌ๋ฆฐ์ƒท์˜ ์ฒซ ๋ฒˆ์งธ ๋ช…๋ น์€ template./openshiftio/application.yaml์„ ์ฐพ๊ธฐ ์œ„ํ•œ ์˜๋„์ ์ธ ์—”์ง€๋‹ˆ์–ด๋ง ๋ฐฉ๋ฒ•์ž…๋‹ˆ๋‹ค.

๋‘ ๋ฒˆ์งธ ๋ช…๋ น์€ ์ด ํ…œํ”Œ๋ฆฟ์„ ๊ธฐ๋ฐ˜์œผ๋กœ ์ƒˆ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์„ ์ƒ์„ฑํ•ฉ๋‹ˆ๋‹ค.

์ด๋Ÿฌํ•œ ๋ช…๋ น์ด ์ž‘๋™ํ•˜๋ฉด ๋‘ ๊ฐœ์˜ ์–ด์…ˆ๋ธ”๋ฆฌ๊ฐ€ ์žˆ์Œ์„ ์•Œ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

OpenShift์˜ ์ตœ์‹  ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜, 2๋ถ€: ์ฒด์ธ ๋นŒ๋“œ

๊ฐœ์š” ํ™”๋ฉด์œผ๋กœ ๋Œ์•„๊ฐ€๋ฉด ์‹คํ–‰๋œ ํฌ๋“œ๊ฐ€ ํ‘œ์‹œ๋ฉ๋‹ˆ๋‹ค.

OpenShift์˜ ์ตœ์‹  ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜, 2๋ถ€: ์ฒด์ธ ๋นŒ๋“œ

๋งํฌ๋ฅผ ํด๋ฆญํ•˜๋ฉด ๊ธฐ๋ณธ React ์•ฑ ํŽ˜์ด์ง€์ธ ์•ฑ์œผ๋กœ ์ด๋™ํ•ฉ๋‹ˆ๋‹ค.

OpenShift์˜ ์ตœ์‹  ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜, 2๋ถ€: ์ฒด์ธ ๋นŒ๋“œ

๋ณด์ถฉ 1

Angular ์• ํ˜ธ๊ฐ€๋“ค์„ ์œ„ํ•ด ์šฐ๋ฆฌ๋Š” ๋˜ํ•œ ์˜ˆ์ œ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜.

OUTPUT_DIR ๋ณ€์ˆ˜๋ฅผ ์ œ์™ธํ•˜๊ณ  ์—ฌ๊ธฐ์˜ ํŒจํ„ด์€ ๋™์ผํ•ฉ๋‹ˆ๋‹ค.

๋ณด์ถฉ 2

์ด ๊ธฐ์‚ฌ์—์„œ๋Š” NGINX๋ฅผ ์›น ์„œ๋ฒ„๋กœ ์‚ฌ์šฉํ–ˆ์ง€๋งŒ ์ด๋ฅผ Apache๋กœ ๊ต์ฒดํ•˜๋Š” ๊ฒƒ์€ ๋งค์šฐ ์‰ฝ์Šต๋‹ˆ๋‹ค. ํŒŒ์ผ์—์„œ ํ…œํ”Œ๋ฆฟ์„ ๋ณ€๊ฒฝํ•˜๊ธฐ๋งŒ ํ•˜๋ฉด ๋ฉ๋‹ˆ๋‹ค. NGINX ์ด๋ฏธ์ง€ ์— ์•„ํŒŒ์น˜ ์ด๋ฏธ์ง€.

๊ฒฐ๋ก 

์ด ์‹œ๋ฆฌ์ฆˆ์˜ ์ฒซ ๋ฒˆ์งธ ๋ถ€๋ถ„์—์„œ๋Š” OpenShift ํ”Œ๋žซํผ์— ์ตœ์‹  ์›น ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์„ ์‹ ์†ํ•˜๊ฒŒ ๋ฐฐํฌํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ๋ณด์—ฌ์ฃผ์—ˆ์Šต๋‹ˆ๋‹ค. ์˜ค๋Š˜ ์šฐ๋ฆฌ๋Š” ์›น ์•ฑ ์ด๋ฏธ์ง€์˜ ๊ธฐ๋Šฅ๊ณผ ์ฒด์ธ ๋นŒ๋“œ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์›น ์•ฑ ์ด๋ฏธ์ง€๋ฅผ NGINX์™€ ๊ฐ™์€ ์ˆœ์ˆ˜ ์›น ์„œ๋ฒ„์™€ ๊ฒฐํ•ฉํ•˜์—ฌ ๋ณด๋‹ค ์ƒ์‚ฐ ์ค€๋น„๊ฐ€ ๋œ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜ ๋นŒ๋“œ๋ฅผ ๋งŒ๋“œ๋Š” ๋ฐฉ๋ฒ•์„ ์‚ดํŽด๋ณด์•˜์Šต๋‹ˆ๋‹ค. ์ด ์‹œ๋ฆฌ์ฆˆ์˜ ๋‹ค์Œ ๊ธฐ์‚ฌ์ด์ž ๋งˆ์ง€๋ง‰ ๊ธฐ์‚ฌ์—์„œ๋Š” OpenShift์—์„œ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์šฉ ๊ฐœ๋ฐœ ์„œ๋ฒ„๋ฅผ ์‹คํ–‰ํ•˜๊ณ  ๋กœ์ปฌ ๋ฐ ์›๊ฒฉ ํŒŒ์ผ์˜ ๋™๊ธฐํ™”๋ฅผ ๋ณด์žฅํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ๋ณด์—ฌ ๋“œ๋ฆฌ๊ฒ ์Šต๋‹ˆ๋‹ค.

์ด ๊ธฐ์‚ฌ ์‹œ๋ฆฌ์ฆˆ์˜ ๋‚ด์šฉ

  • ํŒŒํŠธ 1 : ๋‹จ ๋ช‡ ๋‹จ๊ณ„๋งŒ์œผ๋กœ ์ตœ์‹  ์›น ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์„ ๋ฐฐํฌํ•˜๋Š” ๋ฐฉ๋ฒ•;
  • 2๋ถ€: ํ”„๋กœ๋•์…˜ ๋ฐฐํฌ๋ฅผ ์œ„ํ•ด ์—ฐ๊ฒฐ๋œ OpenShift ์–ด์…ˆ๋ธ”๋ฆฌ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ NGINX์™€ ๊ฐ™์€ ๊ธฐ์กด HTTP ์„œ๋ฒ„ ์ด๋ฏธ์ง€์™€ ํ•จ๊ป˜ ์ƒˆ S2I ์ด๋ฏธ์ง€๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๋ฐฉ๋ฒ•
  • 3๋ถ€: OpenShift ํ”Œ๋žซํผ์—์„œ ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์šฉ ๊ฐœ๋ฐœ ์„œ๋ฒ„๋ฅผ ์‹คํ–‰ํ•˜๊ณ  ์ด๋ฅผ ๋กœ์ปฌ ํŒŒ์ผ ์‹œ์Šคํ…œ๊ณผ ๋™๊ธฐํ™”ํ•˜๋Š” ๋ฐฉ๋ฒ•.

์ถ”๊ฐ€ ๋ฆฌ์†Œ์Šค

์ถœ์ฒ˜ : habr.com

์ฝ”๋ฉ˜ํŠธ๋ฅผ ์ถ”๊ฐ€