opencv 라이브러리를 깔고있는데 에러가 났다.
찾아보니 필수 라이브러리를 사전에 설치해야 에러가 안난다는거다.
그것에 필요한 모듈을 아래와 같이 적어놓는다.

 

 

sudo apt install -y libavformat-dev libavcodec-dev libavdevice-dev \
libavutil-dev libavfilter-dev libswscale-dev libswresample-dev \
pkg-config cmake build-essential python3-dev ffmpeg
libssl-dev


그와 더불어 이것도 오래되서 업데이트 해야 한단다.

pip install --upgrade pip
pip install --upgrade setuptools wheel

라즈베리파이에서 파이썬 라이브러리 설치하다가 다음과 같은 에러가 발생했다.


 

알아보니 라즈비안 정책상 파이썬 모듈로 전역설치를 못하게 막아두었단다. 
찾아보니 가상환경으로 바꾸어서 설치를 하라고 한다.

# 1. 가상환경 생성
python3 -m venv venv

# 2. 가상환경 활성화
source venv/bin/activate

# 3. 필요한 모듈 설치
pip install aiortc aiohttp opencv-python


위와 같이 실행하면 정상적으로 설치를 진행한다.



어느날 Xcode로 토이프로젝트를 진행하다 이제 깃허브에 올려야겠다싶어
터미널 단축키를 찾아봤는데 눈을 씻고 찾아도 없더라..
그런데 알고보니 Xcode엔 그냥 터미널을 지원 안한단다.
그런데 최대한 구글링을 해보니 흡사한 방법이 있어 적어본다.

결론은.. 윈도우 .bat 파일처럼 명령어를 사전에 적어놓고 실행하게끔 하면 된다.

 

1. 사전 명령어를 실행할 스크립트 파일 만들기

touch open_terminal.sh

 

2. 해당 파일접근

vi open_terminal.sh

 

Insert 키누르고, 아래스크립트 작성후에 :wq 작성후 엔터

#!/bin/zsh
open -a Terminal `pwd`

 

위의 #!/bin/zsh 부분은 bash일경우 #!/bin/bash로 바꾸어주면 된다. 실행할 프로그램을 선언하는 것이다.

이제 스크립트 준비는 끝났다.
이제 Xcode로 접근하자.

 

1. Xcode -> Behaviors -> Edit behaviors 접근  

 

 

2. 커스텀 Behavior 작성

 

좌측하단의 + 기호를 누르고 하단의 Run 항목에 체크를 하고 전에 작성한 스크립트를 넣는다.
이때 명령어를 직접 쓰는게 아니라 파일업로드하듯이 파일을 찾아 넣어야 한다.

 

위와 같이하면 해당 프로젝트경로를 가진 터미널을 바로 실행한다.

스벨트에서 객체 및 배열 반복하는 경우가 있어 예제를 작성한다.

  1. 배열 및 배열 안의 객체 반복
let  test_state1 = [1,2];
let  test_state2 = [{uid:1,name :'test1'},{uid:2,name :'test2'}];

{#each test_state1 as item} 
    <option value={item}>{item}</option>
 {/each}

{#each test_state2 as item} 
    <option value={item.uid}>{item.name}</option>
 {/each}
 

2.객체 반복

let  test_state = {"meat":"육류","fish":"어류"};

{#each Object.entries(test_state) as [key, value]}              
              <option value={key}>{value}</option>
{/each}

 

끝~!

 

 

개발환경에서 자바스크립트에 console.log 쓸 일이 매우많다. 지워주면 가장 좋지만,

개발하고 배포하고 개발하고 배포하고 하는 일들이 비일비재하기 때문에

너무 귀찮다.

vite를 활용하여 노출이 안되게 처리해주자.

  1. vite-plugin-remove-console npm 라이브러리 설치
 

vite-plugin-remove-console

A vite plugin that remove the types of console in the production environment. Latest version: 2.2.0, last published: a year ago. Start using vite-plugin-remove-console in your project by running `npm i vite-plugin-remove-console`. There are 8 other project

www.npmjs.com

 

npm i -- save vite-plugin-remove-console

 

2. vite.config.js(또는 .ts)

import { sveltekit } from '@sveltejs/kit/vite';
import  { defineConfig } from 'vite';
import removeConsole from "vite-plugin-remove-console";

export default defineConfig({
	plugins: [sveltekit(),removeConsole()],
  
	... 생략(서버 설정등)
  });
위의 plugins 에 removeConsole() 만 추가해주면 된다.

 

스벨트를 빌드해서 Docker 로 배포하려고 한다.

이때 설정하는 .dockerignore , Dockerfile 에 대해 설정하는 법을 작성해보고자 한다.

1) .dockerignore

node_modules
.svelte-kit

나의 경우 svelte-kit를 포함하고 있어서, svelte-kit를 사용하지 않는 사람은 생략해도 된다.

node_modules는 어차피 docker build를 할때 npm i 명령어로 install 하기 때문에 따로 건드리지 않는다.

2) DockerFile

# 이미지의 기반이 될 이미지 선택
FROM node:20.10.0

# 앱의 소스코드를 포함할 디렉토리 생성
WORKDIR /app

# package.json 파일을 복사한다. 만약 다시 빌드할 때 변경사항이 없을 경우 npm install까지 그냥 넘어간다.
COPY package.json /app


# 이미지를 받으면 npm install을 자동으로 해줌
RUN npm install

# 어떤 파일이 이미지에 들어가야 하는지 
# 첫 번째 .은 이 프로젝트의 모든 폴더 및 파일들 (Dockerfile을 제외한)
# 두 번째 .은 파일을 저장할 컨테이너 내부 경로 (ex /app)
COPY . /app

# 앱 빌드
RUN npm run build


# 포트 설정
EXPOSE 3000

# 프로그램 실행
CMD ["npm","run","preview", "--", "--host"]

DockerFile의 경우 설정법이야 워낙 많지만.. 최소한의 것만 작성한다.

일단 나의 경우 vite를 썼기 때문에 npm run build를 적용하고 preview로 실행하는 데, 이때

포트가 0.0.0.0 으로만 켜지는 것을 방지하기 위해 --, --host를 추가적으로 작성해준다.

 

보통 프론트에서 백엔드 API 로 데이터 요청을 할때 같은 서버내에 프론트서버,백엔드서버 둘다 존재한다면

localhost.. 이런식으로 요청하거나 xxxx.co.kr 이런식으로 도메인을 따서 요청할 것이다.

그런 경우 .env 파일에 경로를 지정해서 import 해서 요청하는 방식을 적용할 것이다.

// .env 파일 
VITE_API_BASE_URL=http://localhost:8081
 
// api 요청 파일
const apiBaseUrl = import.meta.env.VITE_API_BASE_URL;

	const login = (e : any) => { 
    	const url = `${apiBaseUrl}/sign-api/sign-in`
    }

 

위와 같은 식으로 말이다..

그러나 그것을 매번 소스코드에 입력하기도 귀찮고 보안상 그리 좋은 거 같지는 않다.

스벨트에 vite 를 적용했다면 다음과 같이 설정해보자

import { sveltekit } from '@sveltejs/kit/vite';
import  { defineConfig } from 'vite';

export default defineConfig({
	plugins: [sveltekit()],
	server: {
	  proxy: {
		'/api': {    
		  target: 'http://localhost:8081', 
		  changeOrigin: true,
		  rewrite: (path) => path.replace(/^\/api/, ''),
		},
	  },
	},
  });

위의 target은 실질적으로 백엔드 API 주소 를 말하며, '/api' 는 백엔드 API 주소를 치환하겠다는 말이다.

그럼 위 코드를 변경하면

// api 요청 파일
	const login = (e : any) => { 
    	const url = "/api/sign-api/sign-in"
  }

이런식으로

.env 파일이 필요 없어지고 긴 api 주소는 /api 문자열로 처리한다.

훨씬 깔끔한거 같다.

 

Svelte Kit 사용중 외부 라이브러리 css 모듈을 사용할 일이 있는데.. 간혹

import 시 css 파일이 통합 적용 안되어 있는 모듈이 있다.

<link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.8.2/css/all.css">

 

그렇다고 매번 위와 같은 방식을 적용하면 매번 css 파일을 웹으로 접근해서 가져와야 하므로 매우 비효율적이다.

자 Svelte Kit 프로젝트 내의 vite.config.ts 로 접근해보자.

import { sveltekit } from '@sveltejs/kit/vite';
import  { defineConfig } from 'vite';

export default defineConfig({
	build: {
		rollupOptions: {
		  // 외부 모듈을 번들링합니다.
		  external: ['tabulator-tables-css'],
	
		  // 번들에 포함할 모듈의 경로를 설정합니다.
		  output: {
			globals: {
			  'tabulator-tables-css': 'Tabulator', 
// 모듈 이름과 전역 변수 이름을 설정합니다.
			},
		  },
		},
	  },
	  resolve: {
		alias: {
		  // 사용할 모듈의 별칭을 설정합니다.
		  'tabulator-tables-css': 'tabulator-tables/dist/css/tabulator_modern.min.css',
		},
	  },

	plugins: [sveltekit()],
  });

위 코드의 주석을 살펴보면, 먼저 resolve 객체를 가면

  'tabulator-tables-css': 'tabulator-tables/dist/css/tabulator_modern.min.css',

 

왼쪽이 프로젝트 내에서 어떻게 사용할지 별명을 짓는것이며, 우측은 node_modules 내의 소스코드 경로이다.

위의 css 파일 경로를 작성하고, 실제 사용할 .svelte 및 js, ts파일에서 로드하는 방법은

import 'tabulator-tables-css'; // CSS 파일이 import됩니다.

이런식으로 호출해서 사용한다.

그외 scss 나 static 폴더내에 css 를 정의해서 app.html에 정의하는 방법이 있으나

node_modules 내의 css 파일을 import 하는 방법은 저런식으로 사용한다.

지난 포스팅에 이어 백엔드용 Spring Boot 를 빌드 및 배포해보자.

  1. DockerFile 작성 (프로젝트 루트경로에 작성한다
FROM openjdk:11
# FROM amazoncorretto:11 ==> amazon corretto 11 사용할 경우
ARG JAR_FILE=build/libs/*.jar
COPY ${JAR_FILE} app.jar
ENV SPRING_PROFILES_ACTIVE=prod
ENTRYPOINT ["java","-jar","/app.jar"]
# ENTRYPOINT ["java","-jar","-Dspring.profiles.active=prod","/app.jar"]
# => 설정파일을 분리해서 사용할 때
# java -jar -Dspring.profiles.active=prod app.jar

2. Build

필자는 Gradle 을 쓰기 때문에 Gradle 로 한다.

./gradlew build -x test

3. 도커 이미지 생성

# gradle linux/amd64 옵션은 맥북 M1을 위한 옵션
$ docker build --build-arg DEPENDENCY=build/dependency -t 도커허브 ID/Repository --platform linux/amd64 .

# maven
$ docker build -t 도커허브 ID/Repository --platform linux/amd64 .

# 확인
$ docker images

4. 도커 업로드

# 로그인
$ docker login

# 업로드
$ docker push 도커허브이름/Repository:버전정보

그 외 리눅스 서버 배포는 Next.js 배포와 동일하니 거길 보고 따라하시면 됩니다.

 

미루고 미루다 드디어 Docker를 활용하여 배포를 한다.

개념은 나중에 정리하고 바로 시작해보자.

1) next.config.js 파일 수정

/** @type {import('next').NextConfig} */
const path = require('path');
const withImages = require('next-images');

module.exports = {
  output: 'standalone',
  distDir: 'build',
  reactStrictMode: true,
  async rewrites() {
    if (process.env.NODE_ENV === "production") {
      return [
        {
          source: process.env.PRODUCTION_JAVA_SERVER_PATH,
          destination: process.env.PRODUCTION_JAVA_SERVER_URL,
        }

      ];
    } else {
      return [
        {
          source: process.env.JAVA_SERVER_PATH,
          destination: process.env.JAVA_SERVER_URL,
        }
      ];
    }
  },
};
 

2) .env.local 변경

NODE_ENV = 'development'

PRODUCTION_JAVA_SERVER_PATH = '/java/:path*'
PRODUCTION_JAVA_SERVER_URL = 'http://사용하는 IP 주소:8083/:path*'

JAVA_SERVER_PATH = '/java/:path*'
JAVA_SERVER_URL = 'http://localhost:8083/:path*'

 

3) Dockerfile 생성


# 위에서 도커 허브 node 이미지를 기반으로 로컬로 다운로드 및 캐싱 되었기 때문에 이미지를 가져올 수 있다.
FROM node:18.4.0

# 만약 컨테이너 안의 이미지의 경로가 /app 이런식으로 되어있다면 작업할 div 경로를 설정할 수도 있다.
# 설정해주면 COPY 의 두번째 경로를 ./ 이것으로 했을 때 자동으로 /app 경로가 된다.
WORKDIR /app

# package.json 파일을 복사한다. 만약 다시 빌드할 때 변경사항이 없을 경우 npm install까지 그냥 넘어간다.
COPY package.json /app

# 이미지를 받으면 npm install을 자동으로 해줌
RUN npm install


# 어떤 파일이 이미지에 들어가야 하는지 
# 첫 번째 .은 이 프로젝트의 모든 폴더 및 파일들 (Dockerfile을 제외한)
# 두 번째 .은 파일을 저장할 컨테이너 내부 경로 (ex /app)
COPY . /app

# 배포환경으로 설정
ENV NODE_ENV=production

RUN npm run build

# 도케에게 우리가 서버를 실행할 포트를 말해준다.
EXPOSE 3000

# 이미지가 생성될 때 실행되지 않고 컨테이너가 실행될 때 수행하는 명령어
CMD ["npm","start"]

가급적 개발 서버와 Node 버전을 맞춰주어야 한다.

필자는 NVM 을 활용하여 버전을 맞춰주었다.

4) dockerignore 생성

/.dockerignore

.node_modules
.next

5) 이미지 빌드

$ docker build -t 도커허브이름/web-client:버전정보 . ex) docker build -t ohkwonseok/web-client:1.0.1 .

 

만약 맥북에서 빌드하고 리눅스, amd64 서버에 배포할 예정인 경우

$ docker buildx build --platform=linux/amd64 -t 도커허브이름/web_client:버전정보 .
ex) docker buildx build --platform=linux/amd64 -t ohkwonseok/web-client:1.0.1 .

개발서버 및 배포서버의 운영체제에 따라 알맞게 선택하여 둘 중 하나를 사용하면 된다.

6) Dockerhub Repository 생성

 

회원가입을 안했을 경우 회원가입을 해주고, 이미 회원가입이 되어있다면

우측 상단의 Sign In 을 클릭하여 로그인한다.

*** 이때, username 이 실질적인 docker hub name 이 되므로, 비교적 간단하게 작성바란다.

명령어에 계속 작성할 일이 많다. ***

7) Create repository 클릭하여 생성한다. (별로 어렵지 않으니 나머지 부분은 생략)

8) 이제 빌드한 것을 도커허브에 업로드한다.

$ docker push 도커허브이름/web-client:1.0.1
ex) docker push ohkwonseok/web-client:1.0.1

*** 이제부터 리눅스 서버에 도커를 배포하는 것을 진행한다. ***

1) 도커 설치

$ sudo wget -qO- http://get.docker.com/ | sh

2) 도커 로그인

$ docker login
 

3) 도커 시작

$ sudo systemctl start docker
 

4) 도커허브에서 이미지 파일 받기(Pull)

$ docker pull 도커허브이름/web_client:버전정보
ex) docker pull ohkwonseok/web_client:1.0.1

5) 이미지 id 확인

$ docker images
 

6) 이미지 컨테이너 실행

$ docker run -p 80:3000 -d --rm 도커허브이름/web_client:버전정보

3000 번 포트를 80포트로 전환 실행한다.

끝~~!

 

+ Recent posts