Nest.JS | 모나드 -> IO

Jan 27 2023
"입력/출력 모나드"라고도 하는 IO 모나드는 입력/출력 작업의 설명과 실행을 분리할 수 있는 기능적 프로그래밍 개념입니다. 즉, 명시적으로 호출될 때까지 실제로 해당 작업을 수행하지 않고 일부 I/O 작업(예: 파일 읽기 또는 데이터베이스와의 상호 작용)을 수행하는 계산을 정의할 수 있습니다.

"입력/출력 모나드"라고도 하는 IO 모나드는 입력/출력 작업의 설명과 실행을 분리할 수 있는 기능적 프로그래밍 개념입니다. 즉, 명시적으로 호출될 때까지 실제로 해당 작업을 수행하지 않고 일부 I/O 작업(예: 파일 읽기 또는 데이터베이스와의 상호 작용)을 수행하는 계산을 정의할 수 있습니다.

IO 모나드는 종종 JavaScript와 같은 기능적 프로그래밍 언어에서 부작용을 관리하는 데 사용됩니다. IO 모나드를 사용하면 순수하고 구성 가능한 방식으로 효과적인 계산을 설명할 수 있으므로 코드를 더 쉽게 추론하고 테스트할 수 있습니다.

runIO 모나드는 일반적으로 I/O 작업을 수행하고 결과를 반환하는 이라는 단일 메서드가 있는 객체로 구현됩니다 . IO 모나드는 여러 I/O 작업을 함께 연결하고 더 복잡한 계산을 생성하는 데 사용할 수 있습니다.

다음은 JavaScript에서 IO 모나드의 예입니다.

class IO {
  constructor(effect) {
    this.effect = effect
  }
  run() {
    return this.effect()
  }
  map(f) {
    return new IO(() => f(this.run()))
  }
  chain(f) {
    return new IO(() => f(this.run()).run())
  }
  // ...
}

import { Injectable } from '@nestjs/common';
import { IO, io } from 'fp-ts/lib/IO';

@Injectable()
export class MyService {
  public async getUsers(): IO<User[]> {
    return io.fromPromise(this.userRepository.find());
  }

  public async getUserById(id: string): IO<User> {
    return io.fromPromise(this.userRepository.findOne(id));
  }
}

.map(), .chain(), 메서드를 사용하여 여러 계산을 연결할 수 있습니다 .ap().

const program: IO<string> = myService.getUsers()
    .map(users => users.filter(user => user.age > 18))
    .chain(users => myService.getUserById(users[0].id))
    .map(user => user.name)

  program.run()

이 예제는 기본 예제이며 함수형 프로그래밍에서 모나드의 모든 기능을 보여주지 않는다는 점에 유의해야 합니다. 모나드는 오류 처리, 여러 계산 연결 등과 같은 다양한 경우를 처리하는 데 사용할 수 있습니다. 모나드를 적용하기 전에 문제와 사용 사례를 이해하는 것이 가장 좋습니다.

또한 run()메서드는 IO 모나드를 실행하고 결과를 얻기 위해 호출되어야 합니다. 이것은 impure외부 상태/컨텍스트에 의존하는 것으로 알려져 있습니다. IO 모나드는 더 나은 코드 구성을 위해 순수 코드에서 순수 코드를 분리하는 데 사용됩니다. 그리고 테스트.

부품 목록: