
RegistrationTest.pudu
Pudu127 lines6.2 KB
1/** @Test.Registration.Suite — what each registration adds to a catalog */2module PuduLangMediator.RegistrationTest34import Std.HashMap as HashMap5import Std.Io as Io6import Std.Test as Test7import PuduLangMediator.Catalog as Catalog8import PuduLangMediator.Context as Context9import PuduLangMediator.Domain.Order as Order10import PuduLangMediator.Message as Message11import PuduLangMediator as Messaging12import PuduLangMediator.Notification as Notification13import PuduLangMediator.Open as Open14import PuduLangMediator.Publishing as Publishing15import PuduLangMediator.Registration as Registration16import PuduLangMediator.Request as Request17import PuduLangMediator.Stream as Stream1819/** @Test.Registration.Quiet — an open component of every layer that does nothing */20type Quiet = {}2122impl Open.Behavior for Quiet {23 24 fn handleRequest[Q, R, E](self: &Self, request: &Q, info: &Message.Info, context: Context.Context, next: Request.Next[R, E]) -> Messaging.Outcome[R, E] { next(context) }25}2627impl Open.PreProcessor for Quiet {28 29 fn beforeRequest[Q, E](self: &Self, request: &Q, info: &Message.Info, context: Context.Context) -> Messaging.Outcome[(), E] { Ok(()) }30}3132impl Open.PostProcessor for Quiet {33 34 fn afterRequest[Q, R, E](self: &Self, request: &Q, response: &R, info: &Message.Info, context: Context.Context) -> Messaging.Outcome[(), E] { Ok(()) }35}3637impl Open.ExceptionAction for Quiet {38 39 fn onFailure[Q, E](self: &Self, request: &Q, failure: &Messaging.Failure[E], info: &Message.Info, context: Context.Context) -> () { () }40}4142impl Open.NotificationHandler for Quiet {43 44 fn handleNotification[N, E](self: &Self, notification: &N, info: &Message.Info, context: Context.Context) -> Messaging.Outcome[(), E] { Ok(()) }45}4647impl Open.StreamBehavior for Quiet {48 49 fn handleStream[Q, T, E](self: &Self, request: &Q, info: &Message.Info, context: Context.Context, sink: Stream.Sink[T], next: Stream.Next[T, E]) -> Messaging.Outcome[(), E] {50 next(context, sink)51 }52}535455fn applied(registrations: Array[Registration.Registration]) -> Catalog.Catalog {56 var catalog = Catalog.empty(Publishing.Sequential{}, Catalog.ForUnhandled)57 for registration in registrations { catalog = (registration.apply)(catalog) }58 catalog59}606162fn counted(table: &HashMap.HashMap[Str, Catalog.Entry], name: Str) -> (Int, Int) {63 match HashMap.get(table, &name) {64 case Some(entry) => (entry.handlers, entry.components)65 case None => (0, 0)66 }67}686970fn main() -> Int {71 let ask: Request.Kind[Int, Int, Str] = Request.kind("ask")72 let told: Notification.Kind[Int, Str] = Notification.kind("told")73 let flow: Stream.Kind[Int, Int, Str] = Stream.kind("flow")74 let passThrough = fn(_request: Int, context: Context.Context, next: Request.Next[Int, Str]) -> Messaging.Outcome[Int, Str] { next(context) }75 let catalog = applied([76 Registration.openBehavior(Quiet{}),77 Registration.group([78 Registration.handler(&ask, |value: Int, _context: Context.Context| Ok(value)),79 Registration.behavior(&ask, passThrough),80 Registration.preProcessor(&ask, |_value: Int, _context: Context.Context| Ok(())),81 Registration.postProcessor(&ask, |_value: Int, _answer: Int, _context: Context.Context| Ok(()))82 ]),83 Registration.exceptionHandler(&ask, |_value: Int, _failure: Messaging.Failure[Str], _context: Context.Context| None),84 Registration.exceptionAction(&ask, |_value: Int, _failure: Messaging.Failure[Str], _context: Context.Context| ()),85 Registration.openPreProcessor(Quiet{}),86 Registration.openPostProcessor(Quiet{}),87 Registration.openExceptionAction(Quiet{}),88 Registration.notificationHandler(&told, "one", |_value: Int, _context: Context.Context| Ok(())),89 Registration.openNotificationHandler("quiet", Quiet{}),90 Registration.notificationHandler(&told, "two", |_value: Int, _context: Context.Context| Ok(())),91 Registration.streamHandler(&flow, fn(_value: Int, _context: Context.Context, _sink: Stream.Sink[Int]) -> Messaging.Outcome[(), Str] { Ok(()) }),92 Registration.streamBehavior(&flow, fn(_value: Int, context: Context.Context, sink: Stream.Sink[Int], next: Stream.Next[Int, Str]) -> Messaging.Outcome[(), Str] { next(context, sink) }),93 Registration.openStreamBehavior(Quiet{})94 ])95 let held = catalog.assembly96 let checks = Test.suite("Registration", &[97 Test.equals("a request kind counts one handler and five components", &counted(&catalog.requests, "ask"), &(1, 5)),98 Test.equals("a notification kind counts every handler", &counted(&catalog.notifications, "told"), &(2, 0)),99 Test.equals("a stream kind counts its handler and behavior", &counted(&catalog.streams, "flow"), &(1, 1)),100 Test.equals("every open component is kept once", &(held.behaviors.length(), held.preProcessors.length(), held.postProcessors.length(), held.exceptionActions.length(), held.listeners.length(), held.streamBehaviors.length()), &(101 1, 1, 1, 1, 1, 1102 )),103 Test.equals("an open notification handler keeps its name", &held.listeners.map(|listener: Open.Listener| listener.name), &["quiet"]),104 Test.equals("every ordered registration is marked in order, groups included", &held.marks, &[105 Order.Open(Order.Behaviors, 0),106 Order.Closed(Order.Behaviors, "ask"),107 Order.Closed(Order.PreProcessors, "ask"),108 Order.Closed(Order.PostProcessors, "ask"),109 Order.Closed(Order.ExceptionActions, "ask"),110 Order.Open(Order.PreProcessors, 0),111 Order.Open(Order.PostProcessors, 0),112 Order.Open(Order.ExceptionActions, 0),113 Order.Closed(Order.NotificationHandlers, "told"),114 Order.Open(Order.NotificationHandlers, 0),115 Order.Closed(Order.NotificationHandlers, "told"),116 Order.Closed(Order.StreamBehaviors, "flow"),117 Order.Open(Order.StreamBehaviors, 0)118 ]),119 Test.equals("nothing is a problem", &Catalog.problems(&catalog), &[])120 ])121 let ran = Test.run(&checks)122 for failure in Test.failuresOf(&ran) {123 let _reported = Io.writeErrorLine(failure)124 }125 Test.report(&ran)126}127