~b=ddlZddlmZddlmZddlmZddlZddl m Z m Z ddl m Z ejdgd Zd Zd Zd Zej&d GddeZdZdZdZdZdZej&ddGddeZej&d GddeZej&ddGddeZeZdZGdd eZ y)!Nwraps)count)getfullargspec) Transitioner Automaton) preserveNameArgSpecargsvarargsvarkwdefaults kwonlyargskwonlydefaults annotationsc t|}tt|j|j|j |j r |j ndt|j|jr#t|jjndt|jjS)z Normalize inspect.ArgSpec across python versions and convert mutable attributes to immutable types. :param Callable func: A function. :return: The function's ArgSpec. :rtype: ArgSpec r ) getArgsSpecr tupler rrrrritemsr)funcspecs 5/usr/lib/python3/dist-packages/automat/_methodical.py _getArgSpecrs t D  499  jj"&--R)"" $%%++- .(*$**0023  ct|j|jz|jrdndz|jrdndz|j zS)a0 Get the name of all arguments defined in a function signature. The name of * and ** arguments is normalized to "*args" and "**kwargs". :param ArgSpec spec: A function to interrogate for a signature. :return: The set of all argument names in `func`s signature. :rtype: Set[str] )z*argsr)z**kwargs)setr rrrr)rs r _getArgNamesr ,sV  // :2 /!JJ=B 0      rc.tfd}|S)a Decorate a function so all its arguments must be passed by keyword. A useful utility for decorators that take arguments so that they don't accidentally get passed the thing they're decorating as their first argument. Only works for methods right now. c|fi|SNr)selfkwfs rgz_keywords_only..gIs}}rr)r&r's` r_keywords_onlyr(?s  1X HrT)frozenceZdZdZej dZej Zej dZdde fdZ dZ y)MethodicalStatez- A state for a L{MethodicalMachine}. FreprNc ||}|g}t|j}|D]}t|j}|j|r*tdj |j j |j j t|j t|j |jj|||||y)ac Declare a state transition within the :class:`automat.MethodicalMachine` associated with this :class:`automat.MethodicalState`: upon the receipt of the `input`, enter the `state`, emitting each output in `outputs`. :param MethodicalInput input: The input triggering a state transition. :param MethodicalState enter: The resulting state. :param Iterable[MethodicalOutput] outputs: The outputs to be triggered as a result of the declared state transition. :param Callable collector: The function to be used when collecting output return values. :raises TypeError: if any of the `outputs` signatures do not match the `inputs` signature. :raises ValueError: if the state transition from `self` via `input` has already been defined. Nzdmethod {input} signature {inputSignature} does not match output {output} signature {outputSignature})inputoutputinputSignatureoutputSignature) r argSpecissubset TypeErrorformatmethod__name__rmachine_oneTransition)r$r/enteroutputs collector inputArgsr0 outputArgss ruponzMethodicalState.uponXs& =E ?G /  F%fnn5J&&y1228&#ll33%}}55'25<<'@(3FMM(B 393  ##D%Krc.|jjSr#r7r8r$s r_namezMethodicalState._name~{{###r) r8 __module__ __qualname____doc__attribr9r7 serializedlistr@rDrrrr+r+OsIdgg5!G TWWYFe$J $dd$LL$rr+cjt||d}|#t||j}t||||S)z Get a L{Transitioner} N)getattrr initialStatesetattr)oselfsymbol automaton transitioners r_transitionerFromInstancerUsB5&$/L#   " "  v|, rcyr#rrrr_emptyrWsrcy) docstringNrrrr _docstringrZsrc|jjtjjtjjfvr t dy)Nzfunction body must be empty)__code__co_coderWrZ ValueError)inst attributer&s r assertNoCoderasG zz&//"9"9","5"5"="="??677?rcftt|jdd|}|jr|}n#|Dcgc]\}}||jvs|}}}t|}|D] \} } || | fz }t|jddd|jddd} | Dcic] \}}||vs ||} }}| j ||j r| } || fS|jdd|jz}| jDcic] \}}||vr||} }}|| fScc}}wcc}}wcc}}w)a Filter out arguments that were passed to input that output won't accept. :param tuple args: The *args that input received. :param dict kwargs: The **kwargs that input received. :param ArgSpec inputSpec: The input's arg spec. :param ArgSpec outputSpec: The output's arg spec. :return: The args and kwargs that output will accept. :rtype: Tuple[tuple, dict] rN) rzipr rrupdaterrr)r kwargs inputSpec outputSpec named_args return_argsnvpassed_arg_namesnamevaluer full_kwargs return_kwargsall_accepted_namess r _filterArgsrssfs9>>!"-t45J &0HTQ1 3GqH HV}!* eT5M)*9>>$B$'););DbD)ABH$,JDAq9I0I1a4JKJv#   %% (__QR0:3H3HH*5*;*;*=5$!Q!33A5 5  %%'IK5sD!D!" D'/D' D-F)eqhashc$eZdZdZej dZej eZej dZ ej eje dZ ej ddZ e jdZd d Zd Zy) MethodicalInputz. An input for a L{MethodicalMachine}. Fr,) validator)defaultr-initr-c,t|jSr#rr7rCs r _buildArgSpeczMethodicalInput._buildArgSpec4;;''rNctjjtjt jfd}|S)z Return a function that takes no arguments and returns values returned by output functions produced by the given L{MethodicalInput} in C{oself}'s current state. cd j g|i| j} j \}} j|}g}|D]\}|r||j t || j |j \}} | g|i| } |j| ^||Sr#)r7_state transition collectorsrDrsr3append)r rf previousStater< outTracerr=valuesr0akrorQr$rTs rdoInputz(MethodicalInput.__get__..doInputs DKK / / /(//M#/#:#:4#@ Wi 6IF! %flln-"4v~~N1u.q.A. e$  % V$ $r)rUrRrSr r7r)r$rQtyperrTs`` @r__get__zMethodicalInput.__get__sR 1 15A dkk " t{{  %  # %rc.|jjSr#rBrCs rrDzMethodicalInput._namerErr#)r8rFrGrHrIrJrSrar7rRFactorydictrr3ryr~rrDrrrrwrwsU#I TWW| ,F TWW% Fd!3%@Jdgg5u-G __((2$rrwceZdZdZej dZej Zej ddZejdZ d dZ dZ d Z y) MethodicalOutputz/ An output for a L{MethodicalMachine}. Fr,rzc,t|jSr#r}rCs rr~zMethodicalOutput._buildArgSpecrrNcvtdj|j|jj)zX Outputs are private, so raise an exception when we attempt to get one. zf{cls}.{method} is a state-machine output method; to produce this output, call an input method instead.)clsr7)AttributeErrorr6r8r7r$rQrs rrzMethodicalOutput.__get__s= DDJFMM{{++EKE  rc.|j|g|i|S)z- Call the underlying method. )r7)r$rQr rfs r__call__zMethodicalOutput.__call__st{{5242622rc.|jjSr#rBrCs rrDzMethodicalOutput._namerErr#)r8rFrGrHrIrJr9r7r3ryr~rrrDrrrrrs]dgg5!G TWWYFdgg5u-G __((  3 $rrc`eZdZejdZejdZddZy)MethodicalTracerFr,NcTt||j|jfd}|S)Nc(j|yr#)setTrace)tracerrTs rrz*MethodicalTracer.__get__..setTrace's  ! !& )r)rUrRrS)r$rQrrrTs @rrzMethodicalTracer.__get__$s'0 15A  *rr#)r8rFrGrIrJrSrRrrrrrrs'U#I TWW% Frrc8dtttzS)z, Create a unique Python identifier. _symbol_)strnextcounterrrrgensymr.s DM* **rceZdZdZdZd dZe ddZedZedZ dZ ed Z ed Z e d Zd Zy)MethodicalMachinezj A :class:`MethodicalMachine` is an interface to an `Automaton` that uses methods on a class. cNt|_i|_t|_yr#)r _automaton _reducersr_symbolrCs r__init__zMethodicalMachine.__init__<s#+x rNc | td|S)z L{MethodicalMachine} is an implementation detail for setting up class-level state; applications should never need to access it on an instance. z.MethodicalMachine is an implementation detail.)rrs rrzMethodicalMachine.__get__Bs!   @B B rcfd}|S)a Declare a state, possibly an initial state or a terminal state. This is a decorator for methods, but it will modify the method so as not to be callable any more. :param bool initial: is this state the initial state? Only one state on this :class:`automat.MethodicalMachine` may be an initial state; more than one is an error. :param bool terminal: Is this state a terminal state? i.e. a state that the machine can end up in? (This is purely informational at this point.) :param Hashable serialized: a serializable value to be used to represent this state to external systems. This value should be hashable; :py:func:`unicode` is a good type to use. cJt|}r|j_|S)N)r9r7rK)r+rrO) stateMethodstateinitialr$rKs r decoratorz*MethodicalMachine.state..decoratords+#D+6/9;E/4,Lrr)r$rterminalrKrs`` ` rrzMethodicalMachine.stateNs, rcfd}|S)zM Declare an input. This is a decorator for methods. cHtj|jS)N)rSr7rR)rwrr) inputMethodr$s rrz*MethodicalMachine.input..decoratorus "T__*5*.,,8 8rrr$rs` rr/zMethodicalMachine.inputns 8rcfd}|S)z Declare an output. This is a decorator for methods. This method will be called when the state machine transitions to this state as specified in the decorated `output` method. ct|S)N)r9r7)r) outputMethodr$s rrz+MethodicalMachine.output..decorators#DF Frrrs` rr0zMethodicalMachine.output|s Grcp|jj|||t|||j|<y)z. See L{MethodicalState.upon}. N)r addTransitionrr)r$ startState inputTokenendState outputTokensr=s rr:z MethodicalMachine._oneTransitions4& %%j*h&+L&9 ;,5 j)rcfd}|S) c2tfd}|S)Nct|jj}||jjSr#)rUrrrrK)rQrT decorateer$s r serializezBMethodicalMachine.serializer..decorator..serializes68 9= J   (;(;(F(FGGrr)rrr$s` rrz/MethodicalMachine.serializer..decorators$ 9  H H rrrs` r serializerzMethodicalMachine.serializers  rcfd}|S)rc2tfd}|S)Nc|g|i|}i}jjD]}|||j<t|jj}|||_yr#)rstatesrKrUrr) rQr rfrmapping eachStaterTrr$s r unserializezFMethodicalMachine.unserializer..decorator..unserializesp!%9$9&9!%!7!7!9>I4=GI001>84<< : &-en #rr)rrr$s` rrz1MethodicalMachine.unserializer..decorators" 9    rrrs` r unserializerzMethodicalMachine.unserializers rcBt|j|jSr#)rrrrCs r _setTracezMethodicalMachine._setTraces>>rc@ddlm}||jdddS)a Generate a L{graphviz.Digraph} that represents this machine's states and transitions. @return: L{graphviz.Digraph} object; for more information, please see the documentation for U{graphviz} r) makeDigraphc.|jjSr#rB)rs rz-MethodicalMachine.asDigraph.. (=(=rc.|jjSr#rB)r/s rrz-MethodicalMachine.asDigraph..rrc.|jjSr#rB)r0s rrz-MethodicalMachine.asDigraph..s&--*@*@r) stateAsString inputAsStringoutputAsString) _visualizerr)r$rs r asDigraphzMethodicalMachine.asDigraphs$ , OO==@   rr#)FFN)r8rFrGrHrrr(rr/r0r:rrpropertyrrrrrrr6s  ,1>    60  $?? rr)! collections functoolsr itertoolsrinspectrrrI_corerr _introspectionr namedtupler rr r(sobjectr+rUrWrZrarsrwrrrrrrrrrs1 *( !+ -N O 0&  t/$f/$/$d  8"%&P5u($f($($Vt $v $ $D5u v   '+b b r