Skip to content
GitLab
Projects
Groups
Snippets
/
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Menu
Open sidebar
Maud Kerebel
scripts
Commits
51937a9a
Commit
51937a9a
authored
Jul 31, 2014
by
Pierre-Elliott Bécue
Browse files
[trigger] Going back to simplified version
parent
8068f057
Changes
6
Hide whitespace changes
Inline
Side-by-side
gestion/config/trigger.py
View file @
51937a9a
...
...
@@ -7,6 +7,7 @@
import
itertools
debug
=
True
log_level
=
"info"
# Serveur maître
master
=
"rabbitmq.adm.crans.org"
...
...
gestion/trigger/host.py
View file @
51937a9a
...
...
@@ -10,27 +10,50 @@
# License : GPLv3
# Date : 28/04/2014
import
collections
class
TriggerFactory
(
object
):
"""Factory containing which function is part of the trigger set
"""
_meths
=
{}
_services
=
{}
_parsers
=
collections
.
defaultdict
(
list
)
@
classmethod
def
register
(
cls
,
key
,
value
):
cls
.
_
meth
s
[
key
]
=
value
def
register
_service
(
cls
,
key
,
value
):
cls
.
_
service
s
[
key
]
=
value
@
classmethod
def
get
(
cls
,
key
):
return
cls
.
_
meth
s
.
get
(
key
,
None
)
def
get
_service
(
cls
,
key
):
return
cls
.
_
service
s
.
get
(
key
,
None
)
@
classmethod
def
get_services
(
cls
):
return
cls
.
_meths
.
values
()
return
cls
.
_services
.
values
()
@
classmethod
def
register_parser
(
cls
,
keys
,
parser
):
for
key
in
keys
:
cls
.
_parsers
[
key
].
append
(
parser
)
@
classmethod
def
get_parser
(
cls
,
keyword
):
return
cls
.
_parsers
[
keyword
]
def
record_service
(
func
):
"""Records in the triggerfactory the function
The function provided are services to regen
"""
TriggerFactory
.
register_service
(
func
.
func_name
,
func
)
def
record
(
cls
):
TriggerFactory
.
register
(
cls
.
__name__
.
lower
(),
cls
)
def
trigger_service
(
what
):
return
TriggerFactory
.
get_service
(
what
)
def
trigger
(
what
):
return
TriggerFactory
.
get
(
what
)
def
record_parser
(
*
args
):
def
find_parser
(
func
):
TriggerFactory
.
register_parser
(
args
,
func
)
return
func
return
find_parser
gestion/trigger/services/dhcp.py
View file @
51937a9a
...
...
@@ -18,212 +18,186 @@ import struct
import
gestion.config.trigger
as
trigger_config
import
cranslib.clogger
as
clogger
logger
=
clogger
.
CLogger
(
"trigger"
,
"dhcp"
,
"debug"
,
trigger_config
.
debug
)
logger
=
clogger
.
CLogger
(
"trigger"
,
"dhcp"
,
trigger_config
.
log_level
,
trigger_config
.
debug
)
hostname
=
socket
.
gethostname
().
split
(
"."
)[
0
]
+
".adm.crans.org"
hostname
=
socket
.
gethostname
().
split
(
"."
)[
0
]
hostname_adm
=
hostname
+
".adm.crans.org"
import
lc_ldap.shortcuts
from
gestion.trigger.services.service
import
BasicService
from
cranslib.conffile
import
ConfFile
import
gestion.config.dhcp
as
dhcp_config
import
gestion.secrets_new
as
secrets_new
import
gestion.affichage
as
affichage
import
gestion.iptools
as
iptools
from
gestion.trigger.pypureomapi
import
pack_ip
,
pack_mac
,
OMAPI_OP_UPDATE
from
gestion.trigger.pypureomapi
import
Omapi
,
OmapiMessage
from
gestion.trigger.pypureomapi
import
pack_ip
,
pack_mac
,
OMAPI_OP_UPDATE
,
Omapi
,
OmapiMessage
from
gestion.trigger.host
import
record_service
,
record_parser
,
TriggerFactory
if
"dhcp"
in
trigger_config
.
services
[
hostname
]:
dhcp_omapi_keyname
=
secrets_new
.
get
(
"dhcp_omapi_keyname"
)
dhcp_omapi_key
=
secrets_new
.
get
(
"dhcp_omapi_keys"
)[
hostname_adm
]
ldap_conn
=
lc_ldap
.
shortcuts
.
lc_ldap_readonly
()
else
:
dhcp_omapi_keyname
=
None
dhcp_omapi_key
=
None
ldap_conn
=
None
class
Dhcp
(
BasicService
):
"""Class responsible of dhcp service.
@
record_parser
(
lc_ldap
.
attributs
.
macAddress
.
ldap_name
,
lc_ldap
.
attributs
.
ipHostNumber
.
ldap_name
)
def
send_mac_ip
(
body
,
diff
):
"""Computes mac_ip data to send from body and diff
"""
macs
=
tuple
([
body
[
i
].
get
(
lc_ldap
.
attributs
.
macAddress
.
ldap_name
,
[
''
])[
0
]
for
i
in
xrange
(
1
,
3
)])
ips
=
tuple
([
body
[
i
].
get
(
lc_ldap
.
attributs
.
ipHostNumber
.
ldap_name
,
[
''
])[
0
]
for
i
in
xrange
(
1
,
3
)])
hostnames
=
tuple
([
body
[
i
].
get
(
lc_ldap
.
attributs
.
host
.
ldap_name
,
[
''
])[
0
]
for
i
in
xrange
(
1
,
3
)])
# Régénération du DHCP :
if
not
macs
[
0
]:
# Création d'une nouvelle machine.
dhcp_dict
=
{
'add'
:
[(
macs
[
1
],
ips
[
1
],
hostnames
[
1
])]}
elif
not
macs
[
1
]:
# Destruction d'une machine.
dhcp_dict
=
{
'delete'
:
[(
macs
[
0
],
ips
[
0
])]}
else
:
# Mise à jour.
dhcp_dict
=
{
'update'
:
[(
macs
[
0
],
ips
[
0
],
macs
[
1
],
ips
[
1
],
hostnames
[
1
])]}
return
(
"dhcp"
,
dhcp_dict
)
@
record_service
def
dhcp
(
body
=
None
):
"""Regenerates dhcp service taking body into account.
# Class lookup table to define which changes call which function.
changes_trigger
=
{
lc_ldap
.
attributs
.
macAddress
.
ldap_name
:
(
'send_mac_ip'
,),
lc_ldap
.
attributs
.
ipHostNumber
.
ldap_name
:
(
'send_mac_ip'
,),
}
dhcp_omapi_keyname
=
None
dhcp_omapi_key
=
None
ldap_conn
=
None
"""
@
classmethod
def
send_mac_ip
(
cls
,
body
,
diff
):
"""Computes mac_ip data to send from body and diff
"""
macs
=
tuple
([
body
[
i
].
get
(
lc_ldap
.
attributs
.
macAddress
.
ldap_name
,
[
''
])[
0
]
for
i
in
xrange
(
1
,
3
)])
ips
=
tuple
([
body
[
i
].
get
(
lc_ldap
.
attributs
.
ipHostNumber
.
ldap_name
,
[
''
])[
0
]
for
i
in
xrange
(
1
,
3
)])
hostnames
=
tuple
([
body
[
i
].
get
(
lc_ldap
.
attributs
.
host
.
ldap_name
,
[
''
])[
0
]
for
i
in
xrange
(
1
,
3
)])
# Régénération du DHCP :
if
not
macs
[
0
]:
# Création d'une nouvelle machine.
dhcp_dict
=
{
'add'
:
[(
macs
[
1
],
ips
[
1
],
hostnames
[
1
])]}
elif
not
macs
[
1
]:
# Destruction d'une machine.
dhcp_dict
=
{
'delete'
:
[(
macs
[
0
],
ips
[
0
])]}
else
:
# Mise à jour.
dhcp_dict
=
{
'update'
:
[(
macs
[
0
],
ips
[
0
],
macs
[
1
],
ips
[
1
],
hostnames
[
1
])]}
return
(
"dhcp"
,
dhcp_dict
)
@
classmethod
def
regen
(
cls
,
body
=
None
):
"""Regenerates dhcp service taking body into account.
"""
cls
.
check_params
()
# http://satyajit.ranjeev.in/2012/01/12/python--dangerous-default-value-as-argument.html
# dict are referenced.
if
body
is
None
:
body
=
{}
if
body
and
isinstance
(
body
,
dict
):
for
(
mac
,
ip
,
name
)
in
body
.
get
(
"add"
,
[]):
logger
.
info
(
"Updating DHCP db by adding %s, %s, %s"
,
mac
,
ip
,
name
)
# XXX - Uncommend this when we need to start prod
# cls.add_dhcp_host(mac, ip, name)
for
(
mac
,
ip
)
in
body
.
get
(
"delete"
,
[]):
logger
.
info
(
"Updating DHCP db by deleting %s, %s"
,
mac
,
ip
)
# XXX - Uncommend this when we need to start prod
# cls.delete_dhcp_host(mac, ip)
for
(
rmac
,
rip
,
mac
,
ip
,
name
)
in
body
.
get
(
"update"
,
[]):
logger
.
info
(
"Updating DHCP db by modifying %s, %s to %s, %s, %s"
,
rmac
,
rip
,
mac
,
ip
,
name
)
# XXX - Uncommend this when we need to start prod
# cls.delete_dhcp_host(rmac, rip)
# cls.add_dhcp_host(mac, ip, name)
elif
body
==
True
:
hosts
=
{}
host_template
=
"""
host %(nom)s {
hardware ethernet %(mac)s;
fixed-address %(ip)s;
option host-name "%(host)s";
}
# http://satyajit.ranjeev.in/2012/01/12/python--dangerous-default-value-as-argument.html
# dict are referenced.
if
body
is
None
:
body
=
{}
if
body
and
isinstance
(
body
,
dict
):
for
(
mac
,
ip
,
name
)
in
body
.
get
(
"add"
,
[]):
logger
.
info
(
"Updating DHCP db by adding %s, %s, %s"
,
mac
,
ip
,
name
)
# XXX - Uncommend this when we need to start prod
# add_dhcp_host(mac, ip, name)
for
(
mac
,
ip
)
in
body
.
get
(
"delete"
,
[]):
logger
.
info
(
"Updating DHCP db by deleting %s, %s"
,
mac
,
ip
)
# XXX - Uncommend this when we need to start prod
# delete_dhcp_host(mac, ip)
for
(
rmac
,
rip
,
mac
,
ip
,
name
)
in
body
.
get
(
"update"
,
[]):
logger
.
info
(
"Updating DHCP db by modifying %s, %s to %s, %s, %s"
,
rmac
,
rip
,
mac
,
ip
,
name
)
# XXX - Uncommend this when we need to start prod
# delete_dhcp_host(rmac, rip)
# add_dhcp_host(mac, ip, name)
elif
body
==
True
:
hosts
=
{}
host_template
=
"""
host %(nom)s {
hardware ethernet %(mac)s;
fixed-address %(ip)s;
option host-name "%(host)s";
}
"""
affichage
.
prettyDoin
(
"Chargement des machines"
,
"..."
)
machines
=
cls
.
ldap_conn
.
allMachines
()
affichage
.
prettyDoin
(
"Chargement des machines"
,
"Ok"
)
animation
=
affichage
.
Animation
(
texte
=
"Génération de la configuration"
,
nb_cycles
=
len
(
machines
),
couleur
=
True
,
kikoo
=
True
)
for
machine
in
machines
:
for
net
in
dhcp_config
.
reseaux
.
keys
():
ip
=
str
(
machine
[
'ipHostNumber'
][
0
])
mac
=
str
(
machine
[
'macAddress'
][
0
])
nom
=
str
(
machine
[
'host'
][
0
])
if
'<automatique>'
not
in
[
ip
,
mac
]
and
iptools
.
AddrInNet
(
ip
,
net
):
d
=
{
'nom'
:
nom
,
'host'
:
nom
.
split
(
"."
,
1
)[
0
],
'mac'
:
mac
,
'ip'
:
ip
,
}
try
:
hosts
[
net
]
+=
host_template
%
d
except
:
hosts
[
net
]
=
host_template
%
d
animation
.
new_step
()
# Put a \n after the last iteration.
animation
.
end
()
step
=
"Enregistrement de la configuration dans les fichiers"
affichage
.
prettyDoin
(
step
,
"..."
)
for
(
net
,
fichier
)
in
dhcp_config
.
reseaux
.
items
():
with
ConfFile
(
fichier
)
as
configFile
:
configFile
.
header
(
"#"
)
if
hosts
.
has_key
(
net
):
configFile
.
write
(
hosts
[
net
])
affichage
.
prettyDoin
(
"Chargement des machines"
,
"..."
)
machines
=
ldap_conn
.
allMachines
()
affichage
.
prettyDoin
(
"Chargement des machines"
,
"Ok"
)
animation
=
affichage
.
Animation
(
texte
=
"Génération de la configuration"
,
nb_cycles
=
len
(
machines
),
couleur
=
True
,
kikoo
=
True
)
for
machine
in
machines
:
for
net
in
dhcp_config
.
reseaux
.
keys
():
ip
=
str
(
machine
[
'ipHostNumber'
][
0
])
mac
=
str
(
machine
[
'macAddress'
][
0
])
nom
=
str
(
machine
[
'host'
][
0
])
if
'<automatique>'
not
in
[
ip
,
mac
]
and
iptools
.
AddrInNet
(
ip
,
net
):
d
=
{
'nom'
:
nom
,
'host'
:
nom
.
split
(
"."
,
1
)[
0
],
'mac'
:
mac
,
'ip'
:
ip
,
}
try
:
hosts
[
net
]
+=
host_template
%
d
except
:
hosts
[
net
]
=
host_template
%
d
animation
.
new_step
()
# Put a \n after the last iteration.
animation
.
end
()
step
=
"Enregistrement de la configuration dans les fichiers"
affichage
.
prettyDoin
(
step
,
"..."
)
for
(
net
,
fichier
)
in
dhcp_config
.
reseaux
.
items
():
with
ConfFile
(
fichier
)
as
configFile
:
configFile
.
header
(
"#"
)
if
hosts
.
has_key
(
net
):
configFile
.
write
(
hosts
[
net
])
affichage
.
prettyDoin
(
step
,
"Ok"
)
step
=
"Nettoyage des fichiers de leases"
affichage
.
prettyDoin
(
step
,
"..."
)
try
:
lease_clean
()
affichage
.
prettyDoin
(
step
,
"Ok"
)
except
:
affichage
.
prettyDoin
(
step
,
"Erreur"
)
print
"During lease clean, an error occured."
raise
step
=
"Nettoyage des fichiers de leases"
affichage
.
prettyDoin
(
step
,
"..."
)
try
:
cls
.
lease_clean
()
affichage
.
prettyDoin
(
step
,
"Ok"
)
except
:
affichage
.
prettyDoin
(
step
,
"Erreur"
)
print
"During lease clean, an error occured."
raise
@
classmethod
def
check_params
(
cls
):
"""This method allows lazy evaluation for dhcp_omapi_keyname
and dhcp_omapi_key, since event imports all services. This is actually
the best lazy eval we can hope, since property won't work on
classmethods.
"""
if
cls
.
dhcp_omapi_keyname
is
None
:
cls
.
dhcp_omapi_keyname
=
secrets_new
.
get
(
"dhcp_omapi_keyname"
)
if
cls
.
dhcp_omapi_key
is
None
:
cls
.
dhcp_omapi_key
=
secrets_new
.
get
(
"dhcp_omapi_keys"
)[
hostname
]
if
cls
.
ldap_conn
is
None
:
cls
.
ldap_conn
=
lc_ldap
.
shortcuts
.
lc_ldap_readonly
()
@
classmethod
def
add_dhcp_host
(
cls
,
mac
,
ip
,
name
=
None
):
"""Adds a dhcp host using omapi
"""
cls
.
check_params
()
if
'<automatique>'
in
[
ip
,
mac
]:
return
msg
=
OmapiMessage
.
open
(
b
"host"
)
msg
.
message
.
append
((
b
"create"
,
struct
.
pack
(
"!I"
,
1
)))
msg
.
message
.
append
((
b
"exclusive"
,
struct
.
pack
(
"!I"
,
1
)))
msg
.
obj
.
append
((
b
"hardware-address"
,
pack_mac
(
mac
)))
msg
.
obj
.
append
((
b
"hardware-type"
,
struct
.
pack
(
"!I"
,
1
)))
msg
.
obj
.
append
((
b
"ip-address"
,
pack_ip
(
ip
)))
if
name
:
msg
.
obj
.
append
((
b
"name"
,
bytes
(
name
)))
conn
=
Omapi
(
hostname
,
9991
,
cls
.
dhcp_omapi_keyname
,
cls
.
dhcp_omapi_key
)
_
=
conn
.
query_server
(
msg
)
conn
.
close
()
@
classmethod
def
delete_dhcp_host
(
cls
,
mac
,
ip
):
"""Deletes dhcp host using omapi
"""
cls
.
check_params
()
if
'<automatique>'
in
[
ip
,
mac
]:
return
msg
=
OmapiMessage
.
open
(
b
"host"
)
msg
.
obj
.
append
((
b
"hardware-address"
,
pack_mac
(
mac
)))
msg
.
obj
.
append
((
b
"hardware-type"
,
struct
.
pack
(
"!I"
,
1
)))
msg
.
obj
.
append
((
b
"ip-address"
,
pack_ip
(
ip
)))
conn
=
Omapi
(
hostname
,
9991
,
cls
.
dhcp_omapi_keyname
,
cls
.
dhcp_omapi_key
)
response
=
conn
.
query_server
(
msg
)
if
response
.
opcode
==
OMAPI_OP_UPDATE
:
_
=
conn
.
query_server
(
OmapiMessage
.
delete
(
response
.
handle
))
conn
.
close
()
@
staticmethod
def
lease_clean
():
"""Clean the lease file
"""
# TODO : use ConfigFile structure
leasefile
=
open
(
dhcp_config
.
dhcplease
)
newleasefile
=
open
(
dhcp_config
.
dhcplease
+
'.new'
,
'w'
)
line
=
leasefile
.
readline
()
write
=
True
while
line
:
if
line
.
strip
().
startswith
(
'host'
):
write
=
False
if
write
:
newleasefile
.
write
(
line
)
if
not
write
and
line
.
strip
().
endswith
(
'}'
):
write
=
True
line
=
leasefile
.
readline
()
leasefile
.
close
()
newleasefile
.
close
()
os
.
rename
(
dhcp_config
.
dhcplease
+
'.new'
,
dhcp_config
.
dhcplease
)
def
add_dhcp_host
(
mac
,
ip
,
name
=
None
):
"""Adds a dhcp host using omapi
"""
if
'<automatique>'
in
[
ip
,
mac
]:
return
msg
=
OmapiMessage
.
open
(
b
"host"
)
msg
.
message
.
append
((
b
"create"
,
struct
.
pack
(
"!I"
,
1
)))
msg
.
message
.
append
((
b
"exclusive"
,
struct
.
pack
(
"!I"
,
1
)))
msg
.
obj
.
append
((
b
"hardware-address"
,
pack_mac
(
mac
)))
msg
.
obj
.
append
((
b
"hardware-type"
,
struct
.
pack
(
"!I"
,
1
)))
msg
.
obj
.
append
((
b
"ip-address"
,
pack_ip
(
ip
)))
if
name
:
msg
.
obj
.
append
((
b
"name"
,
bytes
(
name
)))
conn
=
Omapi
(
hostname_adm
,
9991
,
dhcp_omapi_keyname
,
dhcp_omapi_key
)
_
=
conn
.
query_server
(
msg
)
conn
.
close
()
def
delete_dhcp_host
(
mac
,
ip
):
"""Deletes dhcp host using omapi
"""
if
'<automatique>'
in
[
ip
,
mac
]:
return
msg
=
OmapiMessage
.
open
(
b
"host"
)
msg
.
obj
.
append
((
b
"hardware-address"
,
pack_mac
(
mac
)))
msg
.
obj
.
append
((
b
"hardware-type"
,
struct
.
pack
(
"!I"
,
1
)))
msg
.
obj
.
append
((
b
"ip-address"
,
pack_ip
(
ip
)))
conn
=
Omapi
(
hostname_adm
,
9991
,
dhcp_omapi_keyname
,
dhcp_omapi_key
)
response
=
conn
.
query_server
(
msg
)
if
response
.
opcode
==
OMAPI_OP_UPDATE
:
_
=
conn
.
query_server
(
OmapiMessage
.
delete
(
response
.
handle
))
conn
.
close
()
def
lease_clean
():
"""Clean the lease file
"""
# TODO : use ConfigFile structure
leasefile
=
open
(
dhcp_config
.
dhcplease
)
newleasefile
=
open
(
dhcp_config
.
dhcplease
+
'.new'
,
'w'
)
line
=
leasefile
.
readline
()
write
=
True
while
line
:
if
line
.
strip
().
startswith
(
'host'
):
write
=
False
if
write
:
newleasefile
.
write
(
line
)
if
not
write
and
line
.
strip
().
endswith
(
'}'
):
write
=
True
line
=
leasefile
.
readline
()
leasefile
.
close
()
newleasefile
.
close
()
os
.
rename
(
dhcp_config
.
dhcplease
+
'.new'
,
dhcp_config
.
dhcplease
)
gestion/trigger/services/event.py
View file @
51937a9a
...
...
@@ -21,10 +21,10 @@ import itertools
import
traceback
import
gestion.secrets_new
as
secrets
# Trigger features
import
gestion.config.trigger
as
trigger_config
from
gestion.trigger.host
import
TriggerFactory
from
gestion.trigger.services.service
import
BasicService
from
gestion.trigger.host
import
TriggerFactory
,
record_service
,
record_parser
# Clogger
import
cranslib.clogger
as
clogger
...
...
@@ -32,7 +32,7 @@ import cranslib.clogger as clogger
# lc_ldap
import
lc_ldap.attributs
logger
=
clogger
.
CLogger
(
"trigger"
,
"event"
,
"debug"
,
trigger_config
.
debug
)
logger
=
clogger
.
CLogger
(
"trigger"
,
"event"
,
trigger_config
.
log_level
,
trigger_config
.
debug
)
services
=
[]
for
config_service
in
trigger_config
.
all_services
:
...
...
@@ -136,63 +136,52 @@ def compare_lists(list1, list2):
return
moins
,
plus
class
Event
(
BasicService
):
"""Event service class. It extends BasicService, but should not implement
any change trigger, since it's this service which is designed to call
change triggers of other services.
"""
@
classmethod
def
get_changes
(
cls
,
body
,
diff
):
"""Compute changes from diff"""
return
[
None
]
@
record_service
def
event
(
body
=
()):
"""When any event arrives on trigger-civet-event, this method is called
and designed to transcript the body (ldap data) in something usable for
the services. Afterwards, it sends these transcripts on the good way
using routing_key.
@
classmethod
def
regen
(
cls
,
body
=
()):
"""When any event arrives on trigger-civet-event, this method is called
and designed to transcript the body (ldap data) in something usable for
the services. Afterwards, it sends these transcripts on the good way
using routing_key.
body is a 3-tuple, containing LDAP dn, the former state of the object
(a simple dict), and the later state. The data are non-binding-dependant.
body is a 3-tuple, containing LDAP dn, the former state of the object
(a simple dict), and the later state. The data are non-binding-dependant.
A new object has body[1] to None, a deleted one has body[2] to None.
A new object has body[1] to None, a deleted one has body[2] to None.
"""
"""
logger
.
info
(
"Received message %r…"
,
body
)
diff
=
diff_o_matic
(
body
)
# Now, diff is a dict containing attributes which has been modified.
# diff['macAddress'] could look like (['aa:bb:cc:dd:ee:fg'], ['aa:bb:cc:dd:ee:ff']),
# where the list on the left is the former value of attributes, and the list on the
# right the latter values.
# -*- Explain -*-
#In [11]: import itertools
#
#In [12]: a = [[(3, 'lol'), ('7', 3)], [(5, 6), None], [None], [('lol', 'lal')]]
#
#In [13]: a
#Out[13]: [[(3, 'lol'), ('7', 3)], [(5, 6), None], [None], [('lol', 'lal')]]
#
#In [14]: list(set([message for message in itertools.chain(*a)]))
#Out[14]: [('7', 3), (5, 6), None, ('lol', 'lal'), (3, 'lol')] # Only one None from a, since [None, x, y, None] is equivalent for itertools to [x, y]
#
#In [15]: b = list(set([message for message in itertools.chain(*a) if message is not None]))
#
#In [16]: b
#Out[16]: [('7', 3), (5, 6), ('lol', 'lal'), (3, 'lol')]
msg_to_send
=
[
message
for
message
in
itertools
.
chain
(
*
[
service
.
get_changes
(
body
,
diff
)
for
service
in
TriggerFactory
.
get_services
()])
if
message
is
not
None
]
for
msg
in
msg_to_send
:
logger
.
info
(
"Sending %r on the road
\\
o/"
,
msg
)
# XXX - uncomment this when in production
# trigger_send(*msg)
logger
.
info
(
"Received message %r…"
,
body
)
diff
=
diff_o_matic
(
body
)
# Now, diff is a dict containing attributes which has been modified.
# diff['macAddress'] could look like (['aa:bb:cc:dd:ee:fg'], ['aa:bb:cc:dd:ee:ff']),
# where the list on the left is the former value of attributes, and the list on the
# right the latter values.
# -*- Explain -*-
#In [11]: import itertools
#
#In [12]: a = [[(3, 'lol'), ('7', 3)], [(5, 6), None], [None], [('lol', 'lal')]]
#
#In [13]: a
#Out[13]: [[(3, 'lol'), ('7', 3)], [(5, 6), None], [None], [('lol', 'lal')]]
#
#In [14]: list(set([message for message in itertools.chain(*a)]))
#Out[14]: [('7', 3), (5, 6), None, ('lol', 'lal'), (3, 'lol')] # Only one None from a, since [None, x, y, None] is equivalent for itertools to [x, y]
#
#In [15]: b = list(set([message for message in itertools.chain(*a) if message is not None]))
#
#In [16]: b
#Out[16]: [('7', 3), (5, 6), ('lol', 'lal'), (3, 'lol')]
functions
=
list
(
set
([
function
for
function
in
itertools
.
chain
(
*
[
TriggerFactory
.
get_parser
(
key
)
for
key
in
diff
])]))
msg_to_send
=
[
function
(
body
,
diff
)
for
function
in
functions
]
for
msg
in
msg_to_send
:
logger
.
info
(
"Sending %r on the road
\\
o/"
,
msg
)
# XXX - uncomment this when in production
trigger_send
(
*
msg
)
def
trigger_send
(
routing_key
,
body
):
sender
=
EventProducer
(
"civet"
)
...
...
gestion/trigger/services/firewall.py
View file @
51937a9a
...
...
@@ -16,67 +16,75 @@ it to regenerate what needs to.
import
cranslib.clogger
as
clogger
import
gestion.config.trigger
as
trigger_config
logger
=
clogger
.
CLogger
(
"trigger"
,
"firewall"
,
"debug"
,
trigger_config
.
debug
)
logger
=
clogger
.
CLogger
(
"trigger"
,
"firewall"
,
trigger_config
.
log_level
,
trigger_config
.
debug
)
import
lc_ldap.shortcuts
from
gestion.trigger.
services.service
import
BasicService
from
gestion.trigger.
host
import
record_service
,
record_parser
import
gestion.trigger.firewall4.firewall4
as
firewall4
class
F
irewall
(
BasicService
):
"""
Firewall service that handles any modification in the firewall
.
class
F
wFactory
(
object
):
"""
Records firewall functions, and provide them
.
"""
# Class lookup table to define which changes call which function.
changes_trigger
=
{
lc_ldap
.
attributs
.
macAddress
.
ldap_name
:
(
'send_mac_ip'
,),
lc_ldap
.
attributs
.
ipHostNumber
.
ldap_name
:
(
'send_mac_ip'
,),
}