1
1
use core:: fmt;
2
2
#[ cfg( feature = "tls" ) ]
3
3
use std:: convert:: TryFrom ;
4
+ use std:: error:: Error ;
4
5
use std:: fmt:: Display ;
5
6
/*
6
7
* Copyright 2020 Clint Byrum
@@ -170,11 +171,14 @@ impl ClientJob {
170
171
/// Should only return when the worker has sent data or completed the job.
171
172
///
172
173
/// Use this in clients to wait for a response on a job that was submitted. This will return an error if used on a background job.
173
- pub async fn response ( & mut self ) -> Result < WorkUpdate , io :: Error > {
174
+ pub async fn response ( & mut self ) -> Result < WorkUpdate , Box < dyn Error > > {
174
175
if let Some ( workupdate) = self . response_rx . recv ( ) . await {
175
176
Ok ( workupdate)
176
177
} else {
177
- Err ( io:: Error :: new ( io:: ErrorKind :: Other , "Nothing to receive." ) )
178
+ Err ( Box :: new ( io:: Error :: new (
179
+ io:: ErrorKind :: NotConnected ,
180
+ "Nothing to receive." ,
181
+ ) ) )
178
182
}
179
183
}
180
184
}
@@ -223,12 +227,21 @@ impl WorkerJob {
223
227
payload. put_u8 ( b'\0' ) ;
224
228
payload. extend ( denominator. as_bytes ( ) ) ;
225
229
let packet = new_res ( WORK_STATUS , payload. freeze ( ) ) ;
226
- self . send_packet ( packet) . await
230
+ self . send_packet ( packet) . await . map_err ( |e| {
231
+ if e. is :: < std:: io:: Error > ( ) {
232
+ * e. downcast :: < std:: io:: Error > ( ) . expect ( "downcast after is" )
233
+ } else {
234
+ std:: io:: Error :: new ( io:: ErrorKind :: Other , e. to_string ( ) )
235
+ }
236
+ } )
227
237
}
228
238
229
- async fn send_packet ( & mut self , packet : Packet ) -> Result < ( ) , io :: Error > {
239
+ async fn send_packet ( & mut self , packet : Packet ) -> Result < ( ) , Box < dyn Error > > {
230
240
match self . sink_tx . send ( packet) . await {
231
- Err ( _) => Err ( io:: Error :: new ( io:: ErrorKind :: Other , "Connection closed" ) ) ,
241
+ Err ( _) => Err ( Box :: new ( io:: Error :: new (
242
+ io:: ErrorKind :: NotConnected ,
243
+ "Connection closed" ,
244
+ ) ) ) ,
232
245
Ok ( _) => Ok ( ( ) ) ,
233
246
}
234
247
}
@@ -237,7 +250,7 @@ impl WorkerJob {
237
250
///
238
251
/// This method is typically called by the [Client::work] method upon return
239
252
/// of an error from the assigned closure.
240
- pub async fn work_fail ( & mut self ) -> Result < ( ) , io :: Error > {
253
+ pub async fn work_fail ( & mut self ) -> Result < ( ) , Box < dyn Error > > {
241
254
let packet = new_res ( WORK_FAIL , self . handle . clone ( ) ) ;
242
255
self . send_packet ( packet) . await
243
256
}
@@ -246,7 +259,7 @@ impl WorkerJob {
246
259
///
247
260
/// This method is typically called by the [Client::work] method upon return of
248
261
/// the assigned closure.
249
- pub async fn work_complete ( & mut self , response : Vec < u8 > ) -> Result < ( ) , io :: Error > {
262
+ pub async fn work_complete ( & mut self , response : Vec < u8 > ) -> Result < ( ) , Box < dyn Error > > {
250
263
let mut payload = BytesMut :: with_capacity ( self . handle . len ( ) + 1 + self . payload . len ( ) ) ;
251
264
payload. extend ( self . handle . clone ( ) ) ;
252
265
payload. put_u8 ( b'\0' ) ;
@@ -437,13 +450,15 @@ impl Client {
437
450
while let Some ( frame) = stream. next ( ) . await {
438
451
trace ! ( "Frame read: {:?}" , frame) ;
439
452
let response = match frame {
440
- Err ( e) => Err ( e) ,
453
+ Err ( e) => Err ( e. to_string ( ) ) ,
441
454
Ok ( frame) => {
442
455
let handler = handler. clone ( ) ;
443
456
debug ! ( "Locking handler" ) ;
444
457
let mut handler = handler;
445
458
debug ! ( "Locked handler" ) ;
446
- handler. call ( frame)
459
+ handler
460
+ . call ( frame)
461
+ . map_err ( |e| e. to_string ( ) )
447
462
}
448
463
} ;
449
464
match response {
@@ -544,18 +559,18 @@ impl Client {
544
559
/// Sends an ECHO_REQ to the first server, a good way to confirm the connection is alive
545
560
///
546
561
/// Returns an error if there aren't any connected servers, or no ECHO_RES comes back
547
- pub async fn echo ( & mut self , payload : & [ u8 ] ) -> Result < ( ) , io :: Error > {
562
+ pub async fn echo ( & mut self , payload : & [ u8 ] ) -> Result < ( ) , Box < dyn Error > > {
548
563
let packet = new_req ( ECHO_REQ , Bytes :: copy_from_slice ( payload) ) ;
549
564
{
550
565
let conns = self
551
566
. conns
552
567
. lock ( )
553
568
. expect ( "All lock holders should not panic" ) ;
554
569
if conns. len ( ) < 1 {
555
- return Err ( io:: Error :: new (
556
- io:: ErrorKind :: Other ,
570
+ return Err ( Box :: new ( io:: Error :: new (
571
+ io:: ErrorKind :: NotConnected ,
557
572
"No connections for echo!" ,
558
- ) ) ;
573
+ ) ) ) ;
559
574
}
560
575
conns
561
576
. get ( 0 )
@@ -573,7 +588,11 @@ impl Client {
573
588
574
589
/// Submits a foreground job. The see [ClientJob::response] for how to see the response from the
575
590
/// worker. The unique ID will be generated using [Uuid::new_v4]
576
- pub async fn submit ( & mut self , function : & str , payload : & [ u8 ] ) -> Result < ClientJob , io:: Error > {
591
+ pub async fn submit (
592
+ & mut self ,
593
+ function : & str ,
594
+ payload : & [ u8 ] ,
595
+ ) -> Result < ClientJob , Box < dyn Error > > {
577
596
self . direct_submit ( SUBMIT_JOB , function, payload, None )
578
597
. await
579
598
}
@@ -584,7 +603,7 @@ impl Client {
584
603
function : & str ,
585
604
unique : & [ u8 ] ,
586
605
payload : & [ u8 ] ,
587
- ) -> Result < ClientJob , io :: Error > {
606
+ ) -> Result < ClientJob , Box < dyn Error > > {
588
607
self . direct_submit ( SUBMIT_JOB , function, payload, Some ( unique) )
589
608
. await
590
609
}
@@ -595,7 +614,7 @@ impl Client {
595
614
& mut self ,
596
615
function : & str ,
597
616
payload : & [ u8 ] ,
598
- ) -> Result < ClientJob , io :: Error > {
617
+ ) -> Result < ClientJob , Box < dyn Error > > {
599
618
self . direct_submit ( SUBMIT_JOB_BG , function, payload, None )
600
619
. await
601
620
}
@@ -607,7 +626,7 @@ impl Client {
607
626
function : & str ,
608
627
unique : & [ u8 ] ,
609
628
payload : & [ u8 ] ,
610
- ) -> Result < ClientJob , io :: Error > {
629
+ ) -> Result < ClientJob , Box < dyn Error > > {
611
630
self . direct_submit ( SUBMIT_JOB_BG , function, payload, Some ( unique) )
612
631
. await
613
632
}
@@ -618,7 +637,7 @@ impl Client {
618
637
function : & str ,
619
638
payload : & [ u8 ] ,
620
639
unique : Option < & [ u8 ] > ,
621
- ) -> Result < ClientJob , io :: Error > {
640
+ ) -> Result < ClientJob , Box < dyn Error > > {
622
641
let mut uuid_unique = BytesMut :: new ( ) ;
623
642
let unique: & [ u8 ] = match unique {
624
643
None => {
@@ -641,10 +660,10 @@ impl Client {
641
660
. expect ( "All lock holders should not panic" ) ;
642
661
let conn = match conns. get_hashed_conn ( & unique. iter ( ) . map ( |b| * b) . collect ( ) ) {
643
662
None => {
644
- return Err ( io:: Error :: new (
645
- io:: ErrorKind :: Other ,
663
+ return Err ( Box :: new ( io:: Error :: new (
664
+ io:: ErrorKind :: NotConnected ,
646
665
"No connections for submitting jobs." ,
647
- ) ) ;
666
+ ) ) ) ;
648
667
}
649
668
Some ( conn) => conn,
650
669
} ;
@@ -664,13 +683,16 @@ impl Client {
664
683
} ;
665
684
Ok ( ClientJob :: new ( handle, rx) )
666
685
} else {
667
- Err ( io:: Error :: new ( io:: ErrorKind :: Other , "No job created!" ) )
686
+ Err ( Box :: new ( io:: Error :: new (
687
+ io:: ErrorKind :: NotConnected ,
688
+ "Receiver exited." ,
689
+ ) ) )
668
690
} ;
669
- submit_result
691
+ Ok ( submit_result? )
670
692
}
671
693
672
694
/// Sends a GET_STATUS packet and then returns the STATUS_RES in a [JobStatus]
673
- pub async fn get_status ( & mut self , handle : & ServerHandle ) -> Result < JobStatus , io :: Error > {
695
+ pub async fn get_status ( & mut self , handle : & ServerHandle ) -> Result < JobStatus , Box < dyn Error > > {
674
696
let mut payload = BytesMut :: with_capacity ( handle. handle ( ) . len ( ) ) ;
675
697
payload. extend ( handle. handle ( ) ) ;
676
698
let status_req = new_req ( GET_STATUS , payload. freeze ( ) ) ;
@@ -686,7 +708,12 @@ impl Client {
686
708
None
687
709
}
688
710
} ) {
689
- None => return Err ( io:: Error :: new ( ErrorKind :: Other , "No connection for job" ) ) ,
711
+ None => {
712
+ return Err ( Box :: new ( io:: Error :: new (
713
+ ErrorKind :: NotConnected ,
714
+ "No connection for job" ,
715
+ ) ) )
716
+ }
690
717
Some ( conn) => conn,
691
718
} ;
692
719
conn. send_packet ( status_req) . await ?;
@@ -695,7 +722,10 @@ impl Client {
695
722
if let Some ( status_res) = self . client_data . receivers ( ) . status_res_rx . recv ( ) . await {
696
723
Ok ( status_res)
697
724
} else {
698
- Err ( io:: Error :: new ( io:: ErrorKind :: Other , "No status to report!" ) )
725
+ Err ( Box :: new ( io:: Error :: new (
726
+ io:: ErrorKind :: NotConnected ,
727
+ "No status to report!" ,
728
+ ) ) )
699
729
}
700
730
}
701
731
@@ -709,7 +739,7 @@ impl Client {
709
739
///
710
740
/// See examples/worker.rs for more information.
711
741
///
712
- pub async fn can_do < F > ( mut self , function : & str , func : F ) -> Result < Self , io :: Error >
742
+ pub async fn can_do < F > ( mut self , function : & str , func : F ) -> Result < Self , Box < dyn Error > >
713
743
where
714
744
F : FnMut ( & mut WorkerJob ) -> Result < Vec < u8 > , io:: Error > + Send + ' static ,
715
745
{
@@ -743,7 +773,7 @@ impl Client {
743
773
task:: spawn_blocking ( move || {
744
774
let rt = tokio:: runtime:: Builder :: new_current_thread ( )
745
775
. build ( )
746
- . unwrap ( ) ;
776
+ . expect ( "Tokio builder should not panic" ) ;
747
777
let res = func_clone. lock ( ) . unwrap ( ) ( & mut job) ;
748
778
match res {
749
779
Err ( _) => {
@@ -767,7 +797,7 @@ impl Client {
767
797
768
798
/// Receive and do just one job. Will not return until a job is done or there
769
799
/// is an error. This is called in a loop by [Client::work].
770
- pub async fn do_one_job ( & mut self ) -> Result < ( ) , io :: Error > {
800
+ pub async fn do_one_job ( & mut self ) -> Result < ( ) , Box < dyn Error > > {
771
801
let job = self . client_data . receivers ( ) . worker_job_rx . try_recv ( ) ;
772
802
let job = match job {
773
803
Err ( TryRecvError :: Empty ) => {
@@ -784,18 +814,18 @@ impl Client {
784
814
match self . client_data . receivers ( ) . worker_job_rx . recv ( ) . await {
785
815
Some ( job) => job,
786
816
None => {
787
- return Err ( io:: Error :: new (
788
- io:: ErrorKind :: Other ,
817
+ return Err ( Box :: new ( io:: Error :: new (
818
+ io:: ErrorKind :: NotConnected ,
789
819
"Worker job tx are all dropped" ,
790
- ) )
820
+ ) ) )
791
821
}
792
822
}
793
823
}
794
824
Err ( TryRecvError :: Disconnected ) => {
795
- return Err ( io:: Error :: new (
796
- io:: ErrorKind :: Other ,
825
+ return Err ( Box :: new ( io:: Error :: new (
826
+ io:: ErrorKind :: NotConnected ,
797
827
"Worker job tx are all dropped" ,
798
- ) )
828
+ ) ) )
799
829
}
800
830
Ok ( job) => job,
801
831
} ;
@@ -804,13 +834,13 @@ impl Client {
804
834
. get_jobs_tx_by_func ( & Vec :: from ( job. function ( ) ) )
805
835
{
806
836
None => {
807
- return Err ( io:: Error :: new (
808
- io:: ErrorKind :: Other ,
837
+ return Err ( Box :: new ( io:: Error :: new (
838
+ io:: ErrorKind :: InvalidInput ,
809
839
format ! (
810
840
"Received job for unregistered function: {:?}" ,
811
841
job. function( )
812
842
) ,
813
- ) )
843
+ ) ) )
814
844
}
815
845
Some ( tx) => tx,
816
846
} ;
@@ -827,15 +857,15 @@ impl Client {
827
857
/// not return unless there is an unexpected error.
828
858
///
829
859
/// See examples/worker.rs for more information on how to use it.
830
- pub async fn work ( mut self ) -> Result < ( ) , io :: Error > {
860
+ pub async fn work ( mut self ) -> Result < ( ) , Box < dyn Error > > {
831
861
loop {
832
862
self . do_one_job ( ) . await ?;
833
863
}
834
864
}
835
865
836
866
/// Gets a single error that might have come from the server. The tuple returned is (code,
837
867
/// message)
838
- pub async fn error ( & mut self ) -> Result < Option < ( Bytes , Bytes ) > , io :: Error > {
868
+ pub async fn error ( & mut self ) -> Result < Option < ( Bytes , Bytes ) > , & str > {
839
869
Ok ( self . client_data . receivers ( ) . error_rx . recv ( ) . await )
840
870
}
841
871
}
0 commit comments