nns_auto.tcl
Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008 package require nameserv ;
00009 package require uevent ;
00010
00011 namespace ::nameserv::auto {}
00012
00013
00014
00015
00016
00017
00018
00019
00020 ret ::nameserv::auto::bind (type name , type data) {
00021 # See nameserv::bind. Remembers the information, for re-binding
00022 # when the connection was lost, and later restored.
00023
00024 variable bindings
00025 variable delay
00026
00027 # Watch base client for loss of connection.
00028 uevent::bind nameserv lost-connection ::nameserv::auto::Reconnect
00029
00030 if {[catch {
00031 nameserv::bind $name $data
00032 } msg]} {
00033 if {[string match *No name server*]} {
00034 # No nameserver. Remember, and start reconnect polling.
00035 set bindings($name) $data
00036 after $delay ::nameserv::auto::Reconnect
00037 return
00038 }
00039 # Name is bound already, lost immediately, generate
00040 # standard event.
00041
00042 uevent::generate nameserv lost-name [list name $name data $data]
00043 return
00044 }
00045
00046 # Success. Remember for possible loss of connection.
00047 set bindings($name) $data
00048 return
00049 }
00050
00051 ret ::nameserv::auto::Reconnect (type args) {
00052 # args = <>|<tags event details>
00053 # <tag,event> = <'nameserv','lost'>
00054 # details = dict ('reason' -> string)
00055
00056 if {![catch {
00057 ::nameserv::server_features
00058 }]} {Rebind ; return}
00059
00060 variable delay
00061 after $delay ::nameserv::auto::Reconnect
00062 return
00063 }
00064
00065 ret ::nameserv::auto::Rebind () {
00066 variable bindings
00067
00068 foreach {name data} [array get bindings] {
00069 if {[catch {
00070 nameserv::bind $name $data
00071 } msg]} {
00072 # Lost server while rebinding names. Abort and wait for
00073 # the reconnect to try again.
00074 if {[string match *No name server*]} break
00075
00076 # Other error => (name already bound) That means someone
00077 # else took the name while we were not connected to the
00078 # service. Best effort we can do: Deliver total loss of
00079 # this binding to observers via event.
00080
00081 uevent::generate nameserv lost-name [list name $name data $data]
00082 }
00083 }
00084 return
00085 }
00086
00087
00088
00089
00090 namespace ::nameserv::auto {
00091
00092
00093
00094 variable bindings ; array bindings = {}
00095 }
00096
00097
00098
00099
00100 ret ::nameserv::auto::cget (type option) {
00101 return [configure $option]
00102 }
00103
00104 ret ::nameserv::auto::configure (type args) {
00105 variable delay
00106
00107 if {![llength $args]} {
00108 return [list -delay $delay]
00109 }
00110 if {[llength $args] == 1} {
00111 # cget
00112 set opt [lindex $args 0]
00113 switch -exact -- $opt {
00114 -delay { return $delay }
00115 default {
00116 return -code error "bad option \"$opt\", expected -delay"
00117 }
00118 }
00119 }
00120
00121 while {[llength $args]} {
00122 set opt [lindex $args 0]
00123 switch -exact -- $opt {
00124 -delay {
00125 if {[llength $args] % 2 == 1} {
00126 return -code error "value for \"$opt\" is missing"
00127 }
00128 # TODO: check integer > 0
00129 set delay [lindex $args 1]
00130 set args [lrange $args 2 end]
00131 }
00132 default {
00133 return -code error "bad option \"$opt\", expected -delay"
00134 }
00135 }
00136 }
00137 return
00138 }
00139
00140
00141
00142
00143 logger::initNamespace ::nameserv::auto
00144 namespace ::nameserv::auto {
00145
00146
00147 variable delay 1000 ;
00148 }
00149
00150
00151
00152
00153 package provide nameserv::auto 0.1
00154
00155
00156
00157