5.1. κ°μ(Overview)
RSocketμ TCP, μΉμμΌ κ·Έλ¦¬κ³ κΈ°ν λ€λ₯Έ λ°μ΄νΈ μ€νΈλ¦Ό μ μ‘μ ν΅ν λ€μ€νλ μλ°©ν₯ ν΅μ μ μν μ ν리μΌμ΄μ νλ‘ν μ½μ΄λ€. μλ μ€ νλλ₯Ό μνΈμμ© λͺ¨λΈλ‘ μ¬μ©νλ€.
Request-Response- λ©μμ§ νλλ₯Ό μ μ‘νκ³ νλμ μλ΅μ λ°λλ€.Request-Stream- λ©μμ§ νλλ₯Ό μ μ‘νκ³ νλμ μλ΅μ μ€νΈλ¦ΌμΌλ‘ λ°λλ€.Channel- μλ°©ν₯μΌλ‘ λ©μμ§ μ€νΈλ¦Όμ μ μ‘νλ€.Fire-and-Forget- λ¨λ°©ν₯ λ©μμ§λ₯Ό μ μ‘νλ€.
컀λ₯μ μ΄ λ§Ίμ΄μ§λ©΄, βν΄λΌμ΄μΈνΈβμ βμλ²β λΌλ ꡬλΆμ μ¬λΌμ§κ³ , μμͺ½μ΄ λμΉμ΄ λμ΄ κ°κ°μ΄ μμ μνΈμμ© λͺ¨λΈ μ€ νλλ₯Ό μμν μ μλ€. λ°λΌμ νλ‘ν μ½μμ μ°Έμ¬νλ μμͺ½μ βμμ²μ(requester)βμ βμλ΅μ(responder)β λΌκ³ λΆλ₯΄λ©°, μνΈ μμ© λͺ¨λΈμ βμμ² μ€νΈλ¦Ό(request streams)β λλ κ°λ¨ν βμμ²(requests)β μ΄λΌκ³ λΆλ₯Έλ€.
λ€μμ RSocket νλ‘ν μ½μ μ£Όμ κΈ°λ₯κ³Ό μ΄μ μ΄λ€:
- λ€νΈμν¬ κ²½κ³λ₯Ό κ°λ‘μ§λ₯΄λ 리μ‘ν°λΈ μ€νΈλ¦Ό μ맨ν±μ€ -
Request-Streamκ³ΌChannelκ°μ μ€νΈλ¦¬λ° μμ²μ μν΄μ, λ°±νλ μ μ νΈλ μμ²μμ μλ΅μ μ¬μ΄λ₯Ό μ€κ°κΈ° λλ¬Έμ μμ²μκ° μλ΅μμ μλλ₯Ό μ μ΄ν μ μλ€. λ°λΌμ λ€νΈμν¬ κ³μΈ΅μ νΌμ‘ μ μ΄μ λν μμ‘΄μ μ€μ΄κ³ λ€νΈμν¬ λ 벨 λλ μ΄λ€ λ 벨μμλ μ§ λ²νΌλ§μ νμμ±μ μ€μΈλ€. - μμ² μ‘°μ (Request throttling) - ν μͺ½μμ
LEASEνλ μμ μ‘μ νλ©΄ μ§μ λ μκ°λμ λ€λ₯Έ μͺ½μ λ³΄λΌ μ μλ μμ²μ΄ μ νλλ€. μ΄ κΈ°λ₯μ βLeasingβ μ΄λΌκ³ λΆλ₯Έλ€. μ΄λ μ£ΌκΈ°μ μΌλ‘ κ°±μ λλ€. - μΈμ μ¬κ°(Session resumption) - 컀λ₯μ μ΄ λμ΄μ§λλΌλ μΌλΆ μνλ₯Ό μ μ§ν΄μ€λ€. μ ν리μΌμ΄μ μ λͺ ννκ² μνλ₯Ό κ΄λ¦¬ν μ μμΌλ©°, λ°±νλ μ μ ν¨κ» μ¬μ©νλ κ²½μ° μμ°μ(producer)λ₯Ό μ€λ¨νκ³ , νμν μνμ μμ μ€μΌ μ μλ€.
- ν° λ©μμ§μ λ¨νΈν(fragmentation)μ μ¬μ‘°λ¦½(re-assembly).
- Keepalive (heartbeats).
RSocketμ μ¬λ¬ μΈμ΄λ‘ ꡬνλμ΄ μλ€. μλ° λΌμ΄λΈλ¬λ¦¬λ μ μ‘μ μν Project Reactorμ Reactor Nettyλ₯Ό κΈ°λ°μΌλ‘ νλ€. μ¦, μ ν리μΌμ΄μ μμ 리μ‘ν°λΈ μ€νΈλ¦Ό Publisherμ μ νΈκ° Roskcetμ ν΅ν΄ λ€νΈμν¬λ₯Ό κ°λ‘μ§λ¬ ν¬λͺ νκ² μ νλλ€λ λ»μ΄λ€.
5.1.1. νλ‘ν μ½(The Protocol)
RSocketμ μ₯μ μ€ νλλ λ€νΈμν¬λ§μμμ λμμ΄ μ μ μλμ΄ μκ³ μΌλΆ νλ‘ν μ½ νμ₯(extensions)κ³Ό ν¨κ» μ½κΈ° μ¬μ΄ μ€ν(specification)μ΄λΌλ κ²μ΄λ€. λ°λΌμ μΈμ΄ ꡬν λ° μμ λ 벨 νλ μμν¬ APIμ μκ΄μμ΄ μ€νμ¬νμ μ½μ΄λ³΄λ κ²μ΄ μ’λ€. μ΄ μΉμ μμλ λ§₯λ½μ μ 립νκΈ° μν κ°κ²°ν κ°μλ₯Ό μ 곡νλ€.
Connecting
μ΄κΈ°μ ν΄λΌμ΄μΈνΈλ TCP λλ μΉμμΌκ³Ό κ°μ μ μμ€ μ€νΈλ¦¬λ° μ μ‘μ ν΅ν΄ μλ²μ μ°κ²°νκ³ , 컀λ₯μ
νλΌλ―Έν° μ€μ μ μν΄ SETUP νλ μμ
μλ²λ‘ μ μ‘νλ€.
μλ²λ SETUP νλ μμ κ±°λΆν μ μμ§λ§, μΌλ°μ μΌλ‘ μ΄ νλ μμ μ μ‘(ν΄λΌμ΄μΈνΈκ°)νκ³ μμ (μλ²κ°)νλ€λ©΄, μμͺ½μμ μμ²μ μμν μ μλ€.
νμ§λ§ SETUP νλ μμ΄ μμ² μλ₯Ό μ ννκΈ° μν΄ leasing μ맨ν±μ€λ₯Ό μ¬μ©νλ€λ©΄, μμ²μ νκΈ° μν΄ μμͺ½ λͺ¨λμμλ λ€λ₯Έ μͺ½μ΄ LEASE
νλ μμ λ³΄λ΄ μμ²μ μλ½ν λκΉμ§ κΈ°λ€λ €μΌ νλ€.
Making Requests
ν λ² μ»€λ₯μ
μ΄ λ§Ίμ΄μ§λ©΄, μμͺ½μ REQUEST_RESPONSE, REQUEST_STREAM, REQUEST_CHANNEL, REQUEST_FNF νλ μ μ€ νλλ₯Ό
ν΅ν΄ μμ²μ μμν μ μλ€. κ° νλ μμ μμ²μλ‘λΆν° μλ΅μμκ² λ©μμ§ νλλ₯Ό μ μ‘νλ€.
μλ΅μλ PAYLOAD νλ μμ μλ΅ λ©μμ§μ ν¨κ» 보λ΄κ³ , REQUEST_CHANNEL μμ²μΈ κ²½μ°, μμ²μλ PAYLOAD νλ μκ³Ό ν¨κ» μμ² λ©μμ§λ₯Ό
λ λ³΄λΌ μ μλ€.
μμ²μ Request-Streamκ³Ό Channelκ³Ό κ°μ λ©μμ§ μ€νΈλ¦Όμ ν¬ν¨λ κ²½μ°, μλ΅μλ μμ²μκ° λ³΄λΈ μꡬ μ νΈ(Demand signals)λ₯Ό
μ€μν΄μΌ νλ€. μꡬμ¬νμ λ©μμ§ μλ‘ ννλλ€. μ΄κΈ° μꡬμ¬νμ REQUEST_STREAM, REQUEST_CHANNEL νλ μμ μ§μ νλ€.
νμ μꡬμ¬νμ REQUEST_N νλ μμ ν΅νλ€.
κ° μΈ‘μ METADATA_PUSH νλ μμ κ°λ³ μμ²μ΄ μλ μ 체 μ°κ²°κ³Ό κ΄λ ¨λ λ©ν λ°μ΄ν° μλ¦Όμ μ μ‘ν μλ μλ€.
Message Format
RSocket λ©μμ§μλ λ°μ΄ν°μ λ©ν λ°μ΄ν°κ° ν¬ν¨λλ€. λ©ν λ°μ΄ν°λ λΌμ°ν
, 보μ ν ν° λ±μ μ μ‘νλλ° μ¬μ©λ μ μλ€. λ°μ΄ν°μ λ©ν λ°μ΄ν°λ
λ€λ₯Έ ν¬λ§·μ μ¬μ©νλ€. κ°κ°μ λν MIME μ νμ SETUP νλ μμ μ μΈλμ΄ μ§μ λ 컀λ₯μ
μ λͺ¨λ μμ²μ μ μ©λλ€.
λͺ¨λ λ©μμ§λ λ©ν λ°μ΄ν°λ₯Ό κ°μ§ μ μμ§λ§ μΌλ°μ μΌλ‘ λΌμ°ν
κ³Ό κ°μ λ©ν λ°μ΄ν°λ λ³΄ν΅ μμ² λΉ νλλ§ νμνλ―λ‘, μμ²μ 첫 λ²μ§Έ λ©μμ§μλ§
ν¬ν¨μν¨λ€. μλ₯Ό λ€μ΄, REQUEST_RESPONSE, REQUEST_STREAM, REQUEST_CHANNEL, REQUEST_FNF.
νλ‘ν μ½ νμ₯μ μ ν리μΌμ΄μ μμ μ¬μ©νκΈ° μν μΌλ°μ μΈ κ³΅ν΅ λ©ν λ°μ΄ν° ν¬λ§·μ μ μνλ€:
- Composite Metadata - λ€μμ λ 립μ μΌλ‘ ν¬λ§·ν λ λ©νλ°μ΄ν° μνΈλ¦¬
- Routing - μμ²μ λν λΌμ°ν
5.1.2. μλ° κ΅¬ν(Java Implementation)
RSocket μλ° κ΅¬ν체
λProject Reactorλ₯Ό κΈ°λ°μΌλ‘ νλ€.
TCPμ μΉμμΌ μ μ‘μ Reactor
Nettyλ₯Ό κΈ°λ°μΌλ‘ νλ€. 리μ‘ν°λΈ μ€νΈλ¦Ό λΌμ΄λΈλ¬λ¦¬λ‘μ, 리μ‘ν°λ νλ‘ν μ½ κ΅¬ν ꡬνμ λ¨μνκ² νλ€.
μ ν리μΌμ΄μ
μμλ μ μΈμ μΈ(declarative) μ°μ°μμ ν¬λͺ
ν λ°±νλ μ
μ§μ κΈ°λ₯μ κ°μΆ Fluxμ Monoλ₯Ό μ¬μ©νλ κ²μ΄ μμ°μ€λ½λ€.
RSocket μλ° APIλ μλμ μΌλ‘ μ΅μμ μ΄κ³ κΈ°λ³Έμ μ΄λ€. APIλ νλ‘ν μ½ κΈ°λ₯μλ§ μ€μ μ λκ³ μ ν리μΌμ΄μ νλ‘κ·Έλλ° λͺ¨λΈ(μλ₯Ό λ€μ΄, RPC codegen, λ€λ₯Έ μ½λ λ±)μ λ λμ μμ€μ λ 립λ κ΄μ¬μ¬λ§ 보면 λλ€.
ꡬν체μΈ
io.rsocket.RSocketμ μ£Όμ μν μ λ€ κ°μ§ μνΈλμ νμ
μ λ§λλ κ²μ΄λ€. λ¨μΌ λ©μμ§λ Mono, λ©μμ§ μ€νΈλ¦Όμ Flux,
λ°μ΄νΈ λ²νΌλ‘ λ°μ΄ν°μ λ©ν λ°μ΄ν°μ μ κ·Όνλ μ€μ λ©μμ§λ io.rsocket.Payloadκ° μλ€. RSocketμ μν μ λμΉμ μΌλ‘ μ¬μ©λλ€.
μμ²μ λν΄μλ μ ν리μΌμ΄μ
μ μμ²μ μν RSocketμ΄ μ£Όμ΄μ§κ³ , μλ΅μ λν΄μλ RSocketμ ꡬννμ¬ μμ²μ νΈλ€λ§νλ€.
μ΄κ²λ€μ μμ ν μκ°κ° μλλ€. λλΆλΆ μ€νλ§ μ ν리μΌμ΄μ μ΄ APIλ₯Ό μ§μ μ¬μ©ν νμκ° μλ€. κ·Έλ¬λ μ€νλ§κ³Ό λ 립μ μΌλ‘ RSocketμ 보거λ ν μ€νΈνλ κ²μ΄ μ€μν μ μλ€. RSocket μλ° μ μ₯μμλ APIμ νλ‘ν μ½ κΈ°λ₯μ 보μ¬μ£Όλ λ§μ μν μ±μ΄ ν¬ν¨λμ΄ μλ€.
5.1.3. μ€νλ§ μ§μ(Spring Support)
spring-messaging λͺ¨λμ λ€μμ ν¬ν¨νλ€:
- RSocketRequester -
io.rsocket.RSocketκ³Ό λ°μ΄ν°, λ©ν λ°μ΄ν°μ μΈμ½λ©/λμ½λ©μ ν΅ν΄ μμ²μ μμ±νλ μ μ°ν API - Annotated Responders - μλ΅μ μν
@RequestMappingμ΄λ Έν μ΄μ μ΄ μ μ©λ νΈλ€λ¬ λ©μλ
spring-web λͺ¨λμλ RSocket μ ν리μΌμ΄μ
μ΄ νμν μλ μλ Jackson, CBOR/JSON, Protobufμ κ°μ Encoderμ Decoder
ꡬνμ²΄κ° ν¬ν¨λμ΄ μλ€. λν ν¨κ³Όμ μΌλ‘ λΌμ°ν
λ§€μΉμ νκΈ° μν PathPatternParserλ ν¬ν¨λμ΄ μλ€.
μ€νλ§λΆνΈ 2.2λ TCPλ μΉμμΌμ μ¬μ©νμ¬ RSocket μλ²λ₯Ό μ§μνκ³ , μΉνλμ€ μλ²μμ μΉμμΌμ ν΅ν RSocketμ λ
ΈμΆνλ μ΅μ
μ ν¬ν¨νλ€.
λν RSocketRequester.Builderμ RSocketStrategiesμ λν ν΄λΌμ΄μΈνΈ μ§μ λ° μλ μ€μ λ μλ€. μμΈν λ΄μ©μ
μ€νλ§ λΆνΈ λ νΌλ°μ€μ RSocket μΉμ
μ μ°Έμ‘°νλΌ.
μ€νλ§ μν리ν°(Spring Security) 5.2λ RSocketμ μ§μνλ€.
μ€νλ§ Integration 5.2λ μΈλ°μ΄λμ μμλ°μ΄λ κ²μ΄νΈ μ¨μ΄λ₯Ό μ 곡νμ¬ RSocket ν΄λΌμ΄μΈνΈμ μλ²μ μνΈμμ©νλ€. μμΈν λ΄μ©μ Spring Integration Reference Manualμ μ°Έμ‘°νλΌ.
μ€νλ§ ν΄λΌμ°λ κ²μ΄νΈμ¨μ΄λ(Spring Cloud Gateway)λ RSocket 컀λ₯μ μ μ§μνλ€.
λͺ©μ°¨ κ°μ΄λ