일반 올레 루비 개체

6738 단어 railsobjectspororuby


TRIGGER WARNING && TL;DR
서비스 객체는 때때로 Rails에서 과도하게 설계된다고 생각합니다. 사실 평범한 오래된 Ruby 객체가 잠재적으로 더 나을 수 있습니다. 서비스, ​​프리젠터, 라이브러리 모듈 등을 관리하기 위해 gem을 사용하고 있다면 그것이 제공하는 이점을 재고하고 가중치를 두어야 할 것입니다.

올해 Digital Rails Conf에서 저는 The Missing guide to Service Objects라는 비디오를 보았습니다.
나에게 이것은 서비스 객체에 대한 독단적인 가이드였지만, 그는 이러한 서비스 객체를 처리하는 여러 가지 방법과 Rails를 처음 접하는 사람들을 위해 이를 수행하는 몇 가지 방법에 대해 논의했습니다. 훌륭한 강연이었지만 제 사고 과정은 그 강연을 "PORO에 대해 이야기합시다"로 리팩토링하는 것이었습니다.

나에게 최고의 레일 설정은 다음을 수행합니다.
  • Rails는 Models 폴더의 모든 항목이 데이터를 설정하고 모델링하기 위한 것, 즉 데이터베이스 데이터를 직접 처리하는 경우에 가장 적합합니다.
  • 컨트롤러는 단순하며 비즈니스 로직 또는 모델을 직접 참조합니다.
  • 비즈니스 로직은 적절한 이름 형식으로 저장되며 컨트롤러 로직에서 떨어져 있습니다.

  • 이렇게 하려면 "#{insert_one}이 필요합니다"라고 생각할 수 있습니다. 서비스 개체, 프리젠터, 구성 요소, 원숭이 패치, 날아다니는 원숭이, 포켓몬, 모듈 개체 및 위젯.

    그럴 수도 있지만 어쨌든 평범한 오래된 루비 개체가 될 가능성이 높으므로 원하는대로 이름을 지정하고 귀하와 귀하의 팀에 적합한 디자인 패턴에 집중하십시오.

    왜 포로?



    이유를 확인하려면 다음 코드를 살펴보십시오. 매개변수를 받아 수행 메소드를 실행하는 간단한 클래스입니다. 간단히 말해서 이것은 서비스 개체이지만 평범한 오래된 루비 개체이기도 합니다.

    class Num::SquaredService
      def initialize(num)
        @num = num
      end 
    
      def call
        @num * @num  
      end 
      alias_method :peform, :call
    end 
    


    이 파일 관리자를 보고 있습니다. 이것은 여러 클래스에 대한 액세스 권한이 있다고 가정하고 각 클래스 내의 매처 메서드를 기반으로 유형을 결정합니다. 이 파일 관리자는 팩토리이거나 lib 폴더에 있거나 다른 이름으로 참조할 수 있습니다.

    class FileInspector::Type
      TYPES = [
        FileInspector::Image,
        FileInspector::Audio,
        FileInspector::Video,
        FileInspector::Text,
        FileInspector::Pdf, 
        FileInspector::Other
      ].freeze
    
      # Sets up mime type instance
      def initialize(file)
        @mime = `file --b --mime-type #{file}`.strip
      end
    
      # Determines the Type to be used in another object.
      def inspect
       TYPES.find { |type| type.matches?(@mime) }.name.demodulize
      end
    end
    


    몇 번의 키 입력으로 이 PORO는 서비스 개체처럼 보일 수 있습니다. 그렇게 해 보겠습니다.

    class FileInspector::TypeService
      TYPES = [
        FileInspector::Image,
        FileInspector::Audio,
        FileInspector::Video,
        FileInspector::Text,
        FileInspector::Pdf, 
        FileInspector::Other
      ].freeze
    
      # Sets up mime type instance
      def initialize(file)
        @mime = `file --b --mime-type #{file}`.strip
      end
    
      # Determines the Type to be used in another object.
      def call
       TYPES.find { |type| type.matches?(@mime) }.name.demodulize
      end
      alias_method :peform, :call
    end
    


    이제 서비스 개체가 생겼습니다. 몇 가지 더 변경하고 일부 HTML을 사용하면 이것을 발표자로 바꿀 수 있습니다. 내 요점은 객체의 기능에 대해 더 많이 생각해야 한다는 것입니다. 이름이나 디렉터리 구조에서 개체의 위치가 아닙니다.

    PORO로 유지하려는 이유는 모든 것을 단순하게 유지하고 모든 클래스가 단일 책임에 집중하도록 하기 위해서입니다. 큰 문제를 쉽게 테스트할 수 있는 작은 문제로 나눕니다.

    좋은 웹페이지 즐겨찾기