동기화 액터 actix_web :: web :: block 또는 futures-cpupool을 사용하여 디젤을 실행해야합니까?


10

배경

r2d2를 통해 디젤을 사용하는 actix-web 응용 프로그램을 작성 중이며 비동기 쿼리를 가장 잘 만드는 방법을 잘 모르겠습니다. 합리적인 것처럼 보이는 세 가지 옵션을 찾았지만 어느 것이 가장 적합한 지 확실하지 않습니다.

잠재적 인 솔루션

싱크 액터

우선 actix 예제를 사용할 수는 있지만 상당히 복잡하고 많은 양의 상용구가 필요합니다. 더 합리적인 해결책이 있기를 바랍니다.

Actix_web::web::block

또 다른 옵션으로를 사용하여 actix_web::web::block쿼리 기능을 미래에 래핑 할 수 있지만 성능의 영향을 확신하지 못합니다.

그런 다음 쿼리가 동일한 Tokio 시스템에서 실행됩니까? 소스에서 찾을 수있는 것으로부터 기본 actix-web threadpool에 스레드가 생성 됩니다. 그게 문제입니까?

코드를 올바르게 읽으면 r2d2가 연결을 가져올 때 스레드를 차단하여 핵심 actix-web 풀의 일부를 차단합니다. 데이터베이스 쿼리와 동일합니다. 그런 다음 해당 풀에 스레드가있는 것보다 더 많은 쿼리를 수행하면 모든 actix-web을 차단합니까? 그렇다면 큰 문제입니다.

선물 CPU 풀

마지막으로 불필요한 오버 헤드가있을 수있는 안전한 내기는 futures-cpupool 입니다. 주요 문제는 내 프로젝트에 다른 상자를 추가한다는 것을 의미하지만 내 응용 프로그램에서 여러 개의 CPU 풀이 불필요하게 떠 다니는 아이디어는 마음에 들지 않습니다.

r2d2와 디젤이 모두 차단되므로 여기에는 놀라운 일이 많이 있습니다.

가장 중요한 것은이 cpupool을 동일한 r2d2 풀을 사용하지 않는 것과 공유하지 마십시오 (만약 작성된 모든 스레드가 r2d2 연결 대기를 막고 작업이있을 때 전체 풀을 잠글 수 있음).

두 번째로 (좀 더 분명히), 풀의 스레드보다 r2d2 연결이 더 크지 않아야하며 그 반대의 경우 더 큰 리소스가 낭비됩니다 (사용하지 않는 연결 / 스레드가 지속적으로 차단됨) cpupool 스케줄러가 아닌 OS 스케줄러에 의한 연결 핸드 오버).

마지막으로, 사용중인 데이터베이스와 성능을 염두에 두십시오. 풀에서 단일 연결 r2d2와 단일 스레드를 실행하는 것은 쓰기 무거운 sqlite 응용 프로그램에서 가장 좋습니다 (그러나 적절한 데이터베이스를 권장합니다).

이전 답변

작동 할 수있는 오래된 솔루션

https://www.reddit.com/r/rust/comments/axy0hp/patterns_to_scale_actixweb_and_diesel/

본질적으로 Futures-cpupool을 권장합니다.

미래의 R에서 차단 I / O를 캡슐화하는 가장 좋은 방법은 무엇입니까?

일반적인 경우 Futures-cpupool을 권장합니다.

작동하지 않는 오래된 솔루션

https://www.reddit.com/r/rust/comments/9fe1ye/noob_here_can_we_talk_about_async_and_databases/

오래된 actix-web 버전에 대한 정말 좋은 수정입니다. 내가 찾을 수있는 것에서 더 이상 요청에 CPU 풀이 없습니다.


이 문제에 대한 의견 에서 디젤 futures-cpupoolasync대한 지원 이 부족한 경우 권장되는 해결 방법 인 것 같습니다 .
Jmb

그것은 일반적인 해결책입니다. 나는 actix 시스템을 활용할 무언가를 바란다. 그럼에도 불구하고, 나는 미래의 CPU 풀을 파고 들어 문제를 찾습니다.
logina

스택 오버플로에 오신 것을 환영합니다! 미래의 R에서 I / O 차단을 캡슐화하는 가장 좋은 방법무엇입니까? . 그렇지 않은 경우 차이점을 설명하기 위해 질문을 편집 하십시오. 그렇지 않으면이 질문을 이미 답변 한 것으로 표시 할 수 있습니다.
Shepmaster

cpupool도 r2d2의 블로킹 연결 풀과 상호 작용하기 때문에 최선의 해결 방법을 모르겠습니다. 나는 지금 그것을 스스로 찾고 있으며 곧 업데이트 될 것입니다.
logina

답변:


3

나는 선물 CPU 풀과 함께 가고 있습니다. 내 상호 작용의 차단 특성으로 인해 최상의 솔루션입니다.

actix_web :: web :: block을 사용하는 것은 충분하지만 actix에서 공유 스레드 풀을 사용합니다. (차단 호출로 인해 전체 스레드 풀을 차단하고 actix_web에 지정된 다른 작업을 방해 할 수 있습니다).

futures-cpupool을 사용하여 데이터베이스 상호 작용을 위해 데이터베이스마다 별도의 스레드 풀을 만드는 것이 좋습니다. 이렇게하면 서로 기다려야하는 모든 작업 (연결보다 많은 작업이있는 경우)을 하나의 풀로 그룹화하여 연결이 필요하지 않은 다른 작업을 차단하지 않고 잠재적으로 스레드 수를 제한 할 수 있습니다. 연결 수 (작업이 차단되지 않을 때만 예약 됨).

하나의 데이터베이스 연결 만 사용하려는 경우 동기화 액터는 매우 좋은 옵션입니다. 하나의 스레드가있는 선물 CPU 풀처럼 작동하여 별도의 스레드 대신 actix-web의 기본 스레드 중 하나를 사용한다는 점을 제외하고 모든 작업이 한 번에 하나씩 실행되도록합니다 (따라서 연결이 거의 없음) . 그래도 상용구가 너무 커서 가치가 없습니다.


6
위의 내 결과를 읽는 받는 관련하시기 바랍니다 넣어 정보 - 대답대답 이 아니라 질문입니다.
Shepmaster
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.