From ac36b5e18db16595c22cb43dfe673de77f2adb98 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 18 Jan 2012 13:31:22 +0100 Subject: [PATCH 01/98] template for new type that starts stuff on boot Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/explorer/cksum | 34 ++++++++++ conf/type/__start_on_boot/explorer/exists | 30 +++++++++ conf/type/__start_on_boot/gencode-local | 43 ++++++++++++ conf/type/__start_on_boot/gencode-remote | 66 +++++++++++++++++++ conf/type/__start_on_boot/man.text | 69 ++++++++++++++++++++ conf/type/__start_on_boot/manifest | 24 +++++++ conf/type/__start_on_boot/parameter/optional | 5 ++ 7 files changed, 271 insertions(+) create mode 100755 conf/type/__start_on_boot/explorer/cksum create mode 100755 conf/type/__start_on_boot/explorer/exists create mode 100755 conf/type/__start_on_boot/gencode-local create mode 100755 conf/type/__start_on_boot/gencode-remote create mode 100644 conf/type/__start_on_boot/man.text create mode 100755 conf/type/__start_on_boot/manifest create mode 100644 conf/type/__start_on_boot/parameter/optional diff --git a/conf/type/__start_on_boot/explorer/cksum b/conf/type/__start_on_boot/explorer/cksum new file mode 100755 index 00000000..dcad99ba --- /dev/null +++ b/conf/type/__start_on_boot/explorer/cksum @@ -0,0 +1,34 @@ +#!/bin/sh +# +# 2011 Nico Schottelius (nico-cdist at schottelius.org) +# +# This file is part of cdist. +# +# cdist is free software: you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# cdist is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with cdist. If not, see . +# +# +# Retrieve the md5sum of a file to be created, if it is already existing. +# + +destination="/$__object_id" + +if [ -e "$destination" ]; then + if [ -f "$destination" ]; then + cksum < "$destination" + else + echo "NO REGULAR FILE" + fi +else + echo "NO FILE FOUND, NO CHECKSUM CALCULATED." +fi diff --git a/conf/type/__start_on_boot/explorer/exists b/conf/type/__start_on_boot/explorer/exists new file mode 100755 index 00000000..f8b85671 --- /dev/null +++ b/conf/type/__start_on_boot/explorer/exists @@ -0,0 +1,30 @@ +#!/bin/sh +# +# 2011 Nico Schottelius (nico-cdist at schottelius.org) +# +# This file is part of cdist. +# +# cdist is free software: you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# cdist is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with cdist. If not, see . +# +# +# Check whether file exists or not +# + +destination="/$__object_id" + +if [ -e "$destination" ]; then + echo yes +else + echo no +fi diff --git a/conf/type/__start_on_boot/gencode-local b/conf/type/__start_on_boot/gencode-local new file mode 100755 index 00000000..d9839a19 --- /dev/null +++ b/conf/type/__start_on_boot/gencode-local @@ -0,0 +1,43 @@ +#!/bin/sh +# +# 2011 Nico Schottelius (nico-cdist at schottelius.org) +# +# This file is part of cdist. +# +# cdist is free software: you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# cdist is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with cdist. If not, see . +# +# +# __file is a very basic type, which will probably be reused quite often +# + +destination="/$__object_id" +state_should="$(cat "$__object/parameter/state")" + +if [ "$state_should" = "present" ]; then + if [ -f "$__object/parameter/source" ]; then + source="$(cat "$__object/parameter/source")" + + if [ -f "$source" ]; then + local_cksum="$(cksum < "$source")" + remote_cksum="$(cat "$__object/explorer/cksum")" + + if [ "$local_cksum" != "$remote_cksum" ]; then + echo "$__remote_copy" "$source" "${__target_host}:${destination}" + fi + else + echo "Source \"$source\" does not exist." >&2 + exit 1 + fi + fi +fi diff --git a/conf/type/__start_on_boot/gencode-remote b/conf/type/__start_on_boot/gencode-remote new file mode 100755 index 00000000..9e700934 --- /dev/null +++ b/conf/type/__start_on_boot/gencode-remote @@ -0,0 +1,66 @@ +#!/bin/sh +# +# 2011 Nico Schottelius (nico-cdist at schottelius.org) +# +# This file is part of cdist. +# +# cdist is free software: you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# cdist is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with cdist. If not, see . +# +# +# __file is a very basic type, which will probably be reused quite often +# + +destination="/$__object_id" +state_should="$(cat "$__object/parameter/state")" +exists="$(cat "$__object/explorer/exists")" + +case "$state_should" in + present) + # No source? Create empty file + if [ ! -f "$__object/parameter/source" ]; then + if [ "$exists" = "no" ]; then + echo touch \"$destination\" + fi + fi + + # Mode settings + if [ -f "$__object/parameter/mode" ]; then + echo chmod \"$(cat "$__object/parameter/mode")\" \"$destination\" + fi + + # Group + if [ -f "$__object/parameter/group" ]; then + echo chgrp \"$(cat "$__object/parameter/group")\" \"$destination\" + fi + + # Owner + if [ -f "$__object/parameter/owner" ]; then + echo chown \"$(cat "$__object/parameter/owner")\" \"$destination\" + fi + ;; + + absent) + + if [ "$exists" = "yes" ]; then + echo rm -f \"$destination\" + fi + + ;; + + *) + echo "Unknown state: $state_should" >&2 + exit 1 + ;; + +esac diff --git a/conf/type/__start_on_boot/man.text b/conf/type/__start_on_boot/man.text new file mode 100644 index 00000000..5e91599f --- /dev/null +++ b/conf/type/__start_on_boot/man.text @@ -0,0 +1,69 @@ +cdist-type__file(7) +=================== +Nico Schottelius + + +NAME +---- +cdist-type__file - Manage files + + +DESCRIPTION +----------- +This cdist type allows you to create files, remove files and set file +attributes on the target. + + +REQUIRED PARAMETERS +------------------- +None. + +OPTIONAL PARAMETERS +------------------- +state:: + 'present' or 'absent', defaults to 'present' + +group:: + Group to chgrp to. + +mode:: + Unix permissions, suitable for chmod. + +owner:: + User to chown to. + +source:: + If supplied, copy this file from the host running cdist to the target. + If not supplied, an empty file or directory will be created. + + +EXAMPLES +-------- + +-------------------------------------------------------------------------------- +# Create /etc/cdist-configured as an empty file +__file /etc/cdist-configured +# The same thing +__file /etc/cdist-configured --state present +# Delete existing file +__file /etc/cdist-configured --state absent + +# Use __file from another type +__file /etc/issue --source "$__type/files/archlinux" --state present + +# Supply some more settings +__file /etc/shadow --source "$__type/files/shadow" \ + --owner root --group shadow --mode 0640 \ + --state present +-------------------------------------------------------------------------------- + + +SEE ALSO +-------- +- cdist-type(7) + + +COPYING +------- +Copyright \(C) 2011-2012 Nico Schottelius. Free use of this software is +granted under the terms of the GNU General Public License version 3 (GPLv3). diff --git a/conf/type/__start_on_boot/manifest b/conf/type/__start_on_boot/manifest new file mode 100755 index 00000000..6b5e1ca7 --- /dev/null +++ b/conf/type/__start_on_boot/manifest @@ -0,0 +1,24 @@ +#!/bin/sh +# +# 2011 Steven Armstrong (steven-cdist at armstrong.cc) +# 2012 Nico Schottelius (nico-cdist at schottelius.org) +# +# This file is part of cdist. +# +# cdist is free software: you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# cdist is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with cdist. If not, see . +# + +# set default: present, if not setup +statefile="$__object/parameter/state" +[ -f "$statefile" ] || echo present > "$statefile" diff --git a/conf/type/__start_on_boot/parameter/optional b/conf/type/__start_on_boot/parameter/optional new file mode 100644 index 00000000..c696d592 --- /dev/null +++ b/conf/type/__start_on_boot/parameter/optional @@ -0,0 +1,5 @@ +state +group +mode +owner +source From c567ade17a2072d502613a059e99ce7e812faf6e Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 18 Jan 2012 14:42:36 +0100 Subject: [PATCH 02/98] add manpage for __start_on_boot Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/man.text | 43 +++++++++--------------------- 1 file changed, 12 insertions(+), 31 deletions(-) diff --git a/conf/type/__start_on_boot/man.text b/conf/type/__start_on_boot/man.text index 5e91599f..e9691401 100644 --- a/conf/type/__start_on_boot/man.text +++ b/conf/type/__start_on_boot/man.text @@ -1,17 +1,17 @@ -cdist-type__file(7) -=================== +cdist-type__start_on_boot(7) +============================ Nico Schottelius NAME ---- -cdist-type__file - Manage files +cdist-type__start_on_boot - Manage stuff to be started at boot DESCRIPTION ----------- -This cdist type allows you to create files, remove files and set file -attributes on the target. +This cdist type allows you to enable or disable stuff to be started +at boot of your operating system. REQUIRED PARAMETERS @@ -23,38 +23,19 @@ OPTIONAL PARAMETERS state:: 'present' or 'absent', defaults to 'present' -group:: - Group to chgrp to. - -mode:: - Unix permissions, suitable for chmod. - -owner:: - User to chown to. - -source:: - If supplied, copy this file from the host running cdist to the target. - If not supplied, an empty file or directory will be created. - EXAMPLES -------- -------------------------------------------------------------------------------- -# Create /etc/cdist-configured as an empty file -__file /etc/cdist-configured -# The same thing -__file /etc/cdist-configured --state present -# Delete existing file -__file /etc/cdist-configured --state absent +# Ensure snmpd is started at boot +__start_on_boot snmpd -# Use __file from another type -__file /etc/issue --source "$__type/files/archlinux" --state present +# Same, but more explicit +__start_on_boot snmpd --state present -# Supply some more settings -__file /etc/shadow --source "$__type/files/shadow" \ - --owner root --group shadow --mode 0640 \ - --state present +# Ensure legacy configuration management will not be started +__start_on_boot puppet --state absent -------------------------------------------------------------------------------- @@ -65,5 +46,5 @@ SEE ALSO COPYING ------- -Copyright \(C) 2011-2012 Nico Schottelius. Free use of this software is +Copyright \(C) 2012 Nico Schottelius. Free use of this software is granted under the terms of the GNU General Public License version 3 (GPLv3). From aea107079899f2c76ca0f0aa7a9a62f278f4a9e7 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 18 Jan 2012 14:50:50 +0100 Subject: [PATCH 03/98] add global explorer runlevel Signed-off-by: Nico Schottelius --- conf/explorer/runlevel | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+) create mode 100755 conf/explorer/runlevel diff --git a/conf/explorer/runlevel b/conf/explorer/runlevel new file mode 100755 index 00000000..7cdd81ef --- /dev/null +++ b/conf/explorer/runlevel @@ -0,0 +1,26 @@ +#!/bin/sh +# +# 2012 Nico Schottelius (nico-cdist at schottelius.org) +# +# This file is part of cdist. +# +# cdist is free software: you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# cdist is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with cdist. If not, see . +# +# + +set +e +executable=$(which runlevel 2>/dev/null) +if [ -x "$executable" ]; then + "$executable" | awk '{ print $2 }' +fi From 14127446191d92ed343145a50dc04c9e66507c20 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 18 Jan 2012 15:52:19 +0100 Subject: [PATCH 04/98] begin state explorer Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/explorer/exists | 30 ---------------- .../__start_on_boot/explorer/{cksum => state} | 34 ++++++++++++------- 2 files changed, 22 insertions(+), 42 deletions(-) delete mode 100755 conf/type/__start_on_boot/explorer/exists rename conf/type/__start_on_boot/explorer/{cksum => state} (59%) diff --git a/conf/type/__start_on_boot/explorer/exists b/conf/type/__start_on_boot/explorer/exists deleted file mode 100755 index f8b85671..00000000 --- a/conf/type/__start_on_boot/explorer/exists +++ /dev/null @@ -1,30 +0,0 @@ -#!/bin/sh -# -# 2011 Nico Schottelius (nico-cdist at schottelius.org) -# -# This file is part of cdist. -# -# cdist is free software: you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation, either version 3 of the License, or -# (at your option) any later version. -# -# cdist is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with cdist. If not, see . -# -# -# Check whether file exists or not -# - -destination="/$__object_id" - -if [ -e "$destination" ]; then - echo yes -else - echo no -fi diff --git a/conf/type/__start_on_boot/explorer/cksum b/conf/type/__start_on_boot/explorer/state similarity index 59% rename from conf/type/__start_on_boot/explorer/cksum rename to conf/type/__start_on_boot/explorer/state index dcad99ba..c68ec2ba 100755 --- a/conf/type/__start_on_boot/explorer/cksum +++ b/conf/type/__start_on_boot/explorer/state @@ -1,6 +1,6 @@ #!/bin/sh # -# 2011 Nico Schottelius (nico-cdist at schottelius.org) +# 2012 Nico Schottelius (nico-cdist at schottelius.org) # # This file is part of cdist. # @@ -18,17 +18,27 @@ # along with cdist. If not, see . # # -# Retrieve the md5sum of a file to be created, if it is already existing. +# Check whether the given name will be started on boot or not # -destination="/$__object_id" +os=$(cat "$__global/explorer/os") + +case "$os" in + debian|ubuntu) + echo update-rc.d \"$name\" defaults + ;; + + gentoo) + echo rc-update add \"$name\" default + ;; + + centos|fedora|owl|redhat) + echo chkconfig \"$name\" on + ;; + + *) + echo "Unsupported os: $os" >&2 + exit 1 + ;; +esac -if [ -e "$destination" ]; then - if [ -f "$destination" ]; then - cksum < "$destination" - else - echo "NO REGULAR FILE" - fi -else - echo "NO FILE FOUND, NO CHECKSUM CALCULATED." -fi From 6b6ae1bde225765051f7be1972c2fd463f789b48 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 18 Jan 2012 15:52:47 +0100 Subject: [PATCH 05/98] document more exported environment variables Signed-off-by: Nico Schottelius --- doc/man/cdist-reference.text.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/doc/man/cdist-reference.text.sh b/doc/man/cdist-reference.text.sh index 6b4e786f..ffc40ee3 100755 --- a/doc/man/cdist-reference.text.sh +++ b/doc/man/cdist-reference.text.sh @@ -167,7 +167,7 @@ ENVIRONMENT VARIABLES --------------------- __explorer:: Directory that contains all global explorers. - Available for: explorer + Available for: explorer, type explorer __manifest:: Directory that contains the initial manifest. Available for: initial manifest @@ -188,7 +188,7 @@ __object_name:: Available for: type manifest, type explorer, type gencode __target_host:: The host we are deploying to. - Available for: initial manifest, type manifest, type gencode + Available for: explorer, initial manifest, type explorer, type manifest, type gencode __type:: Path to the current type. Available for: type manifest, type gencode From 42e3c18d02823a47423ac194ef884a57fd741aa2 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 18 Jan 2012 15:54:32 +0100 Subject: [PATCH 06/98] +update of __start_on_boot Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/explorer/state | 2 +- conf/type/__start_on_boot/gencode-remote | 71 ++++++++++++------------ conf/type/__start_on_boot/man.text | 3 + 3 files changed, 39 insertions(+), 37 deletions(-) diff --git a/conf/type/__start_on_boot/explorer/state b/conf/type/__start_on_boot/explorer/state index c68ec2ba..136c1e05 100755 --- a/conf/type/__start_on_boot/explorer/state +++ b/conf/type/__start_on_boot/explorer/state @@ -21,7 +21,7 @@ # Check whether the given name will be started on boot or not # -os=$(cat "$__global/explorer/os") +os=$("$__explorer/os") case "$os" in debian|ubuntu) diff --git a/conf/type/__start_on_boot/gencode-remote b/conf/type/__start_on_boot/gencode-remote index 9e700934..5133810d 100755 --- a/conf/type/__start_on_boot/gencode-remote +++ b/conf/type/__start_on_boot/gencode-remote @@ -1,6 +1,6 @@ #!/bin/sh # -# 2011 Nico Schottelius (nico-cdist at schottelius.org) +# 2012 Nico Schottelius (nico-cdist at schottelius.org) # # This file is part of cdist. # @@ -18,49 +18,48 @@ # along with cdist. If not, see . # # -# __file is a very basic type, which will probably be reused quite often -# -destination="/$__object_id" -state_should="$(cat "$__object/parameter/state")" -exists="$(cat "$__object/explorer/exists")" +if [ -f "$__object/parameter/state" ]; then + state_should="$(cat "$__object/parameter/state")" +else + state_should="present" +fi + +os=$(cat "$__global/explorer/os") +name="$__object_id" + +# Support runlevels later +#runlevel=$(cat $__global/explorer/runlevel) case "$state_should" in - present) - # No source? Create empty file - if [ ! -f "$__object/parameter/source" ]; then - if [ "$exists" = "no" ]; then - echo touch \"$destination\" - fi - fi + present) + case "$os" in + debian|ubuntu) + echo update-rc.d \"$name\" defaults + ;; - # Mode settings - if [ -f "$__object/parameter/mode" ]; then - echo chmod \"$(cat "$__object/parameter/mode")\" \"$destination\" - fi + gentoo) + echo rc-update add \"$name\" default + ;; - # Group - if [ -f "$__object/parameter/group" ]; then - echo chgrp \"$(cat "$__object/parameter/group")\" \"$destination\" - fi + centos|fedora|owl|redhat) + echo echo chkconfig \"$name\" on + ;; - # Owner - if [ -f "$__object/parameter/owner" ]; then - echo chown \"$(cat "$__object/parameter/owner")\" \"$destination\" - fi - ;; + *) + echo "Unsupported os: $os" >&2 + exit 1 + ;; + esac + ;; - absent) + absent) - if [ "$exists" = "yes" ]; then - echo rm -f \"$destination\" - fi + ;; - ;; - - *) - echo "Unknown state: $state_should" >&2 - exit 1 - ;; + *) + echo "Unknown state: $state_should" >&2 + exit 1 + ;; esac diff --git a/conf/type/__start_on_boot/man.text b/conf/type/__start_on_boot/man.text index e9691401..eb9dbe7f 100644 --- a/conf/type/__start_on_boot/man.text +++ b/conf/type/__start_on_boot/man.text @@ -23,6 +23,9 @@ OPTIONAL PARAMETERS state:: 'present' or 'absent', defaults to 'present' +runlevel:: + Specify runlevel(s) to affect. Defaults to default or current runlevel. + EXAMPLES -------- From 1e9940ae53b3b517b4e90896ee8fac2a722e3162 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 18 Jan 2012 15:54:50 +0100 Subject: [PATCH 07/98] ++fixme of logging Signed-off-by: Nico Schottelius --- lib/cdist/core/explorer.py | 1 + 1 file changed, 1 insertion(+) diff --git a/lib/cdist/core/explorer.py b/lib/cdist/core/explorer.py index 01c4c81d..19833d92 100644 --- a/lib/cdist/core/explorer.py +++ b/lib/cdist/core/explorer.py @@ -73,6 +73,7 @@ class Explorer(object): '__target_host': self.target_host, '__explorer': self.remote.global_explorer_path, } + # FIXME: remove soon with new logging infrastructure if self.log.getEffectiveLevel() == logging.DEBUG: self.env.update({'__debug': "yes" }) self._type_explorers_transferred = [] From 5a383fcbad5c99e0c16dd365c0b94ca85cf9585f Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 18 Jan 2012 15:54:58 +0100 Subject: [PATCH 08/98] ++todo for nico Signed-off-by: Nico Schottelius --- doc/dev/todo/TAKEME | 3 --- doc/dev/todo/niconext | 6 +++++- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/doc/dev/todo/TAKEME b/doc/dev/todo/TAKEME index 875d2970..56bb8284 100644 --- a/doc/dev/todo/TAKEME +++ b/doc/dev/todo/TAKEME @@ -37,6 +37,3 @@ TYPES ------ - __user add option to include --create-home -- __init_script? - to enable/disable startup of init stuff - http://linuxhelp.blogspot.com/2006/04/enabling-and-disabling-services-during_01.html diff --git a/doc/dev/todo/niconext b/doc/dev/todo/niconext index ad859266..4543b32a 100644 --- a/doc/dev/todo/niconext +++ b/doc/dev/todo/niconext @@ -1,4 +1,9 @@ +- __init_script? + to enable/disable startup of init stuff + http://linuxhelp.blogspot.com/2006/04/enabling-and-disabling-services-during_01.html + - update/create docs + - document __remote_copy and __remote_exec - cdist-cache:: How to get use information about the hosts we have been working on [advanced] - cdist-scaling-tuning:: @@ -12,4 +17,3 @@ - exec flag is not true for manifest anymore - SSH HINTS - ssh agent - From 0ccf000713dc196686a80256fd543a15b499ce56 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 18 Jan 2012 15:55:06 +0100 Subject: [PATCH 09/98] more stuff for 2.0.6 Signed-off-by: Nico Schottelius --- doc/changelog | 2 ++ 1 file changed, 2 insertions(+) diff --git a/doc/changelog b/doc/changelog index 062db392..5867d54d 100644 --- a/doc/changelog +++ b/doc/changelog @@ -7,6 +7,8 @@ * New Type: __rvm_gem (Evax Software) * New Type: __rvm_gemset (Evax Software) * New Type: __rvm_ruby (Evax Software) + * New Explorer: runlevel + * Documentation: Update of reference (environment variables) 2.0.5: 2012-01-18 * Bugfix __key_value: Use correct delimiters From fe0fae69023eca7561c6c01831b97f6e50a8e2c4 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 18 Jan 2012 16:07:33 +0100 Subject: [PATCH 10/98] update explorer and gencode and parameter Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/explorer/state | 5 ++- conf/type/__start_on_boot/gencode-local | 43 -------------------- conf/type/__start_on_boot/gencode-remote | 25 +++++++++++- conf/type/__start_on_boot/man.text | 1 + conf/type/__start_on_boot/parameter/optional | 4 -- 5 files changed, 29 insertions(+), 49 deletions(-) delete mode 100755 conf/type/__start_on_boot/gencode-local diff --git a/conf/type/__start_on_boot/explorer/state b/conf/type/__start_on_boot/explorer/state index 136c1e05..8db4b9d2 100755 --- a/conf/type/__start_on_boot/explorer/state +++ b/conf/type/__start_on_boot/explorer/state @@ -22,6 +22,7 @@ # os=$("$__explorer/os") +runlevel=$("$__explorer/runlevel") case "$os" in debian|ubuntu) @@ -33,7 +34,8 @@ case "$os" in ;; centos|fedora|owl|redhat) - echo chkconfig \"$name\" on + state=$(chkconfig --level "$runlevel" \"$name\" || echo absent) + [ "$state" ] || state="present" ;; *) @@ -42,3 +44,4 @@ case "$os" in ;; esac +echo $state diff --git a/conf/type/__start_on_boot/gencode-local b/conf/type/__start_on_boot/gencode-local deleted file mode 100755 index d9839a19..00000000 --- a/conf/type/__start_on_boot/gencode-local +++ /dev/null @@ -1,43 +0,0 @@ -#!/bin/sh -# -# 2011 Nico Schottelius (nico-cdist at schottelius.org) -# -# This file is part of cdist. -# -# cdist is free software: you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation, either version 3 of the License, or -# (at your option) any later version. -# -# cdist is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with cdist. If not, see . -# -# -# __file is a very basic type, which will probably be reused quite often -# - -destination="/$__object_id" -state_should="$(cat "$__object/parameter/state")" - -if [ "$state_should" = "present" ]; then - if [ -f "$__object/parameter/source" ]; then - source="$(cat "$__object/parameter/source")" - - if [ -f "$source" ]; then - local_cksum="$(cksum < "$source")" - remote_cksum="$(cat "$__object/explorer/cksum")" - - if [ "$local_cksum" != "$remote_cksum" ]; then - echo "$__remote_copy" "$source" "${__target_host}:${destination}" - fi - else - echo "Source \"$source\" does not exist." >&2 - exit 1 - fi - fi -fi diff --git a/conf/type/__start_on_boot/gencode-remote b/conf/type/__start_on_boot/gencode-remote index 5133810d..aa854658 100755 --- a/conf/type/__start_on_boot/gencode-remote +++ b/conf/type/__start_on_boot/gencode-remote @@ -25,6 +25,11 @@ else state_should="present" fi +state_is=$(cat "$__object/explorer/state") + +# Nothing todo, go away +[ "$state_should" = "$state_is" ] && exit 0 + os=$(cat "$__global/explorer/os") name="$__object_id" @@ -43,7 +48,7 @@ case "$state_should" in ;; centos|fedora|owl|redhat) - echo echo chkconfig \"$name\" on + echo chkconfig \"$name\" on ;; *) @@ -54,7 +59,25 @@ case "$state_should" in ;; absent) + case "$os" in + debian|ubuntu) + echo update-rc.d -f \"$name\" remove + ;; + gentoo) + echo rc-update del \"$name\" + ;; + + centos|fedora|owl|redhat) + echo chkconfig \"$name\" off + ;; + + *) + echo "Unsupported os: $os" >&2 + exit 1 + ;; + esac + ;; diff --git a/conf/type/__start_on_boot/man.text b/conf/type/__start_on_boot/man.text index eb9dbe7f..5614f16b 100644 --- a/conf/type/__start_on_boot/man.text +++ b/conf/type/__start_on_boot/man.text @@ -25,6 +25,7 @@ state:: runlevel:: Specify runlevel(s) to affect. Defaults to default or current runlevel. + NOT YET SUPPORTED, ALWAYS USING CURRENT RUNLEVEL. EXAMPLES diff --git a/conf/type/__start_on_boot/parameter/optional b/conf/type/__start_on_boot/parameter/optional index c696d592..ff72b5c7 100644 --- a/conf/type/__start_on_boot/parameter/optional +++ b/conf/type/__start_on_boot/parameter/optional @@ -1,5 +1 @@ state -group -mode -owner -source From 559670ab4f333b44831c29e18b70ab442275b8d9 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 18 Jan 2012 16:15:53 +0100 Subject: [PATCH 11/98] add debian / ubuntu support for checking state Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/explorer/state | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/conf/type/__start_on_boot/explorer/state b/conf/type/__start_on_boot/explorer/state index 8db4b9d2..2778e784 100755 --- a/conf/type/__start_on_boot/explorer/state +++ b/conf/type/__start_on_boot/explorer/state @@ -21,12 +21,19 @@ # Check whether the given name will be started on boot or not # +set -x +exec >&2 + os=$("$__explorer/os") runlevel=$("$__explorer/runlevel") +name="$__object_id" + +# default +state="present" case "$os" in debian|ubuntu) - echo update-rc.d \"$name\" defaults + [ -f "/etc/rc$runlevel.d/S"??"$name" ] || state="absent" ;; gentoo) @@ -45,3 +52,4 @@ case "$os" in esac echo $state +exit 1 From aa870e012441a0a570aae87c35d45a11552609fb Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 18 Jan 2012 16:37:09 +0100 Subject: [PATCH 12/98] remove debug, remove gentoo support until tested Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/explorer/state | 8 -------- conf/type/__start_on_boot/gencode-remote | 15 ++++++++------- 2 files changed, 8 insertions(+), 15 deletions(-) diff --git a/conf/type/__start_on_boot/explorer/state b/conf/type/__start_on_boot/explorer/state index 2778e784..9d63b84e 100755 --- a/conf/type/__start_on_boot/explorer/state +++ b/conf/type/__start_on_boot/explorer/state @@ -21,9 +21,6 @@ # Check whether the given name will be started on boot or not # -set -x -exec >&2 - os=$("$__explorer/os") runlevel=$("$__explorer/runlevel") name="$__object_id" @@ -36,10 +33,6 @@ case "$os" in [ -f "/etc/rc$runlevel.d/S"??"$name" ] || state="absent" ;; - gentoo) - echo rc-update add \"$name\" default - ;; - centos|fedora|owl|redhat) state=$(chkconfig --level "$runlevel" \"$name\" || echo absent) [ "$state" ] || state="present" @@ -52,4 +45,3 @@ case "$os" in esac echo $state -exit 1 diff --git a/conf/type/__start_on_boot/gencode-remote b/conf/type/__start_on_boot/gencode-remote index aa854658..ee2bdeb6 100755 --- a/conf/type/__start_on_boot/gencode-remote +++ b/conf/type/__start_on_boot/gencode-remote @@ -43,9 +43,10 @@ case "$state_should" in echo update-rc.d \"$name\" defaults ;; - gentoo) - echo rc-update add \"$name\" default - ;; +# Disabled until the explorer is checked +# gentoo) +# echo rc-update add \"$name\" default +# ;; centos|fedora|owl|redhat) echo chkconfig \"$name\" on @@ -64,9 +65,10 @@ case "$state_should" in echo update-rc.d -f \"$name\" remove ;; - gentoo) - echo rc-update del \"$name\" - ;; +# Disabled until the explorer is checked +# gentoo) +# echo rc-update del \"$name\" +# ;; centos|fedora|owl|redhat) echo chkconfig \"$name\" off @@ -80,7 +82,6 @@ case "$state_should" in ;; - *) echo "Unknown state: $state_should" >&2 exit 1 From a112b4f123d591096bede64ba96545e911204edd Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Thu, 19 Jan 2012 09:12:54 +0100 Subject: [PATCH 13/98] documet debian/ubuntu problem Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/gencode-remote | 3 +++ 1 file changed, 3 insertions(+) diff --git a/conf/type/__start_on_boot/gencode-remote b/conf/type/__start_on_boot/gencode-remote index ee2bdeb6..5e9c6343 100755 --- a/conf/type/__start_on_boot/gencode-remote +++ b/conf/type/__start_on_boot/gencode-remote @@ -40,6 +40,9 @@ case "$state_should" in present) case "$os" in debian|ubuntu) + # This does not work as expected: + # insserv: warning: current start runlevel(s) (3 4 5) of script `postfix' overwrites defaults (2 3 4 5). + #echo update-rc.d \"$name\" defaults echo update-rc.d \"$name\" defaults ;; From aae67652e9cdb79c019c7c405e2a97e0d8c32f90 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Fri, 20 Jan 2012 12:57:40 +0100 Subject: [PATCH 14/98] explore state of init script on archlinux Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/explorer/state | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) diff --git a/conf/type/__start_on_boot/explorer/state b/conf/type/__start_on_boot/explorer/state index 9d63b84e..1de1fe57 100755 --- a/conf/type/__start_on_boot/explorer/state +++ b/conf/type/__start_on_boot/explorer/state @@ -29,6 +29,23 @@ name="$__object_id" state="present" case "$os" in + archlinux) + # convert bash array to shell + daemons=$(grep ^DAEMONS /etc/rc.conf | sed -e 's/^.*=(//' -e 's/)$//') + + # absent, as long as not found + state="absent" + + # iterate, last one wins. + for daemon in $daemons; do + if [ "$daemon" = "$name" -o "$daemon" = "@${name}" ]; then + state="present" + elif [ "$daemon" = "!${name}" ]; then + state="absent" + fi + done + ;; + debian|ubuntu) [ -f "/etc/rc$runlevel.d/S"??"$name" ] || state="absent" ;; From bd32bd0953d3075b21586df15abee23f22eb99c7 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Fri, 20 Jan 2012 12:58:50 +0100 Subject: [PATCH 15/98] setup state in os specific sections to get better overview Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/explorer/state | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/conf/type/__start_on_boot/explorer/state b/conf/type/__start_on_boot/explorer/state index 1de1fe57..ff092a65 100755 --- a/conf/type/__start_on_boot/explorer/state +++ b/conf/type/__start_on_boot/explorer/state @@ -25,8 +25,6 @@ os=$("$__explorer/os") runlevel=$("$__explorer/runlevel") name="$__object_id" -# default -state="present" case "$os" in archlinux) @@ -44,21 +42,23 @@ case "$os" in state="absent" fi done - ;; + ;; debian|ubuntu) + state="present" [ -f "/etc/rc$runlevel.d/S"??"$name" ] || state="absent" - ;; + ;; centos|fedora|owl|redhat) + state="present" state=$(chkconfig --level "$runlevel" \"$name\" || echo absent) [ "$state" ] || state="present" - ;; + ;; *) echo "Unsupported os: $os" >&2 exit 1 - ;; + ;; esac echo $state From 4ea85fb40224da50eeb945fa0d1a366e846a0196 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Fri, 20 Jan 2012 13:12:14 +0100 Subject: [PATCH 16/98] ++todo (absent/present) Signed-off-by: Nico Schottelius --- doc/dev/todo/TAKEME | 2 ++ 1 file changed, 2 insertions(+) diff --git a/doc/dev/todo/TAKEME b/doc/dev/todo/TAKEME index 948aa1a5..abcd5097 100644 --- a/doc/dev/todo/TAKEME +++ b/doc/dev/todo/TAKEME @@ -36,3 +36,5 @@ TYPES ------ - __user add option to include --create-home +- ensure that all types, which support --state support + present and absent (consistent look and feel) From 6d5c69d5c423b2dcb049b11618b4f15216213161 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Fri, 20 Jan 2012 14:16:49 +0100 Subject: [PATCH 17/98] remove runlevel parameter for now - seems to be too complex/unecessary for the moment Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/man.text | 4 ---- 1 file changed, 4 deletions(-) diff --git a/conf/type/__start_on_boot/man.text b/conf/type/__start_on_boot/man.text index 5614f16b..e9691401 100644 --- a/conf/type/__start_on_boot/man.text +++ b/conf/type/__start_on_boot/man.text @@ -23,10 +23,6 @@ OPTIONAL PARAMETERS state:: 'present' or 'absent', defaults to 'present' -runlevel:: - Specify runlevel(s) to affect. Defaults to default or current runlevel. - NOT YET SUPPORTED, ALWAYS USING CURRENT RUNLEVEL. - EXAMPLES -------- From a357d7d794990d3123a36c6690ccf5ac8ed979fb Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Fri, 20 Jan 2012 14:57:25 +0100 Subject: [PATCH 18/98] support adding start on boot on archlinux (no removal so far) Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/gencode-remote | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/conf/type/__start_on_boot/gencode-remote b/conf/type/__start_on_boot/gencode-remote index 5e9c6343..c13013ad 100755 --- a/conf/type/__start_on_boot/gencode-remote +++ b/conf/type/__start_on_boot/gencode-remote @@ -33,12 +33,12 @@ state_is=$(cat "$__object/explorer/state") os=$(cat "$__global/explorer/os") name="$__object_id" -# Support runlevels later -#runlevel=$(cat $__global/explorer/runlevel) - case "$state_should" in present) case "$os" in + archlinux) + echo sed -i /etc/rc.conf \"s/^\\(DAEMONS=.*\\))/\\1 foo)/\" + ;; debian|ubuntu) # This does not work as expected: # insserv: warning: current start runlevel(s) (3 4 5) of script `postfix' overwrites defaults (2 3 4 5). From 6d14e32911c78130860718515115fe8a1ec248b1 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Fri, 20 Jan 2012 15:34:18 +0100 Subject: [PATCH 19/98] support removal and correct adding daemons on archlinux Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/gencode-remote | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/conf/type/__start_on_boot/gencode-remote b/conf/type/__start_on_boot/gencode-remote index c13013ad..61a6b465 100755 --- a/conf/type/__start_on_boot/gencode-remote +++ b/conf/type/__start_on_boot/gencode-remote @@ -37,7 +37,7 @@ case "$state_should" in present) case "$os" in archlinux) - echo sed -i /etc/rc.conf \"s/^\\(DAEMONS=.*\\))/\\1 foo)/\" + echo sed -i /etc/rc.conf \"s/^\\(DAEMONS=.*\\))/\\1 $name)/\" ;; debian|ubuntu) # This does not work as expected: @@ -64,6 +64,9 @@ case "$state_should" in absent) case "$os" in + archlinux) + echo sed -i /etc/rc.conf -e \"s/ $name / /g\" -e \"s/($name/(/\" -e \"s/ $name)/)/\" + ;; debian|ubuntu) echo update-rc.d -f \"$name\" remove ;; From 1b263b57cfde719eb8a8134555317201d1e8e0aa Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Fri, 20 Jan 2012 16:30:44 +0100 Subject: [PATCH 20/98] prefer ' over " Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/gencode-remote | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/conf/type/__start_on_boot/gencode-remote b/conf/type/__start_on_boot/gencode-remote index 61a6b465..09c4912d 100755 --- a/conf/type/__start_on_boot/gencode-remote +++ b/conf/type/__start_on_boot/gencode-remote @@ -37,7 +37,7 @@ case "$state_should" in present) case "$os" in archlinux) - echo sed -i /etc/rc.conf \"s/^\\(DAEMONS=.*\\))/\\1 $name)/\" + echo sed -i /etc/rc.conf \'s/^\\(DAEMONS=.*\\))/\\1 $name)/\' ;; debian|ubuntu) # This does not work as expected: From 85f7880c7ed4b86453e837bc781861ac0cd694e5 Mon Sep 17 00:00:00 2001 From: Steven Armstrong Date: Fri, 3 Feb 2012 20:50:17 +0100 Subject: [PATCH 21/98] add a hopefully more robust implementation for changing existing values Signed-off-by: Steven Armstrong --- conf/type/__key_value/gencode-remote | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/conf/type/__key_value/gencode-remote b/conf/type/__key_value/gencode-remote index eff0925c..08b3a0f3 100755 --- a/conf/type/__key_value/gencode-remote +++ b/conf/type/__key_value/gencode-remote @@ -40,10 +40,7 @@ DONE else # change value cat << DONE -awk -F "$delimiter" ' -/${key}${delimiter}*/{gsub("$value_is", "$value_should")};{print}' "$file" > "${file}+" \ -&& mv "${file}+" "$file" - +sed -i "s|^$key\($delimiter\+\).*|$key\1$value_should|" "$file" DONE fi ;; From 4628dad04576103945553609c9e46c71cee35de8 Mon Sep 17 00:00:00 2001 From: Steven Armstrong Date: Fri, 3 Feb 2012 20:55:24 +0100 Subject: [PATCH 22/98] cleaner way to set default values Signed-off-by: Steven Armstrong --- conf/type/__key_value/explorer/value | 8 +++----- conf/type/__key_value/manifest | 9 +++------ 2 files changed, 6 insertions(+), 11 deletions(-) diff --git a/conf/type/__key_value/explorer/value b/conf/type/__key_value/explorer/value index 3afc7cc5..b4e1fafd 100755 --- a/conf/type/__key_value/explorer/value +++ b/conf/type/__key_value/explorer/value @@ -21,11 +21,9 @@ # Get the current value of key or __NOTSET__ if the key doesn't exist. # -if [ -f "$__object/parameter/key" ]; then - key="$(cat "$__object/parameter/key")" -else - key="$__object_id" -fi +key="$(cat "$__object/parameter/key" 2>/dev/null \ + || echo "$__object_id")" + file="$(cat "$__object/parameter/file")" delimiter="$(cat "$__object/parameter/delimiter")" diff --git a/conf/type/__key_value/manifest b/conf/type/__key_value/manifest index 706b0b0d..84c06352 100755 --- a/conf/type/__key_value/manifest +++ b/conf/type/__key_value/manifest @@ -18,9 +18,6 @@ # along with cdist. If not, see . # -if [ -f "$__object/parameter/key" ]; then - key="$(cat "$__object/parameter/key")" -else - echo "$__object_id" > "$__object/parameter/key" -fi - +# set defaults +[ -f "$__object/parameter/key" ] \ + || echo "$__object_id" > "$__object/parameter/key" From cad2097d0559861f66a988c88c4022721fa8c033 Mon Sep 17 00:00:00 2001 From: Steven Armstrong Date: Fri, 3 Feb 2012 22:43:34 +0100 Subject: [PATCH 23/98] complete rewrite: use state explorer to determine current state, more robust implementation for adding, changing, removing key/values Signed-off-by: Steven Armstrong --- .../__key_value/explorer/{value => state} | 35 ++++++++---- conf/type/__key_value/gencode-remote | 54 +++++++++++-------- conf/type/__key_value/man.text | 11 ++-- conf/type/__key_value/manifest | 11 +++- conf/type/__key_value/parameter/optional | 2 + conf/type/__key_value/parameter/required | 1 - 6 files changed, 75 insertions(+), 39 deletions(-) rename conf/type/__key_value/explorer/{value => state} (54%) diff --git a/conf/type/__key_value/explorer/value b/conf/type/__key_value/explorer/state similarity index 54% rename from conf/type/__key_value/explorer/value rename to conf/type/__key_value/explorer/state index b4e1fafd..7e66cb69 100755 --- a/conf/type/__key_value/explorer/value +++ b/conf/type/__key_value/explorer/state @@ -17,19 +17,34 @@ # You should have received a copy of the GNU General Public License # along with cdist. If not, see . # -# -# Get the current value of key or __NOTSET__ if the key doesn't exist. -# key="$(cat "$__object/parameter/key" 2>/dev/null \ || echo "$__object_id")" - +state="$(cat "$__object/parameter/state" 2>/dev/null \ + || echo "present")" file="$(cat "$__object/parameter/file")" delimiter="$(cat "$__object/parameter/delimiter")" +value="$(cat "$__object/parameter/value" 2>/dev/null \ + || echo "__CDIST_NOTSET__")" -awk -F "$delimiter" ' -BEGIN { found=0 } -/^'$key'/ { print $2; found=1 } -END { if (found) exit 0; else exit 1 }' "$file" \ -|| echo "__NOTSET__" - +case "$state" in + absent) + # if the key exists, with whatever value, we will have to remove it + # so report it as present + if egrep -q "^$key$delimiter+" "$file"; then + echo present + fi + ;; + present) + if egrep -q "^$key$delimiter+$value$" "$file"; then + # key exists and value is same + echo present + elif egrep -q "^$key$delimiter+" "$file"; then + # key exists, but value is empty or different + echo wrongvalue + else + # key does not exist + echo absent + fi + ;; +esac diff --git a/conf/type/__key_value/gencode-remote b/conf/type/__key_value/gencode-remote index 08b3a0f3..0846dca1 100755 --- a/conf/type/__key_value/gencode-remote +++ b/conf/type/__key_value/gencode-remote @@ -18,32 +18,40 @@ # along with cdist. If not, see . # -value_is="$(cat "$__object/explorer/value")" -value_should="$(cat "$__object/parameter/value")" - key="$(cat "$__object/parameter/key")" file="$(cat "$__object/parameter/file")" delimiter="$(cat "$__object/parameter/delimiter")" +value="$(cat "$__object/parameter/value")" -if [ "$value_is" != "$value_should" ]; then - case "$value_is" in - __NOTSET__) - # add key and value - echo "echo \"${key}${delimiter}${value_should}\" >> \"$file\"" - ;; - *) - if [ "$value_should" = '__NOTSET__' ]; then - # remove key and value - cat << DONE -sed -i '/^${key}/d' "$file" -DONE - else - # change value - cat << DONE -sed -i "s|^$key\($delimiter\+\).*|$key\1$value_should|" "$file" -DONE - fi - ;; - esac +state_is="$(cat "$__object/explorer/state")" +state_should="$(cat "$__object/parameter/state")" + +if [ "$state_is" = "$state_should" ]; then + # nothing to do + exit 0 fi +case "$state_should" in + absent) + # remove lines starting with key + echo "sed -i '/^$key\($delimiter\+\)/d' \"$file\"" + ;; + present) + case "$state_is" in + absent) + # add new key and value + echo "echo \"${key}${delimiter}${value}\" >> \"$file\"" + ;; + wrongvalue) + # change exisiting value + echo "sed -i \"s|^$key\($delimiter\+\).*|$key\1$value|\" \"$file\"" + ;; + *) + echo "Unknown explorer state: $state_is" >&2 + exit 1 + esac + ;; + *) + echo "Unknown state: $state_should" >&2 + exit 1 +esac diff --git a/conf/type/__key_value/man.text b/conf/type/__key_value/man.text index 3e4e8013..1423fc7d 100644 --- a/conf/type/__key_value/man.text +++ b/conf/type/__key_value/man.text @@ -16,9 +16,6 @@ file. REQUIRED PARAMETERS ------------------- -value:: - The value for the key. Setting the value to `__NOTSET__` will remove the key - from the file. file:: The file to operate on. delimiter:: @@ -27,8 +24,13 @@ delimiter:: OPTIONAL PARAMETERS ------------------- +state:: + present or absent, defaults to present. If present, sets the key to value, + if absent, removes the key from the file. key:: The key to change. Defaults to object_id. +value:: + The value for the key. Optional if state=absent, required otherwise. EXAMPLES @@ -45,6 +47,9 @@ __key_value my-fancy-id --file /etc/login.defs --key SYS_UID_MAX --value 666 \ # Enable packet forwarding __key_value net.ipv4.ip_forward --file /etc/sysctl.conf --value 1 \ --delimiter '=' + +# Remove existing key/value +__key_value LEGACY_KEY --file /etc/somefile --state absent --delimiter '=' -------------------------------------------------------------------------------- diff --git a/conf/type/__key_value/manifest b/conf/type/__key_value/manifest index 84c06352..2e75e175 100755 --- a/conf/type/__key_value/manifest +++ b/conf/type/__key_value/manifest @@ -19,5 +19,12 @@ # # set defaults -[ -f "$__object/parameter/key" ] \ - || echo "$__object_id" > "$__object/parameter/key" +key="$(cat "$__object/parameter/key" 2>/dev/null \ + || echo "$__object_id" | tee "$__object/parameter/key")" +state="$(cat "$__object/parameter/state" 2>/dev/null \ + || echo "present" | tee "$__object/parameter/state")" + +if [ "$state" = "present" -a ! -f "$__object/parameter/value" ]; then + echo "Missing required parameter 'value'" >&2 + exit 1 +fi diff --git a/conf/type/__key_value/parameter/optional b/conf/type/__key_value/parameter/optional index 06bfde49..483e3192 100644 --- a/conf/type/__key_value/parameter/optional +++ b/conf/type/__key_value/parameter/optional @@ -1 +1,3 @@ key +value +state diff --git a/conf/type/__key_value/parameter/required b/conf/type/__key_value/parameter/required index 8f4aa53c..3ae10da3 100644 --- a/conf/type/__key_value/parameter/required +++ b/conf/type/__key_value/parameter/required @@ -1,3 +1,2 @@ -value file delimiter From ef81f03e89a2b53498f52d2e6262ea0ec94afdd4 Mon Sep 17 00:00:00 2001 From: Steven Armstrong Date: Fri, 3 Feb 2012 22:49:10 +0100 Subject: [PATCH 24/98] have to report absent state no matter what the desired state is Signed-off-by: Steven Armstrong --- conf/type/__key_value/explorer/state | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/conf/type/__key_value/explorer/state b/conf/type/__key_value/explorer/state index 7e66cb69..ec760f71 100755 --- a/conf/type/__key_value/explorer/state +++ b/conf/type/__key_value/explorer/state @@ -29,10 +29,13 @@ value="$(cat "$__object/parameter/value" 2>/dev/null \ case "$state" in absent) - # if the key exists, with whatever value, we will have to remove it - # so report it as present if egrep -q "^$key$delimiter+" "$file"; then + # if the key exists, with whatever value, we will have to remove it + # so report it as present echo present + else + # key does not exist + echo absent fi ;; present) From 4d845b3feaf14f413e768256d20983491d9567f9 Mon Sep 17 00:00:00 2001 From: Matt Coddington Date: Tue, 7 Feb 2012 10:27:28 -0500 Subject: [PATCH 25/98] fix for changing a user's group by name --- conf/type/__user/gencode-remote | 19 ++++++++++++++----- 1 file changed, 14 insertions(+), 5 deletions(-) diff --git a/conf/type/__user/gencode-remote b/conf/type/__user/gencode-remote index 595c7f64..077562f4 100755 --- a/conf/type/__user/gencode-remote +++ b/conf/type/__user/gencode-remote @@ -28,6 +28,7 @@ cd "$__object/parameter" if grep -q "^${name}:" "$__object/explorer/passwd"; then for property in $(ls .); do new_value="$(cat "$property")" + unset current_value file="$__object/explorer/passwd" @@ -36,9 +37,15 @@ if grep -q "^${name}:" "$__object/explorer/passwd"; then if $(echo "$new_value" | grep -q '^[0-9][0-9]*$'); then field=4 else - # group name - file="$__object/explorer/group" - field=1 + # we were passed a group name. compare to current gid and + # set $current_value to $oldgid if it needs changing. + newgid=$(awk -F: '{ print $3 }' "$__object/explorer/group") + oldgid=$(awk -F: '{ print $4 }' "$file") + if [ "$newgid" != "$oldgid" ]; then + current_value="$oldgid" + else + current_value=$new_value + fi fi ;; password) @@ -51,8 +58,10 @@ if grep -q "^${name}:" "$__object/explorer/passwd"; then uid) field=3 ;; esac - export field - current_value="$(awk -F: '{ print $ENVIRON["field"] }' < "$file")" + if [ -z "$current_value" ]; then + export field + current_value="$(awk -F: '{ print $ENVIRON["field"] }' < "$file")" + fi if [ "$new_value" != "$current_value" ]; then set -- "$@" "--$property" \'$new_value\' From 908e74689c19c08534cc946949051a4ca11081e0 Mon Sep 17 00:00:00 2001 From: Matt Coddington Date: Tue, 7 Feb 2012 12:38:21 -0500 Subject: [PATCH 26/98] improve comments and use better variable names --- conf/type/__user/gencode-remote | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-) diff --git a/conf/type/__user/gencode-remote b/conf/type/__user/gencode-remote index 077562f4..8979c56e 100755 --- a/conf/type/__user/gencode-remote +++ b/conf/type/__user/gencode-remote @@ -37,14 +37,15 @@ if grep -q "^${name}:" "$__object/explorer/passwd"; then if $(echo "$new_value" | grep -q '^[0-9][0-9]*$'); then field=4 else - # we were passed a group name. compare to current gid and - # set $current_value to $oldgid if it needs changing. - newgid=$(awk -F: '{ print $3 }' "$__object/explorer/group") - oldgid=$(awk -F: '{ print $4 }' "$file") - if [ "$newgid" != "$oldgid" ]; then - current_value="$oldgid" + # We were passed a group name. Compare the gid in + # the user's /etc/passwd entry with the gid of the + # group returned by the group explorer. + gid_from_group=$(awk -F: '{ print $3 }' "$__object/explorer/group") + gid_from_passwd=$(awk -F: '{ print $4 }' "$file") + if [ "$gid_from_group" != "$gid_from_passwd" ]; then + current_value="$gid_from_passwd" else - current_value=$new_value + current_value="$new_value" fi fi ;; @@ -58,6 +59,8 @@ if grep -q "^${name}:" "$__object/explorer/passwd"; then uid) field=3 ;; esac + # If we haven't already set $current_value above, pull it from the + # appropriate file/field. if [ -z "$current_value" ]; then export field current_value="$(awk -F: '{ print $ENVIRON["field"] }' < "$file")" From 817ce9c2562cc24117702a3eac7c3717766d0a87 Mon Sep 17 00:00:00 2001 From: Steven Armstrong Date: Wed, 8 Feb 2012 08:31:59 +0100 Subject: [PATCH 27/98] /egrep/grep -E/ Signed-off-by: Steven Armstrong --- conf/type/__key_value/explorer/state | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/conf/type/__key_value/explorer/state b/conf/type/__key_value/explorer/state index ec760f71..94a5ea7f 100755 --- a/conf/type/__key_value/explorer/state +++ b/conf/type/__key_value/explorer/state @@ -29,7 +29,7 @@ value="$(cat "$__object/parameter/value" 2>/dev/null \ case "$state" in absent) - if egrep -q "^$key$delimiter+" "$file"; then + if grep -q -E "^$key$delimiter+" "$file"; then # if the key exists, with whatever value, we will have to remove it # so report it as present echo present @@ -39,10 +39,10 @@ case "$state" in fi ;; present) - if egrep -q "^$key$delimiter+$value$" "$file"; then + if grep -q -E "^$key$delimiter+$value$" "$file"; then # key exists and value is same echo present - elif egrep -q "^$key$delimiter+" "$file"; then + elif grep -q -E "^$key$delimiter+" "$file"; then # key exists, but value is empty or different echo wrongvalue else From d55c52601f970deec649f29418d66575be88db66 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Thu, 9 Feb 2012 19:08:32 +0100 Subject: [PATCH 28/98] move run_type_explorer near run_type_explorers Signed-off-by: Nico Schottelius --- lib/cdist/core/explorer.py | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/lib/cdist/core/explorer.py b/lib/cdist/core/explorer.py index 01c4c81d..43b0339c 100644 --- a/lib/cdist/core/explorer.py +++ b/lib/cdist/core/explorer.py @@ -130,6 +130,19 @@ class Explorer(object): self.log.debug("Running type explorer '%s' for object '%s'", explorer, cdist_object.name) cdist_object.explorers[explorer] = output + def run_type_explorer(self, explorer, cdist_object): + """Run the given type explorer for the given object and return it's output.""" + cdist_type = cdist_object.type + env = self.env.copy() + env.update({ + '__object': os.path.join(self.remote.object_path, cdist_object.path), + '__object_id': cdist_object.object_id, + '__object_fq': cdist_object.path, + '__type_explorer': os.path.join(self.remote.type_path, cdist_type.explorer_path) + }) + script = os.path.join(self.remote.type_path, cdist_type.explorer_path, explorer) + return self.remote.run_script(script, env=env, return_output=True) + def transfer_type_explorers(self, cdist_type): """Transfer the type explorers for the given type to the remote side.""" if cdist_type.explorers: @@ -149,16 +162,3 @@ class Explorer(object): destination = os.path.join(self.remote.object_path, cdist_object.parameter_path) self.remote.mkdir(destination) self.remote.transfer(source, destination) - - def run_type_explorer(self, explorer, cdist_object): - """Run the given type explorer for the given object and return it's output.""" - cdist_type = cdist_object.type - env = self.env.copy() - env.update({ - '__object': os.path.join(self.remote.object_path, cdist_object.path), - '__object_id': cdist_object.object_id, - '__object_fq': cdist_object.path, - '__type_explorer': os.path.join(self.remote.type_path, cdist_type.explorer_path) - }) - script = os.path.join(self.remote.type_path, cdist_type.explorer_path, explorer) - return self.remote.run_script(script, env=env, return_output=True) From 1dcc420a38d7fe394e8400704779d2fbb2363a65 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Thu, 9 Feb 2012 19:09:32 +0100 Subject: [PATCH 29/98] no, no common base class for local/remote Signed-off-by: Nico Schottelius --- lib/cdist/exec/remote.py | 2 -- 1 file changed, 2 deletions(-) diff --git a/lib/cdist/exec/remote.py b/lib/cdist/exec/remote.py index 87db7273..b46235a8 100644 --- a/lib/cdist/exec/remote.py +++ b/lib/cdist/exec/remote.py @@ -20,8 +20,6 @@ # # -# FIXME: common base class with Local? - import io import os import sys From 53c61d42ad659fc6d0f156317c26a3ae34bde071 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Thu, 9 Feb 2012 19:12:49 +0100 Subject: [PATCH 30/98] remove useless if env: Signed-off-by: Nico Schottelius --- lib/cdist/exec/remote.py | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/lib/cdist/exec/remote.py b/lib/cdist/exec/remote.py index b46235a8..69dc5dda 100644 --- a/lib/cdist/exec/remote.py +++ b/lib/cdist/exec/remote.py @@ -146,18 +146,17 @@ class Remote(object): os_environ = os.environ.copy() os_environ['__target_host'] = self.target_host + self.log.debug("Remote run script: %s", command) + # can't pass environment to remote side, so prepend command with # variable declarations if env: + self.log.debug("Remote run script env: %s", env) command.extend(["%s=%s" % item for item in env.items()]) command.extend(["/bin/sh", "-e"]) command.append(script) - self.log.debug("Remote run script: %s", command) - if env: - self.log.debug("Remote run script env: %s", env) - try: if return_output: return subprocess.check_output(command, env=os_environ).decode() From 45053c6d84d0d1693442b6c3f63342042ba4fe83 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Thu, 9 Feb 2012 19:31:30 +0100 Subject: [PATCH 31/98] allow pip to be non existent during explorer stage Signed-off-by: Nico Schottelius --- conf/type/__package_pip/explorer/state | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/conf/type/__package_pip/explorer/state b/conf/type/__package_pip/explorer/state index 3a086e58..7886a46b 100644 --- a/conf/type/__package_pip/explorer/state +++ b/conf/type/__package_pip/explorer/state @@ -35,14 +35,14 @@ else pip="pip" fi -# which is not posix, but command is :-) +# If there is no pip, it may get created from somebody else. +# If it will be created, there is probably no package installed. if ! command -v "$pip" >/dev/null 2>&1; then - echo "No usable pip found at path \"$pip\"" >&2 - exit 1 -fi - -if "$pip" freeze | grep -i -q "^$name=="; then - echo present -else echo absent +else + if "$pip" freeze | grep -i -q "^$name=="; then + echo present + else + echo absent + fi fi From 49917d29332558afa7411f1624971cc17c975648 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Fri, 10 Feb 2012 13:01:29 +0100 Subject: [PATCH 32/98] +object id issues/ideas Signed-off-by: Nico Schottelius --- doc/dev/logs/2012-02-10.object_id-and-slashes | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) create mode 100644 doc/dev/logs/2012-02-10.object_id-and-slashes diff --git a/doc/dev/logs/2012-02-10.object_id-and-slashes b/doc/dev/logs/2012-02-10.object_id-and-slashes new file mode 100644 index 00000000..de46a1f8 --- /dev/null +++ b/doc/dev/logs/2012-02-10.object_id-and-slashes @@ -0,0 +1,18 @@ +__typename /foo/bar # possible, usual use case +require="__a//b" __typename /foo/bar # possible and happens often for __a/$id in loops + +__typename /foo/bar/ # trailing slash will be stripped, can be documented + +__typename /foo//bar//baz # // will be converted to / implicitly through fs; error prone; disallow + +require="__a//b//c" __typename # // will be converted to / implicitly through fs; error prone; disallow + + +Solution: + + 1) allow require __a//b: type __a, object id /b + => strip first slash of object id, as we do in non-dep-mode + 2) allow _one_ trailing /: __type /foo/bar/ and require="__foo/abc/" + => strip one leading slash of object id + 3) disallow // within object id + 4) disallow starting or ending / after 1) and 2) From 947c9a4ccb3a96c2a825a97f40bea4eced22a8e3 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Fri, 10 Feb 2012 16:17:53 +0100 Subject: [PATCH 33/98] ++changes for 2.0.7 Signed-off-by: Nico Schottelius --- conf/type/__package_pip/explorer/state | 1 + doc/changelog | 1 + 2 files changed, 2 insertions(+) diff --git a/conf/type/__package_pip/explorer/state b/conf/type/__package_pip/explorer/state index 7886a46b..5be07280 100644 --- a/conf/type/__package_pip/explorer/state +++ b/conf/type/__package_pip/explorer/state @@ -40,6 +40,7 @@ fi if ! command -v "$pip" >/dev/null 2>&1; then echo absent else + if "$pip" freeze | grep -i -q "^$name=="; then echo present else diff --git a/doc/changelog b/doc/changelog index 7e070cc5..dace28dd 100644 --- a/doc/changelog +++ b/doc/changelog @@ -8,6 +8,7 @@ Changelog * Bugfix __file: Use chmod after chown/chgrp (Matt Coddington) * Bugfix __user: Correct shadow field in explorer (Matt Coddington) * Bugfix __link: Properly handle existing links (Steven Armstrong) + * Bugfix __key_value: More robust implementation (Steven Armstrong) * New Type: __package_pip 2.0.6: 2012-01-28 From 2fc2df3a35aefc67ad39f0f0431529970d720049 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Sat, 11 Feb 2012 11:53:40 +0100 Subject: [PATCH 34/98] Preperation -> Preparation Signed-off-by: Nico Schottelius --- README | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README b/README index 51fb323c..965138c4 100644 --- a/README +++ b/README @@ -89,7 +89,7 @@ cdist was tested or is know to run on at least ## Installation -### Preperation +### Preparation Ensure you have Python 3.2 installed on the machine you use to **deploy to the targets** (the ***source host***). From 6dcbfc3b88bf7d075801003575f8aec66a943a02 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Sun, 12 Feb 2012 00:05:01 +0100 Subject: [PATCH 35/98] more todo Signed-off-by: Nico Schottelius --- doc/dev/todo/niconext | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/doc/dev/todo/niconext b/doc/dev/todo/niconext index 4db98d58..167f124a 100644 --- a/doc/dev/todo/niconext +++ b/doc/dev/todo/niconext @@ -1,5 +1,14 @@ -- __file/foo/bar//bar - - fails later +- cleanup object_id handling + - problems + - __file/foo/bar//bar + - fails later + - right strip __foo/bar/ last slash + - only emulator creates objects + - strip slashes in object creation? + + + +-------------------------------------------------------------------------------- - __user add option to include --create-home From 15fb097464f13f78009a6330c9578b45b102f03c Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Sun, 12 Feb 2012 00:05:21 +0100 Subject: [PATCH 36/98] add function to sanitise object_id and verify no // Signed-off-by: Nico Schottelius --- lib/cdist/core/object.py | 23 +++++++++++++++++++++-- 1 file changed, 21 insertions(+), 2 deletions(-) diff --git a/lib/cdist/core/object.py b/lib/cdist/core/object.py index da2f21a6..23e2fba5 100644 --- a/lib/cdist/core/object.py +++ b/lib/cdist/core/object.py @@ -105,12 +105,17 @@ class Object(object): raise IllegalObjectIdError(object_id, 'object_id may not start with /') if OBJECT_MARKER in object_id.split(os.sep): raise IllegalObjectIdError(object_id, 'object_id may not contain \'%s\'' % OBJECT_MARKER) + if '//' in object_id: + raise IllegalObjectIdError(object_id, 'object_id may not contain //') def __init__(self, cdist_type, base_path, object_id=None): - self.validate_object_id(object_id) self.type = cdist_type # instance of Type self.base_path = base_path self.object_id = object_id + + self.sanitise_object_id() + self.validate_object_id(object_id) + self.name = self.join_name(self.type.name, self.object_id) self.path = os.path.join(self.type.path, self.object_id, OBJECT_MARKER) self.absolute_path = os.path.join(self.base_path, self.path) @@ -128,7 +133,6 @@ class Object(object): def __hash__(self): return hash(self.name) - def __lt__(self, other): return isinstance(other, self.__class__) and self.name < other.name @@ -146,6 +150,21 @@ class Object(object): type_name, object_id = self.split_name(object_name) return self.__class__(self.type.__class__(type_path, type_name), base_path, object_id=object_id) + def sanitise_object_id(self): + """ + Remove leading and trailing slash (one only) + """ + + print(self.__repr__()) + + # Remove leading slash + if self.object_id[0] == '/': + self.object_id = self.object_id[1:] + + # Remove trailing slash + if self.object_id[-1] == '/': + self.object_id = self.object_id[:-1] + # FIXME: still needed? @property def explorer_path(self): From 4be37f6e9372e0bc338a8c319bba782b84f23090 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Sun, 12 Feb 2012 00:08:18 +0100 Subject: [PATCH 37/98] begin rename Object => CdistObject Signed-off-by: Nico Schottelius --- lib/cdist/config_install.py | 12 +++++----- lib/cdist/core/object.py | 8 +++---- lib/cdist/emulator.py | 6 ++--- lib/cdist/test/code/__init__.py | 2 +- lib/cdist/test/emulator/__init__.py | 4 ++-- lib/cdist/test/explorer/__init__.py | 6 ++--- lib/cdist/test/manifest/__init__.py | 2 +- lib/cdist/test/object/__init__.py | 34 ++++++++++++++--------------- lib/cdist/test/resolver/__init__.py | 2 +- 9 files changed, 37 insertions(+), 39 deletions(-) diff --git a/lib/cdist/config_install.py b/lib/cdist/config_install.py index 542f2024..f27fff77 100644 --- a/lib/cdist/config_install.py +++ b/lib/cdist/config_install.py @@ -89,9 +89,9 @@ class ConfigInstall(object): new_objects_created = True while new_objects_created: new_objects_created = False - for cdist_object in core.Object.list_objects(self.local.object_path, + for cdist_object in core.CdistObject.list_objects(self.local.object_path, self.local.type_path): - if cdist_object.state == core.Object.STATE_PREPARED: + if cdist_object.state == core.CdistObject.STATE_PREPARED: self.log.debug("Skipping re-prepare of object %s", cdist_object) continue else: @@ -103,12 +103,12 @@ class ConfigInstall(object): self.log.info("Running manifest and explorers for " + cdist_object.name) self.explorer.run_type_explorers(cdist_object) self.manifest.run_type_manifest(cdist_object) - cdist_object.state = core.Object.STATE_PREPARED + cdist_object.state = core.CdistObject.STATE_PREPARED def object_run(self, cdist_object): """Run gencode and code for an object""" self.log.debug("Trying to run object " + cdist_object.name) - if cdist_object.state == core.Object.STATE_DONE: + if cdist_object.state == core.CdistObject.STATE_DONE: # TODO: remove once we are sure that this really never happens. raise cdist.Error("Attempting to run an already finished object: %s", cdist_object) @@ -130,13 +130,13 @@ class ConfigInstall(object): # Mark this object as done self.log.debug("Finishing run of " + cdist_object.name) - cdist_object.state = core.Object.STATE_DONE + cdist_object.state = core.CdistObject.STATE_DONE def stage_run(self): """The final (and real) step of deployment""" self.log.info("Generating and executing code") - objects = core.Object.list_objects( + objects = core.CdistObject.list_objects( self.local.object_path, self.local.type_path) diff --git a/lib/cdist/core/object.py b/lib/cdist/core/object.py index 23e2fba5..278cdc46 100644 --- a/lib/cdist/core/object.py +++ b/lib/cdist/core/object.py @@ -42,7 +42,7 @@ class IllegalObjectIdError(cdist.Error): return '%s: %s' % (self.message, self.object_id) -class Object(object): +class CdistObject(object): """Represents a cdist object. All interaction with objects in cdist should be done through this class. @@ -124,7 +124,7 @@ class Object(object): self.parameter_path = os.path.join(self.path, "parameter") def __repr__(self): - return '' % self.name + return '' % self.name def __eq__(self, other): """define equality as 'name is the same'""" @@ -142,7 +142,7 @@ class Object(object): Mainly intended to create objects when resolving requirements. e.g: - .object_from_name('__other/object') -> + .object_from_name('__other/object') -> """ type_path = self.type.base_path @@ -155,8 +155,6 @@ class Object(object): Remove leading and trailing slash (one only) """ - print(self.__repr__()) - # Remove leading slash if self.object_id[0] == '/': self.object_id = self.object_id[1:] diff --git a/lib/cdist/emulator.py b/lib/cdist/emulator.py index 05202a39..77bc5ac8 100644 --- a/lib/cdist/emulator.py +++ b/lib/cdist/emulator.py @@ -126,7 +126,7 @@ class Emulator(object): self.object_id = self.object_id.lstrip('/') # Instantiate the cdist object we are defining - self.cdist_object = core.Object(self.cdist_type, self.object_base_path, self.object_id) + self.cdist_object = core.CdistObject(self.cdist_type, self.object_base_path, self.object_id) # Create object with given parameters self.parameters = {} @@ -154,13 +154,13 @@ class Emulator(object): if len(requirement) == 0: continue - requirement_type_name, requirement_object_id = core.Object.split_name(requirement) + requirement_type_name, requirement_object_id = core.CdistObject.split_name(requirement) # Instantiate type which fails if type does not exist requirement_type = core.Type(self.type_base_path, requirement_type_name) if requirement_object_id: # Validate object_id if any - core.Object.validate_object_id(requirement_object_id) + core.CdistObject.validate_object_id(requirement_object_id) elif not requirement_type.is_singleton: # Only singeltons have no object_id raise IllegalRequirementError(requirement, "Missing object_id and type is not a singleton.") diff --git a/lib/cdist/test/code/__init__.py b/lib/cdist/test/code/__init__.py index 2f061086..198d3e95 100644 --- a/lib/cdist/test/code/__init__.py +++ b/lib/cdist/test/code/__init__.py @@ -55,7 +55,7 @@ class CodeTestCase(test.CdistTestCase): self.code = code.Code(self.target_host, self.local, self.remote) self.cdist_type = core.Type(self.local.type_path, '__dump_environment') - self.cdist_object = core.Object(self.cdist_type, self.local.object_path, 'whatever') + self.cdist_object = core.CdistObject(self.cdist_type, self.local.object_path, 'whatever') self.cdist_object.create() self.log = logging.getLogger("cdist") diff --git a/lib/cdist/test/emulator/__init__.py b/lib/cdist/test/emulator/__init__.py index e67bed4a..4ea792cb 100644 --- a/lib/cdist/test/emulator/__init__.py +++ b/lib/cdist/test/emulator/__init__.py @@ -120,7 +120,7 @@ class AutoRequireEmulatorTestCase(test.CdistTestCase): initial_manifest = os.path.join(self.local.manifest_path, "init") self.manifest.run_initial_manifest(initial_manifest) cdist_type = core.Type(self.local.type_path, '__saturn') - cdist_object = core.Object(cdist_type, self.local.object_path, 'singleton') + cdist_object = core.CdistObject(cdist_type, self.local.object_path, 'singleton') self.manifest.run_type_manifest(cdist_object) expected = ['__planet/Saturn', '__moon/Prometheus'] self.assertEqual(sorted(cdist_object.requirements), sorted(expected)) @@ -157,5 +157,5 @@ class ArgumentsWithDashesTestCase(test.CdistTestCase): emu.run() cdist_type = core.Type(self.local.type_path, '__arguments_with_dashes') - cdist_object = core.Object(cdist_type, self.local.object_path, 'some-id') + cdist_object = core.CdistObject(cdist_type, self.local.object_path, 'some-id') self.assertTrue('with-dash' in cdist_object.parameters) diff --git a/lib/cdist/test/explorer/__init__.py b/lib/cdist/test/explorer/__init__.py index cafe34fc..df5a76ab 100644 --- a/lib/cdist/test/explorer/__init__.py +++ b/lib/cdist/test/explorer/__init__.py @@ -110,7 +110,7 @@ class ExplorerClassTestCase(test.CdistTestCase): def test_transfer_object_parameters(self): cdist_type = core.Type(self.local.type_path, '__test_type') - cdist_object = core.Object(cdist_type, self.local.object_path, 'whatever') + cdist_object = core.CdistObject(cdist_type, self.local.object_path, 'whatever') cdist_object.create() cdist_object.parameters = {'first': 'first value', 'second': 'second value'} self.explorer.transfer_object_parameters(cdist_object) @@ -120,14 +120,14 @@ class ExplorerClassTestCase(test.CdistTestCase): def test_run_type_explorer(self): cdist_type = core.Type(self.local.type_path, '__test_type') - cdist_object = core.Object(cdist_type, self.local.object_path, 'whatever') + cdist_object = core.CdistObject(cdist_type, self.local.object_path, 'whatever') self.explorer.transfer_type_explorers(cdist_type) output = self.explorer.run_type_explorer('world', cdist_object) self.assertEqual(output, 'hello\n') def test_run_type_explorers(self): cdist_type = core.Type(self.local.type_path, '__test_type') - cdist_object = core.Object(cdist_type, self.local.object_path, 'whatever') + cdist_object = core.CdistObject(cdist_type, self.local.object_path, 'whatever') cdist_object.create() self.explorer.run_type_explorers(cdist_object) self.assertEqual(cdist_object.explorers, {'world': 'hello'}) diff --git a/lib/cdist/test/manifest/__init__.py b/lib/cdist/test/manifest/__init__.py index 2383adf7..158cf6fd 100644 --- a/lib/cdist/test/manifest/__init__.py +++ b/lib/cdist/test/manifest/__init__.py @@ -80,7 +80,7 @@ class ManifestTestCase(test.CdistTestCase): def test_type_manifest_environment(self): cdist_type = core.Type(self.local.type_path, '__dump_environment') - cdist_object = core.Object(cdist_type, self.local.object_path, 'whatever') + cdist_object = core.CdistObject(cdist_type, self.local.object_path, 'whatever') handle, output_file = self.mkstemp(dir=self.temp_dir) os.close(handle) os.environ['__cdist_test_out'] = output_file diff --git a/lib/cdist/test/object/__init__.py b/lib/cdist/test/object/__init__.py index f199ffb5..9e6f1221 100644 --- a/lib/cdist/test/object/__init__.py +++ b/lib/cdist/test/object/__init__.py @@ -34,19 +34,19 @@ type_base_path = op.join(fixtures, 'type') class ObjectClassTestCase(test.CdistTestCase): def test_list_object_names(self): - object_names = list(core.Object.list_object_names(object_base_path)) + object_names = list(core.CdistObject.list_object_names(object_base_path)) self.assertEqual(object_names, ['__first/man', '__second/on-the', '__third/moon']) def test_list_type_names(self): - type_names = list(core.Object.list_type_names(object_base_path)) + type_names = list(core.CdistObject.list_type_names(object_base_path)) self.assertEqual(type_names, ['__first', '__second', '__third']) def test_list_objects(self): - objects = list(core.Object.list_objects(object_base_path, type_base_path)) + objects = list(core.CdistObject.list_objects(object_base_path, type_base_path)) objects_expected = [ - core.Object(core.Type(type_base_path, '__first'), object_base_path, 'man'), - core.Object(core.Type(type_base_path, '__second'), object_base_path, 'on-the'), - core.Object(core.Type(type_base_path, '__third'), object_base_path, 'moon'), + core.CdistObject(core.Type(type_base_path, '__first'), object_base_path, 'man'), + core.CdistObject(core.Type(type_base_path, '__second'), object_base_path, 'on-the'), + core.CdistObject(core.Type(type_base_path, '__third'), object_base_path, 'moon'), ] self.assertEqual(objects, objects_expected) @@ -56,18 +56,18 @@ class ObjectIdTestCase(test.CdistTestCase): cdist_type = core.Type(type_base_path, '__third') illegal_object_id = '/object_id/may/not/start/with/slash' with self.assertRaises(core.IllegalObjectIdError): - core.Object(cdist_type, object_base_path, illegal_object_id) + core.CdistObject(cdist_type, object_base_path, illegal_object_id) def test_object_id_contains_object_marker(self): cdist_type = core.Type(type_base_path, '__third') illegal_object_id = 'object_id/may/not/contain/%s/anywhere' % core.OBJECT_MARKER with self.assertRaises(core.IllegalObjectIdError): - core.Object(cdist_type, object_base_path, illegal_object_id) + core.CdistObject(cdist_type, object_base_path, illegal_object_id) def test_object_id_contains_object_marker_string(self): cdist_type = core.Type(type_base_path, '__third') illegal_object_id = 'object_id/may/contain_%s_in_filename' % core.OBJECT_MARKER - core.Object(cdist_type, object_base_path, illegal_object_id) + core.CdistObject(cdist_type, object_base_path, illegal_object_id) # if we get here, the test passed @@ -75,7 +75,7 @@ class ObjectTestCase(test.CdistTestCase): def setUp(self): self.cdist_type = core.Type(type_base_path, '__third') - self.cdist_object = core.Object(self.cdist_type, object_base_path, 'moon') + self.cdist_object = core.CdistObject(self.cdist_type, object_base_path, 'moon') def tearDown(self): self.cdist_object.changed = False @@ -159,16 +159,16 @@ class ObjectTestCase(test.CdistTestCase): self.assertEqual(self.cdist_object.state, '') def test_state_prepared(self): - self.cdist_object.state = core.Object.STATE_PREPARED - self.assertEqual(self.cdist_object.state, core.Object.STATE_PREPARED) + self.cdist_object.state = core.CdistObject.STATE_PREPARED + self.assertEqual(self.cdist_object.state, core.CdistObject.STATE_PREPARED) def test_state_running(self): - self.cdist_object.state = core.Object.STATE_RUNNING - self.assertEqual(self.cdist_object.state, core.Object.STATE_RUNNING) + self.cdist_object.state = core.CdistObject.STATE_RUNNING + self.assertEqual(self.cdist_object.state, core.CdistObject.STATE_RUNNING) def test_state_done(self): - self.cdist_object.state = core.Object.STATE_DONE - self.assertEqual(self.cdist_object.state, core.Object.STATE_DONE) + self.cdist_object.state = core.CdistObject.STATE_DONE + self.assertEqual(self.cdist_object.state, core.CdistObject.STATE_DONE) def test_source(self): self.assertEqual(list(self.cdist_object.source), []) @@ -195,6 +195,6 @@ class ObjectTestCase(test.CdistTestCase): self.cdist_object.code_remote = 'Hello World' other_name = '__first/man' other_object = self.cdist_object.object_from_name(other_name) - self.assertTrue(isinstance(other_object, core.Object)) + self.assertTrue(isinstance(other_object, core.CdistObject)) self.assertEqual(other_object.type.name, '__first') self.assertEqual(other_object.object_id, 'man') diff --git a/lib/cdist/test/resolver/__init__.py b/lib/cdist/test/resolver/__init__.py index cca058a4..ae8f6915 100644 --- a/lib/cdist/test/resolver/__init__.py +++ b/lib/cdist/test/resolver/__init__.py @@ -37,7 +37,7 @@ type_base_path = op.join(fixtures, 'type') class ResolverTestCase(test.CdistTestCase): def setUp(self): - self.objects = list(core.Object.list_objects(object_base_path, type_base_path)) + self.objects = list(core.CdistObject.list_objects(object_base_path, type_base_path)) self.object_index = dict((o.name, o) for o in self.objects) self.dependency_resolver = resolver.DependencyResolver(self.objects) From 1314567012d7394e9b87b7689ccc5080cb0cb981 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Sun, 12 Feb 2012 01:10:57 +0100 Subject: [PATCH 38/98] also begin to prefix type with cdist Signed-off-by: Nico Schottelius --- lib/cdist/core/__init__.py | 16 ++++++++-------- lib/cdist/core/{object.py => cdist_object.py} | 0 lib/cdist/core/{type.py => cdist_type.py} | 6 +++--- lib/cdist/test/object/__init__.py | 2 +- 4 files changed, 12 insertions(+), 12 deletions(-) rename lib/cdist/core/{object.py => cdist_object.py} (100%) rename lib/cdist/core/{type.py => cdist_type.py} (97%) diff --git a/lib/cdist/core/__init__.py b/lib/cdist/core/__init__.py index c61c659b..66ee00a5 100644 --- a/lib/cdist/core/__init__.py +++ b/lib/cdist/core/__init__.py @@ -19,11 +19,11 @@ # # -from cdist.core.type import Type -from cdist.core.type import NoSuchTypeError -from cdist.core.object import Object -from cdist.core.object import IllegalObjectIdError -from cdist.core.object import OBJECT_MARKER -from cdist.core.explorer import Explorer -from cdist.core.manifest import Manifest -from cdist.core.code import Code +from cdist.core.cdist_type import CdistType +from cdist.core.cdist_type import NoSuchTypeError +from cdist.core.cdist_object import CdistObject +from cdist.core.cdist_object import IllegalObjectIdError +from cdist.core.cdist_object import OBJECT_MARKER +from cdist.core.explorer import Explorer +from cdist.core.manifest import Manifest +from cdist.core.code import Code diff --git a/lib/cdist/core/object.py b/lib/cdist/core/cdist_object.py similarity index 100% rename from lib/cdist/core/object.py rename to lib/cdist/core/cdist_object.py diff --git a/lib/cdist/core/type.py b/lib/cdist/core/cdist_type.py similarity index 97% rename from lib/cdist/core/type.py rename to lib/cdist/core/cdist_type.py index 20365b8d..55609e7e 100644 --- a/lib/cdist/core/type.py +++ b/lib/cdist/core/cdist_type.py @@ -34,7 +34,7 @@ class NoSuchTypeError(cdist.Error): return "Type '%s' does not exist at %s" % (self.type_path, self.type_absolute_path) -class Type(object): +class CdistType(object): """Represents a cdist type. All interaction with types in cdist should be done through this class. @@ -61,7 +61,7 @@ class Type(object): # name is second argument name = args[1] if not name in cls._instances: - instance = super(Type, cls).__new__(cls) + instance = super(CdistType, cls).__new__(cls) cls._instances[name] = instance # return instance so __init__ is called return cls._instances[name] @@ -84,7 +84,7 @@ class Type(object): self.__optional_parameters = None def __repr__(self): - return '' % self.name + return '' % self.name def __eq__(self, other): return isinstance(other, self.__class__) and self.name == other.name diff --git a/lib/cdist/test/object/__init__.py b/lib/cdist/test/object/__init__.py index 9e6f1221..a633955a 100644 --- a/lib/cdist/test/object/__init__.py +++ b/lib/cdist/test/object/__init__.py @@ -38,7 +38,7 @@ class ObjectClassTestCase(test.CdistTestCase): self.assertEqual(object_names, ['__first/man', '__second/on-the', '__third/moon']) def test_list_type_names(self): - type_names = list(core.CdistObject.list_type_names(object_base_path)) + type_names = list(cdist.core.CdistObject.list_type_names(object_base_path)) self.assertEqual(type_names, ['__first', '__second', '__third']) def test_list_objects(self): From fb4f8784b6cb0cdd83aa6fe109bcddcd884967f2 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Sun, 12 Feb 2012 01:18:14 +0100 Subject: [PATCH 39/98] rename Type => CdistType Signed-off-by: Nico Schottelius --- lib/cdist/core/cdist_object.py | 2 +- lib/cdist/test/code/__init__.py | 6 ++-- lib/cdist/test/emulator/__init__.py | 4 +-- lib/cdist/test/explorer/__init__.py | 18 +++++----- lib/cdist/test/manifest/__init__.py | 2 +- lib/cdist/test/object/__init__.py | 14 ++++---- lib/cdist/test/type/__init__.py | 52 ++++++++++++++--------------- 7 files changed, 50 insertions(+), 48 deletions(-) diff --git a/lib/cdist/core/cdist_object.py b/lib/cdist/core/cdist_object.py index 278cdc46..43d07d6b 100644 --- a/lib/cdist/core/cdist_object.py +++ b/lib/cdist/core/cdist_object.py @@ -61,7 +61,7 @@ class CdistObject(object): """Return a list of object instances""" for object_name in cls.list_object_names(object_base_path): type_name, object_id = cls.split_name(object_name) - yield cls(cdist.core.Type(type_base_path, type_name), object_base_path, object_id=object_id) + yield cls(cdist.core.CdistType(type_base_path, type_name), object_base_path, object_id=object_id) @classmethod def list_type_names(cls, object_base_path): diff --git a/lib/cdist/test/code/__init__.py b/lib/cdist/test/code/__init__.py index 198d3e95..176f139c 100644 --- a/lib/cdist/test/code/__init__.py +++ b/lib/cdist/test/code/__init__.py @@ -48,13 +48,13 @@ class CodeTestCase(test.CdistTestCase): self.remote_base_path = self.mkdtemp() self.user = getpass.getuser() - remote_exec = "ssh -o User=%s -q" % self.user - remote_copy = "scp -o User=%s -q" % self.user + remote_exec = "ssh -o User=%s -q" % "root" # self.user + remote_copy = "scp -o User=%s -q" % "root" # self.user self.remote = remote.Remote(self.target_host, self.remote_base_path, remote_exec, remote_copy) self.code = code.Code(self.target_host, self.local, self.remote) - self.cdist_type = core.Type(self.local.type_path, '__dump_environment') + self.cdist_type = core.CdistType(self.local.type_path, '__dump_environment') self.cdist_object = core.CdistObject(self.cdist_type, self.local.object_path, 'whatever') self.cdist_object.create() diff --git a/lib/cdist/test/emulator/__init__.py b/lib/cdist/test/emulator/__init__.py index 4ea792cb..c0037b68 100644 --- a/lib/cdist/test/emulator/__init__.py +++ b/lib/cdist/test/emulator/__init__.py @@ -119,7 +119,7 @@ class AutoRequireEmulatorTestCase(test.CdistTestCase): def test_autorequire(self): initial_manifest = os.path.join(self.local.manifest_path, "init") self.manifest.run_initial_manifest(initial_manifest) - cdist_type = core.Type(self.local.type_path, '__saturn') + cdist_type = core.CdistType(self.local.type_path, '__saturn') cdist_object = core.CdistObject(cdist_type, self.local.object_path, 'singleton') self.manifest.run_type_manifest(cdist_object) expected = ['__planet/Saturn', '__moon/Prometheus'] @@ -156,6 +156,6 @@ class ArgumentsWithDashesTestCase(test.CdistTestCase): emu = emulator.Emulator(argv) emu.run() - cdist_type = core.Type(self.local.type_path, '__arguments_with_dashes') + cdist_type = core.CdistType(self.local.type_path, '__arguments_with_dashes') cdist_object = core.CdistObject(cdist_type, self.local.object_path, 'some-id') self.assertTrue('with-dash' in cdist_object.parameters) diff --git a/lib/cdist/test/explorer/__init__.py b/lib/cdist/test/explorer/__init__.py index df5a76ab..716e56b7 100644 --- a/lib/cdist/test/explorer/__init__.py +++ b/lib/cdist/test/explorer/__init__.py @@ -49,8 +49,10 @@ class ExplorerClassTestCase(test.CdistTestCase): self.remote_base_path = self.mkdtemp() self.user = getpass.getuser() - remote_exec = "ssh -o User=%s -q" % self.user - remote_copy = "scp -o User=%s -q" % self.user + #remote_exec = "ssh -o User=%s -q" % self.user + #remote_copy = "scp -o User=%s -q" % self.user + remote_exec = "ssh -o User=%s -q" % "root" + remote_copy = "scp -o User=%s -q" % "root" self.remote = remote.Remote(self.target_host, self.remote_base_path, remote_exec, remote_copy) self.explorer = explorer.Explorer(self.target_host, self.local, self.remote) @@ -83,19 +85,19 @@ class ExplorerClassTestCase(test.CdistTestCase): shutil.rmtree(out_path) def test_list_type_explorer_names(self): - cdist_type = core.Type(self.local.type_path, '__test_type') + cdist_type = core.CdistType(self.local.type_path, '__test_type') expected = cdist_type.explorers self.assertEqual(self.explorer.list_type_explorer_names(cdist_type), expected) def test_transfer_type_explorers(self): - cdist_type = core.Type(self.local.type_path, '__test_type') + cdist_type = core.CdistType(self.local.type_path, '__test_type') self.explorer.transfer_type_explorers(cdist_type) source = os.path.join(self.local.type_path, cdist_type.explorer_path) destination = os.path.join(self.remote.type_path, cdist_type.explorer_path) self.assertEqual(os.listdir(source), os.listdir(destination)) def test_transfer_type_explorers_only_once(self): - cdist_type = core.Type(self.local.type_path, '__test_type') + cdist_type = core.CdistType(self.local.type_path, '__test_type') # first transfer self.explorer.transfer_type_explorers(cdist_type) source = os.path.join(self.local.type_path, cdist_type.explorer_path) @@ -109,7 +111,7 @@ class ExplorerClassTestCase(test.CdistTestCase): self.assertFalse(os.listdir(destination)) def test_transfer_object_parameters(self): - cdist_type = core.Type(self.local.type_path, '__test_type') + cdist_type = core.CdistType(self.local.type_path, '__test_type') cdist_object = core.CdistObject(cdist_type, self.local.object_path, 'whatever') cdist_object.create() cdist_object.parameters = {'first': 'first value', 'second': 'second value'} @@ -119,14 +121,14 @@ class ExplorerClassTestCase(test.CdistTestCase): self.assertEqual(sorted(os.listdir(source)), sorted(os.listdir(destination))) def test_run_type_explorer(self): - cdist_type = core.Type(self.local.type_path, '__test_type') + cdist_type = core.CdistType(self.local.type_path, '__test_type') cdist_object = core.CdistObject(cdist_type, self.local.object_path, 'whatever') self.explorer.transfer_type_explorers(cdist_type) output = self.explorer.run_type_explorer('world', cdist_object) self.assertEqual(output, 'hello\n') def test_run_type_explorers(self): - cdist_type = core.Type(self.local.type_path, '__test_type') + cdist_type = core.CdistType(self.local.type_path, '__test_type') cdist_object = core.CdistObject(cdist_type, self.local.object_path, 'whatever') cdist_object.create() self.explorer.run_type_explorers(cdist_object) diff --git a/lib/cdist/test/manifest/__init__.py b/lib/cdist/test/manifest/__init__.py index 158cf6fd..a188c788 100644 --- a/lib/cdist/test/manifest/__init__.py +++ b/lib/cdist/test/manifest/__init__.py @@ -79,7 +79,7 @@ class ManifestTestCase(test.CdistTestCase): self.assertEqual(output_dict['__manifest'], self.local.manifest_path) def test_type_manifest_environment(self): - cdist_type = core.Type(self.local.type_path, '__dump_environment') + cdist_type = core.CdistType(self.local.type_path, '__dump_environment') cdist_object = core.CdistObject(cdist_type, self.local.object_path, 'whatever') handle, output_file = self.mkstemp(dir=self.temp_dir) os.close(handle) diff --git a/lib/cdist/test/object/__init__.py b/lib/cdist/test/object/__init__.py index a633955a..00cc1e00 100644 --- a/lib/cdist/test/object/__init__.py +++ b/lib/cdist/test/object/__init__.py @@ -44,28 +44,28 @@ class ObjectClassTestCase(test.CdistTestCase): def test_list_objects(self): objects = list(core.CdistObject.list_objects(object_base_path, type_base_path)) objects_expected = [ - core.CdistObject(core.Type(type_base_path, '__first'), object_base_path, 'man'), - core.CdistObject(core.Type(type_base_path, '__second'), object_base_path, 'on-the'), - core.CdistObject(core.Type(type_base_path, '__third'), object_base_path, 'moon'), + core.CdistObject(core.CdistType(type_base_path, '__first'), object_base_path, 'man'), + core.CdistObject(core.CdistType(type_base_path, '__second'), object_base_path, 'on-the'), + core.CdistObject(core.CdistType(type_base_path, '__third'), object_base_path, 'moon'), ] self.assertEqual(objects, objects_expected) class ObjectIdTestCase(test.CdistTestCase): def test_object_id_starts_with_slash(self): - cdist_type = core.Type(type_base_path, '__third') + cdist_type = core.CdistType(type_base_path, '__third') illegal_object_id = '/object_id/may/not/start/with/slash' with self.assertRaises(core.IllegalObjectIdError): core.CdistObject(cdist_type, object_base_path, illegal_object_id) def test_object_id_contains_object_marker(self): - cdist_type = core.Type(type_base_path, '__third') + cdist_type = core.CdistType(type_base_path, '__third') illegal_object_id = 'object_id/may/not/contain/%s/anywhere' % core.OBJECT_MARKER with self.assertRaises(core.IllegalObjectIdError): core.CdistObject(cdist_type, object_base_path, illegal_object_id) def test_object_id_contains_object_marker_string(self): - cdist_type = core.Type(type_base_path, '__third') + cdist_type = core.CdistType(type_base_path, '__third') illegal_object_id = 'object_id/may/contain_%s_in_filename' % core.OBJECT_MARKER core.CdistObject(cdist_type, object_base_path, illegal_object_id) # if we get here, the test passed @@ -74,7 +74,7 @@ class ObjectIdTestCase(test.CdistTestCase): class ObjectTestCase(test.CdistTestCase): def setUp(self): - self.cdist_type = core.Type(type_base_path, '__third') + self.cdist_type = core.CdistType(type_base_path, '__third') self.cdist_object = core.CdistObject(self.cdist_type, object_base_path, 'moon') def tearDown(self): diff --git a/lib/cdist/test/type/__init__.py b/lib/cdist/test/type/__init__.py index 7bb8654c..2ef14a4c 100644 --- a/lib/cdist/test/type/__init__.py +++ b/lib/cdist/test/type/__init__.py @@ -33,115 +33,115 @@ class TypeTestCase(test.CdistTestCase): def test_list_type_names(self): base_path = op.join(fixtures, 'list_types') - type_names = core.Type.list_type_names(base_path) + type_names = core.CdistType.list_type_names(base_path) self.assertEqual(type_names, ['__first', '__second', '__third']) def test_list_types(self): base_path = op.join(fixtures, 'list_types') - types = list(core.Type.list_types(base_path)) + types = list(core.CdistType.list_types(base_path)) types_expected = [ - core.Type(base_path, '__first'), - core.Type(base_path, '__second'), - core.Type(base_path, '__third'), + core.CdistType(base_path, '__first'), + core.CdistType(base_path, '__second'), + core.CdistType(base_path, '__third'), ] self.assertEqual(types, types_expected) def test_only_one_instance(self): base_path = fixtures - cdist_type1 = core.Type(base_path, '__name_path') - cdist_type2 = core.Type(base_path, '__name_path') + cdist_type1 = core.CdistType(base_path, '__name_path') + cdist_type2 = core.CdistType(base_path, '__name_path') self.assertEqual(id(cdist_type1), id(cdist_type2)) def test_nonexistent_type(self): base_path = fixtures - self.assertRaises(core.NoSuchTypeError, core.Type, base_path, '__i-dont-exist') + self.assertRaises(core.NoSuchTypeError, core.CdistType, base_path, '__i-dont-exist') def test_name(self): base_path = fixtures - cdist_type = core.Type(base_path, '__name_path') + cdist_type = core.CdistType(base_path, '__name_path') self.assertEqual(cdist_type.name, '__name_path') def test_path(self): base_path = fixtures - cdist_type = core.Type(base_path, '__name_path') + cdist_type = core.CdistType(base_path, '__name_path') self.assertEqual(cdist_type.path, '__name_path') def test_base_path(self): base_path = fixtures - cdist_type = core.Type(base_path, '__name_path') + cdist_type = core.CdistType(base_path, '__name_path') self.assertEqual(cdist_type.base_path, base_path) def test_absolute_path(self): base_path = fixtures - cdist_type = core.Type(base_path, '__name_path') + cdist_type = core.CdistType(base_path, '__name_path') self.assertEqual(cdist_type.absolute_path, os.path.join(base_path, '__name_path')) def test_manifest_path(self): base_path = fixtures - cdist_type = core.Type(base_path, '__name_path') + cdist_type = core.CdistType(base_path, '__name_path') self.assertEqual(cdist_type.manifest_path, os.path.join('__name_path', 'manifest')) def test_explorer_path(self): base_path = fixtures - cdist_type = core.Type(base_path, '__name_path') + cdist_type = core.CdistType(base_path, '__name_path') self.assertEqual(cdist_type.explorer_path, os.path.join('__name_path', 'explorer')) def test_gencode_local_path(self): base_path = fixtures - cdist_type = core.Type(base_path, '__name_path') + cdist_type = core.CdistType(base_path, '__name_path') self.assertEqual(cdist_type.gencode_local_path, os.path.join('__name_path', 'gencode-local')) def test_gencode_remote_path(self): base_path = fixtures - cdist_type = core.Type(base_path, '__name_path') + cdist_type = core.CdistType(base_path, '__name_path') self.assertEqual(cdist_type.gencode_remote_path, os.path.join('__name_path', 'gencode-remote')) def test_singleton_is_singleton(self): base_path = fixtures - cdist_type = core.Type(base_path, '__singleton') + cdist_type = core.CdistType(base_path, '__singleton') self.assertTrue(cdist_type.is_singleton) def test_not_singleton_is_singleton(self): base_path = fixtures - cdist_type = core.Type(base_path, '__not_singleton') + cdist_type = core.CdistType(base_path, '__not_singleton') self.assertFalse(cdist_type.is_singleton) def test_install_is_install(self): base_path = fixtures - cdist_type = core.Type(base_path, '__install') + cdist_type = core.CdistType(base_path, '__install') self.assertTrue(cdist_type.is_install) def test_not_install_is_install(self): base_path = fixtures - cdist_type = core.Type(base_path, '__not_install') + cdist_type = core.CdistType(base_path, '__not_install') self.assertFalse(cdist_type.is_install) def test_with_explorers(self): base_path = fixtures - cdist_type = core.Type(base_path, '__with_explorers') + cdist_type = core.CdistType(base_path, '__with_explorers') self.assertEqual(cdist_type.explorers, ['whatever']) def test_without_explorers(self): base_path = fixtures - cdist_type = core.Type(base_path, '__without_explorers') + cdist_type = core.CdistType(base_path, '__without_explorers') self.assertEqual(cdist_type.explorers, []) def test_with_required_parameters(self): base_path = fixtures - cdist_type = core.Type(base_path, '__with_required_parameters') + cdist_type = core.CdistType(base_path, '__with_required_parameters') self.assertEqual(cdist_type.required_parameters, ['required1', 'required2']) def test_without_required_parameters(self): base_path = fixtures - cdist_type = core.Type(base_path, '__without_required_parameters') + cdist_type = core.CdistType(base_path, '__without_required_parameters') self.assertEqual(cdist_type.required_parameters, []) def test_with_optional_parameters(self): base_path = fixtures - cdist_type = core.Type(base_path, '__with_optional_parameters') + cdist_type = core.CdistType(base_path, '__with_optional_parameters') self.assertEqual(cdist_type.optional_parameters, ['optional1', 'optional2']) def test_without_optional_parameters(self): base_path = fixtures - cdist_type = core.Type(base_path, '__without_optional_parameters') + cdist_type = core.CdistType(base_path, '__without_optional_parameters') self.assertEqual(cdist_type.optional_parameters, []) From 91ecfa7d3f185e4baab2d5a3e903924d4170c026 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Sun, 12 Feb 2012 01:27:25 +0100 Subject: [PATCH 40/98] back to 100% tests working Signed-off-by: Nico Schottelius --- lib/cdist/emulator.py | 8 +++++--- lib/cdist/exec/local.py | 2 +- lib/cdist/test/code/__init__.py | 4 ++-- lib/cdist/test/explorer/__init__.py | 6 ++---- lib/cdist/test/object/__init__.py | 2 ++ 5 files changed, 12 insertions(+), 10 deletions(-) diff --git a/lib/cdist/emulator.py b/lib/cdist/emulator.py index 77bc5ac8..72ed3b9b 100644 --- a/lib/cdist/emulator.py +++ b/lib/cdist/emulator.py @@ -41,14 +41,16 @@ class Emulator(object): self.object_id = False self.global_path = os.environ['__global'] - self.object_source = os.environ['__cdist_manifest'] self.target_host = os.environ['__target_host'] + + # Internally only + self.object_source = os.environ['__cdist_manifest'] self.type_base_path = os.environ['__cdist_type_base_path'] self.object_base_path = os.path.join(self.global_path, "object") self.type_name = os.path.basename(argv[0]) - self.cdist_type = core.Type(self.type_base_path, self.type_name) + self.cdist_type = core.CdistType(self.type_base_path, self.type_name) self.__init_log() @@ -156,7 +158,7 @@ class Emulator(object): requirement_type_name, requirement_object_id = core.CdistObject.split_name(requirement) # Instantiate type which fails if type does not exist - requirement_type = core.Type(self.type_base_path, requirement_type_name) + requirement_type = core.CdistType(self.type_base_path, requirement_type_name) if requirement_object_id: # Validate object_id if any diff --git a/lib/cdist/exec/local.py b/lib/cdist/exec/local.py index 613f5cf2..cdf06205 100644 --- a/lib/cdist/exec/local.py +++ b/lib/cdist/exec/local.py @@ -143,7 +143,7 @@ class Local(object): def link_emulator(self, exec_path): """Link emulator to types""" src = os.path.abspath(exec_path) - for cdist_type in core.Type.list_types(self.type_path): + for cdist_type in core.CdistType.list_types(self.type_path): dst = os.path.join(self.bin_path, cdist_type.name) self.log.debug("Linking emulator: %s to %s", src, dst) diff --git a/lib/cdist/test/code/__init__.py b/lib/cdist/test/code/__init__.py index 176f139c..dc701cce 100644 --- a/lib/cdist/test/code/__init__.py +++ b/lib/cdist/test/code/__init__.py @@ -48,8 +48,8 @@ class CodeTestCase(test.CdistTestCase): self.remote_base_path = self.mkdtemp() self.user = getpass.getuser() - remote_exec = "ssh -o User=%s -q" % "root" # self.user - remote_copy = "scp -o User=%s -q" % "root" # self.user + remote_exec = "ssh -o User=%s -q" % self.user + remote_copy = "scp -o User=%s -q" % self.user self.remote = remote.Remote(self.target_host, self.remote_base_path, remote_exec, remote_copy) self.code = code.Code(self.target_host, self.local, self.remote) diff --git a/lib/cdist/test/explorer/__init__.py b/lib/cdist/test/explorer/__init__.py index 716e56b7..257ad8a9 100644 --- a/lib/cdist/test/explorer/__init__.py +++ b/lib/cdist/test/explorer/__init__.py @@ -49,10 +49,8 @@ class ExplorerClassTestCase(test.CdistTestCase): self.remote_base_path = self.mkdtemp() self.user = getpass.getuser() - #remote_exec = "ssh -o User=%s -q" % self.user - #remote_copy = "scp -o User=%s -q" % self.user - remote_exec = "ssh -o User=%s -q" % "root" - remote_copy = "scp -o User=%s -q" % "root" + remote_exec = "ssh -o User=%s -q" % self.user + remote_copy = "scp -o User=%s -q" % self.user self.remote = remote.Remote(self.target_host, self.remote_base_path, remote_exec, remote_copy) self.explorer = explorer.Explorer(self.target_host, self.local, self.remote) diff --git a/lib/cdist/test/object/__init__.py b/lib/cdist/test/object/__init__.py index 00cc1e00..0f8c0189 100644 --- a/lib/cdist/test/object/__init__.py +++ b/lib/cdist/test/object/__init__.py @@ -25,6 +25,8 @@ import shutil from cdist import test from cdist import core +import cdist + import os.path as op my_dir = op.abspath(op.dirname(__file__)) fixtures = op.join(my_dir, 'fixtures') From 0c990e17566bc86fbcdade68fcbbcb3eff450a5f Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 07:25:04 +0100 Subject: [PATCH 41/98] add singleton / no object_id test to CdistObject Signed-off-by: Nico Schottelius --- lib/cdist/core/cdist_object.py | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/lib/cdist/core/cdist_object.py b/lib/cdist/core/cdist_object.py index 43d07d6b..6b1e02b0 100644 --- a/lib/cdist/core/cdist_object.py +++ b/lib/cdist/core/cdist_object.py @@ -96,25 +96,29 @@ class CdistObject(object): """ return os.path.join(type_name, object_id) - @staticmethod - def validate_object_id(object_id): + def validate_object_id(self): """Validate the given object_id and raise IllegalObjectIdError if it's not valid. """ if object_id: - if object_id.startswith('/'): + if self.object_id.startswith('/'): raise IllegalObjectIdError(object_id, 'object_id may not start with /') - if OBJECT_MARKER in object_id.split(os.sep): + if OBJECT_MARKER in self.object_id.split(os.sep): raise IllegalObjectIdError(object_id, 'object_id may not contain \'%s\'' % OBJECT_MARKER) - if '//' in object_id: + if '//' in self.object_id: raise IllegalObjectIdError(object_id, 'object_id may not contain //') + # If no object_id and type is not singleton => error out + if not object_id and not self.type.is_singleton: + raise IllegalObjectIdError(object_id, + "Missing object_id and type is not a singleton.") + def __init__(self, cdist_type, base_path, object_id=None): self.type = cdist_type # instance of Type self.base_path = base_path self.object_id = object_id self.sanitise_object_id() - self.validate_object_id(object_id) + self.validate_object_id() self.name = self.join_name(self.type.name, self.object_id) self.path = os.path.join(self.type.path, self.object_id, OBJECT_MARKER) From ab565dc3d90e8f2de14976e0e902bc52e3669af0 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 07:45:10 +0100 Subject: [PATCH 42/98] cleanup / emulator Signed-off-by: Nico Schottelius --- doc/dev/todo/niconext | 12 ++++-------- lib/cdist/emulator.py | 17 ++++------------- 2 files changed, 8 insertions(+), 21 deletions(-) diff --git a/doc/dev/todo/niconext b/doc/dev/todo/niconext index 167f124a..34c2f7b0 100644 --- a/doc/dev/todo/niconext +++ b/doc/dev/todo/niconext @@ -1,12 +1,8 @@ - cleanup object_id handling - - problems - - __file/foo/bar//bar - - fails later - - right strip __foo/bar/ last slash - - only emulator creates objects - - strip slashes in object creation? - - + - have a look at singletons + - double check verification + - cleanup emulator to create object + - adjust tests -------------------------------------------------------------------------------- diff --git a/lib/cdist/emulator.py b/lib/cdist/emulator.py index 72ed3b9b..67f6d373 100644 --- a/lib/cdist/emulator.py +++ b/lib/cdist/emulator.py @@ -115,18 +115,13 @@ class Emulator(object): def setup_object(self): - # FIXME: verify object id - - # Setup object_id + # Setup object_id - FIXME: unset / do not setup anymore! if self.cdist_type.is_singleton: self.object_id = "singleton" else: self.object_id = self.args.object_id[0] del self.args.object_id - # strip leading slash from object_id - self.object_id = self.object_id.lstrip('/') - # Instantiate the cdist object we are defining self.cdist_object = core.CdistObject(self.cdist_type, self.object_base_path, self.object_id) @@ -160,13 +155,9 @@ class Emulator(object): # Instantiate type which fails if type does not exist requirement_type = core.CdistType(self.type_base_path, requirement_type_name) - if requirement_object_id: - # Validate object_id if any - core.CdistObject.validate_object_id(requirement_object_id) - elif not requirement_type.is_singleton: - # Only singeltons have no object_id - raise IllegalRequirementError(requirement, "Missing object_id and type is not a singleton.") - + # FIXME: need try/catch here or pass exception from core.CdistObject? + # Instantiate object, which fails if object id is broken + requirement_object = core.CdistObject(requirement_type, self.object_base_path, requirement_object_id) self.log.debug("Recording requirement: " + requirement) self.cdist_object.requirements.append(requirement) From f27730e10b374a1952b825cb874b7089fb12acbf Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 07:45:32 +0100 Subject: [PATCH 43/98] finish rewrite to instance method Signed-off-by: Nico Schottelius --- lib/cdist/core/cdist_object.py | 42 ++++++++++++++++++---------------- 1 file changed, 22 insertions(+), 20 deletions(-) diff --git a/lib/cdist/core/cdist_object.py b/lib/cdist/core/cdist_object.py index 6b1e02b0..81b7e7e9 100644 --- a/lib/cdist/core/cdist_object.py +++ b/lib/cdist/core/cdist_object.py @@ -97,19 +97,21 @@ class CdistObject(object): return os.path.join(type_name, object_id) def validate_object_id(self): + # FIXME: also check that there is no object ID when type is singleton? + """Validate the given object_id and raise IllegalObjectIdError if it's not valid. """ - if object_id: + if self.object_id: if self.object_id.startswith('/'): - raise IllegalObjectIdError(object_id, 'object_id may not start with /') + raise IllegalObjectIdError(self.object_id, 'object_id may not start with /') if OBJECT_MARKER in self.object_id.split(os.sep): - raise IllegalObjectIdError(object_id, 'object_id may not contain \'%s\'' % OBJECT_MARKER) + raise IllegalObjectIdError(self.object_id, 'object_id may not contain \'%s\'' % OBJECT_MARKER) if '//' in self.object_id: - raise IllegalObjectIdError(object_id, 'object_id may not contain //') + raise IllegalObjectIdError(self.object_id, 'object_id may not contain //') # If no object_id and type is not singleton => error out - if not object_id and not self.type.is_singleton: - raise IllegalObjectIdError(object_id, + if not self.object_id and not self.type.is_singleton: + raise IllegalObjectIdError(self.object_id, "Missing object_id and type is not a singleton.") def __init__(self, cdist_type, base_path, object_id=None): @@ -127,19 +129,6 @@ class CdistObject(object): self.code_remote_path = os.path.join(self.path, "code-remote") self.parameter_path = os.path.join(self.path, "parameter") - def __repr__(self): - return '' % self.name - - def __eq__(self, other): - """define equality as 'name is the same'""" - return self.name == other.name - - def __hash__(self): - return hash(self.name) - - def __lt__(self, other): - return isinstance(other, self.__class__) and self.name < other.name - def object_from_name(self, object_name): """Convenience method for creating an object instance from an object name. @@ -154,7 +143,20 @@ class CdistObject(object): type_name, object_id = self.split_name(object_name) return self.__class__(self.type.__class__(type_path, type_name), base_path, object_id=object_id) - def sanitise_object_id(self): + def __repr__(self): + return '' % self.name + + def __eq__(self, other): + """define equality as 'name is the same'""" + return self.name == other.name + + def __hash__(self): + return hash(self.name) + + def __lt__(self, other): + return isinstance(other, self.__class__) and self.name < other.name + + def sanitise_object_id(self): """ Remove leading and trailing slash (one only) """ From 754aba1a15fcee312308fcd54d3757fdae195b59 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 07:47:33 +0100 Subject: [PATCH 44/98] record source in setup_object not in requirements Signed-off-by: Nico Schottelius --- lib/cdist/emulator.py | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/lib/cdist/emulator.py b/lib/cdist/emulator.py index 67f6d373..8174b38f 100644 --- a/lib/cdist/emulator.py +++ b/lib/cdist/emulator.py @@ -140,6 +140,9 @@ class Emulator(object): self.cdist_object.create() self.cdist_object.parameters = self.parameters + # Record / Append source + self.cdist_object.source.append(self.object_source) + def record_requirements(self): """record requirements""" @@ -153,17 +156,16 @@ class Emulator(object): requirement_type_name, requirement_object_id = core.CdistObject.split_name(requirement) # Instantiate type which fails if type does not exist - requirement_type = core.CdistType(self.type_base_path, requirement_type_name) + requirement_type = core.CdistType(self.type_base_path, + requirement_type_name) - # FIXME: need try/catch here or pass exception from core.CdistObject? # Instantiate object, which fails if object id is broken - requirement_object = core.CdistObject(requirement_type, self.object_base_path, requirement_object_id) + requirement_object = core.CdistObject(requirement_type, + self.object_base_path, requirement_object_id) + self.log.debug("Recording requirement: " + requirement) self.cdist_object.requirements.append(requirement) - # Record / Append source - self.cdist_object.source.append(self.object_source) - def record_auto_requirements(self): """An object shall automatically depend on all objects that it defined in it's type manifest. """ From 097b4ea6ada2bd55c0750429218a43871b80f413 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 07:50:11 +0100 Subject: [PATCH 45/98] :%s/self.type/self.cdist_type/g Signed-off-by: Nico Schottelius --- lib/cdist/core/cdist_object.py | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/lib/cdist/core/cdist_object.py b/lib/cdist/core/cdist_object.py index 81b7e7e9..e7ea7a9f 100644 --- a/lib/cdist/core/cdist_object.py +++ b/lib/cdist/core/cdist_object.py @@ -110,20 +110,20 @@ class CdistObject(object): raise IllegalObjectIdError(self.object_id, 'object_id may not contain //') # If no object_id and type is not singleton => error out - if not self.object_id and not self.type.is_singleton: + if not self.object_id and not self.cdist_type.is_singleton: raise IllegalObjectIdError(self.object_id, "Missing object_id and type is not a singleton.") def __init__(self, cdist_type, base_path, object_id=None): - self.type = cdist_type # instance of Type + self.cdist_type = cdist_type # instance of Type self.base_path = base_path self.object_id = object_id self.sanitise_object_id() self.validate_object_id() - self.name = self.join_name(self.type.name, self.object_id) - self.path = os.path.join(self.type.path, self.object_id, OBJECT_MARKER) + self.name = self.join_name(self.cdist_type.name, self.object_id) + self.path = os.path.join(self.cdist_type.path, self.object_id, OBJECT_MARKER) self.absolute_path = os.path.join(self.base_path, self.path) self.code_local_path = os.path.join(self.path, "code-local") self.code_remote_path = os.path.join(self.path, "code-remote") @@ -138,10 +138,10 @@ class CdistObject(object): .object_from_name('__other/object') -> """ - type_path = self.type.base_path + type_path = self.cdist_type.base_path base_path = self.base_path type_name, object_id = self.split_name(object_name) - return self.__class__(self.type.__class__(type_path, type_name), base_path, object_id=object_id) + return self.__class__(self.cdist_type.__class__(type_path, type_name), base_path, object_id=object_id) def __repr__(self): return '' % self.name From 2492d51f6f5d0741096344e13a3a2c54c782d36a Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 07:56:37 +0100 Subject: [PATCH 46/98] make object_from_name() better readable Signed-off-by: Nico Schottelius --- lib/cdist/core/cdist_object.py | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/lib/cdist/core/cdist_object.py b/lib/cdist/core/cdist_object.py index e7ea7a9f..b6bf0903 100644 --- a/lib/cdist/core/cdist_object.py +++ b/lib/cdist/core/cdist_object.py @@ -138,10 +138,15 @@ class CdistObject(object): .object_from_name('__other/object') -> """ - type_path = self.cdist_type.base_path + base_path = self.base_path + type_path = self.cdist_type.base_path + type_name, object_id = self.split_name(object_name) - return self.__class__(self.cdist_type.__class__(type_path, type_name), base_path, object_id=object_id) + + cdist_type = self.cdist_type.__class__(type_path, type_name) + + return self.__class__(cdist_type, base_path, object_id=object_id) def __repr__(self): return '' % self.name From dcd3bcee3258ef6f8bb55047db08151bf2e72770 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 07:57:51 +0100 Subject: [PATCH 47/98] use the great method object_from_name() in emulator Signed-off-by: Nico Schottelius --- lib/cdist/emulator.py | 10 +--------- 1 file changed, 1 insertion(+), 9 deletions(-) diff --git a/lib/cdist/emulator.py b/lib/cdist/emulator.py index 8174b38f..64773334 100644 --- a/lib/cdist/emulator.py +++ b/lib/cdist/emulator.py @@ -154,15 +154,7 @@ class Emulator(object): if len(requirement) == 0: continue - requirement_type_name, requirement_object_id = core.CdistObject.split_name(requirement) - # Instantiate type which fails if type does not exist - requirement_type = core.CdistType(self.type_base_path, - requirement_type_name) - - # Instantiate object, which fails if object id is broken - requirement_object = core.CdistObject(requirement_type, - self.object_base_path, requirement_object_id) - + self.cdist_object.object_from_name(requirement) self.log.debug("Recording requirement: " + requirement) self.cdist_object.requirements.append(requirement) From eadb62e67a9e4136e5321140d8160b01aa4fe931 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 08:44:09 +0100 Subject: [PATCH 48/98] minimal beaufity Signed-off-by: Nico Schottelius --- doc/dev/todo/niconext | 1 - lib/cdist/emulator.py | 4 ++-- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/doc/dev/todo/niconext b/doc/dev/todo/niconext index 34c2f7b0..77cbe986 100644 --- a/doc/dev/todo/niconext +++ b/doc/dev/todo/niconext @@ -1,7 +1,6 @@ - cleanup object_id handling - have a look at singletons - double check verification - - cleanup emulator to create object - adjust tests -------------------------------------------------------------------------------- diff --git a/lib/cdist/emulator.py b/lib/cdist/emulator.py index 64773334..5e95e31c 100644 --- a/lib/cdist/emulator.py +++ b/lib/cdist/emulator.py @@ -151,9 +151,9 @@ class Emulator(object): self.log.debug("reqs = " + requirements) for requirement in requirements.split(" "): # Ignore empty fields - probably the only field anyway - if len(requirement) == 0: - continue + if len(requirement) == 0: continue + # Raises an error, if object cannot be created self.cdist_object.object_from_name(requirement) self.log.debug("Recording requirement: " + requirement) self.cdist_object.requirements.append(requirement) From 921b0c0dffb5d09b624cd384b3aa5bf2de90effc Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 08:49:49 +0100 Subject: [PATCH 49/98] do not submit run/exec types containing echo only Signed-off-by: Nico Schottelius --- doc/man/man7/cdist-hacker.text | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/doc/man/man7/cdist-hacker.text b/doc/man/man7/cdist-hacker.text index 9bdf63d4..646439a3 100644 --- a/doc/man/man7/cdist-hacker.text +++ b/doc/man/man7/cdist-hacker.text @@ -61,12 +61,19 @@ including it. HOW TO SUBMIT A NEW TYPE ------------------------ +For detailled information about types, see cdist-type(7). + Submitting a type works as described above, with the additional requirement that a corresponding manpage named man.text in asciidoc format with the manpage-name "cdist-type__NAME" is included in the type directory AND asciidoc is able to compile it (i.e. do NOT have to many "=" in the second line). +Warning: Submitting "exec" or "run" types that simply echo their parameter in +gencode* will not be accepted, because they are of no use. Every type can output +code and thus such a type introduces redundant functionality that is given by +core cdist already. + SEE ALSO -------- From 1e5226e21c9007484982fe076c13087bea714c5f Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 08:51:40 +0100 Subject: [PATCH 50/98] fix indention errors due to vim c&p Signed-off-by: Nico Schottelius --- lib/cdist/core/cdist_object.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/cdist/core/cdist_object.py b/lib/cdist/core/cdist_object.py index b6bf0903..f425ca60 100644 --- a/lib/cdist/core/cdist_object.py +++ b/lib/cdist/core/cdist_object.py @@ -148,7 +148,7 @@ class CdistObject(object): return self.__class__(cdist_type, base_path, object_id=object_id) - def __repr__(self): + def __repr__(self): return '' % self.name def __eq__(self, other): @@ -161,7 +161,7 @@ class CdistObject(object): def __lt__(self, other): return isinstance(other, self.__class__) and self.name < other.name - def sanitise_object_id(self): + def sanitise_object_id(self): """ Remove leading and trailing slash (one only) """ From 2bc201614a77f99f554992f5b3260f0047c4c807 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 08:54:09 +0100 Subject: [PATCH 51/98] :%s/cdist_object.type/cdist_object.cdist_type/g Signed-off-by: Nico Schottelius --- lib/cdist/core/explorer.py | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/lib/cdist/core/explorer.py b/lib/cdist/core/explorer.py index 43b0339c..bbd2108c 100644 --- a/lib/cdist/core/explorer.py +++ b/lib/cdist/core/explorer.py @@ -121,18 +121,18 @@ class Explorer(object): in the object. """ - self.log.debug("Transfering type explorers for type: %s", cdist_object.type) - self.transfer_type_explorers(cdist_object.type) + self.log.debug("Transfering type explorers for type: %s", cdist_object.cdist_type) + self.transfer_type_explorers(cdist_object.cdist_type) self.log.debug("Transfering object parameters for object: %s", cdist_object.name) self.transfer_object_parameters(cdist_object) - for explorer in self.list_type_explorer_names(cdist_object.type): + for explorer in self.list_type_explorer_names(cdist_object.cdist_type): output = self.run_type_explorer(explorer, cdist_object) self.log.debug("Running type explorer '%s' for object '%s'", explorer, cdist_object.name) cdist_object.explorers[explorer] = output def run_type_explorer(self, explorer, cdist_object): """Run the given type explorer for the given object and return it's output.""" - cdist_type = cdist_object.type + cdist_type = cdist_object.cdist_type env = self.env.copy() env.update({ '__object': os.path.join(self.remote.object_path, cdist_object.path), From a8e9b7feedb7485239f877ce1e5d2f2731930d7f Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 08:55:42 +0100 Subject: [PATCH 52/98] :%s/cdist_object.type/cdist_object.cdist_type/g Signed-off-by: Nico Schottelius --- lib/cdist/core/manifest.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/cdist/core/manifest.py b/lib/cdist/core/manifest.py index 704a3978..8b784229 100644 --- a/lib/cdist/core/manifest.py +++ b/lib/cdist/core/manifest.py @@ -87,7 +87,7 @@ class Manifest(object): self.local.run_script(script, env=env) def run_type_manifest(self, cdist_object): - script = os.path.join(self.local.type_path, cdist_object.type.manifest_path) + script = os.path.join(self.local.type_path, cdist_object.cdist_type.manifest_path) if os.path.isfile(script): env = os.environ.copy() env.update(self.env) @@ -96,7 +96,7 @@ class Manifest(object): '__object_id': cdist_object.object_id, '__object_name': cdist_object.name, '__self': cdist_object.name, - '__type': cdist_object.type.absolute_path, + '__type': cdist_object.cdist_type.absolute_path, '__cdist_manifest': script, }) self.local.run_script(script, env=env) From 8f75a9133fae3a75f459aa5314934bb58db042e5 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 10:38:36 +0100 Subject: [PATCH 53/98] do not fail validation on empty object_id Signed-off-by: Nico Schottelius --- lib/cdist/core/cdist_object.py | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/lib/cdist/core/cdist_object.py b/lib/cdist/core/cdist_object.py index f425ca60..3c2de01b 100644 --- a/lib/cdist/core/cdist_object.py +++ b/lib/cdist/core/cdist_object.py @@ -166,13 +166,15 @@ class CdistObject(object): Remove leading and trailing slash (one only) """ - # Remove leading slash - if self.object_id[0] == '/': - self.object_id = self.object_id[1:] + # Allow empty object id for singletons + if self.object_id: + # Remove leading slash + if self.object_id[0] == '/': + self.object_id = self.object_id[1:] - # Remove trailing slash - if self.object_id[-1] == '/': - self.object_id = self.object_id[:-1] + # Remove trailing slash + if self.object_id[-1] == '/': + self.object_id = self.object_id[:-1] # FIXME: still needed? @property From 0851af7d52e98f30ad5454a000c6a7291b62539c Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 10:39:04 +0100 Subject: [PATCH 54/98] allow object_id to start and end with one /, fail with any // Signed-off-by: Nico Schottelius --- lib/cdist/test/object/__init__.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/cdist/test/object/__init__.py b/lib/cdist/test/object/__init__.py index 0f8c0189..72530910 100644 --- a/lib/cdist/test/object/__init__.py +++ b/lib/cdist/test/object/__init__.py @@ -54,9 +54,9 @@ class ObjectClassTestCase(test.CdistTestCase): class ObjectIdTestCase(test.CdistTestCase): - def test_object_id_starts_with_slash(self): + def test_object_id_contains_double_slash(self): cdist_type = core.CdistType(type_base_path, '__third') - illegal_object_id = '/object_id/may/not/start/with/slash' + illegal_object_id = '/object_id//may/not/contain/double/slash' with self.assertRaises(core.IllegalObjectIdError): core.CdistObject(cdist_type, object_base_path, illegal_object_id) From f12a83f3dddbe6481581b594ba8ee119f00181c7 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 10:41:12 +0100 Subject: [PATCH 55/98] -migration to CdistType error Signed-off-by: Nico Schottelius --- doc/dev/todo/niconext | 3 +++ lib/cdist/core/code.py | 4 ++-- lib/cdist/test/object/__init__.py | 2 +- 3 files changed, 6 insertions(+), 3 deletions(-) diff --git a/doc/dev/todo/niconext b/doc/dev/todo/niconext index 77cbe986..dd20026c 100644 --- a/doc/dev/todo/niconext +++ b/doc/dev/todo/niconext @@ -3,6 +3,9 @@ - double check verification - adjust tests +- remove useless + ERROR: monitoring02: Code that raised the error: + -------------------------------------------------------------------------------- - __user diff --git a/lib/cdist/core/code.py b/lib/cdist/core/code.py index 51912559..7e69f21c 100644 --- a/lib/cdist/core/code.py +++ b/lib/cdist/core/code.py @@ -96,13 +96,13 @@ class Code(object): self.env.update({'__debug': "yes" }) def _run_gencode(self, cdist_object, which): - cdist_type = cdist_object.type + cdist_type = cdist_object.cdist_type script = os.path.join(self.local.type_path, getattr(cdist_type, 'gencode_%s_path' % which)) if os.path.isfile(script): env = os.environ.copy() env.update(self.env) env.update({ - '__type': cdist_object.type.absolute_path, + '__type': cdist_object.cdist_type.absolute_path, '__object': cdist_object.absolute_path, '__object_id': cdist_object.object_id, '__object_name': cdist_object.name, diff --git a/lib/cdist/test/object/__init__.py b/lib/cdist/test/object/__init__.py index 72530910..3a91f709 100644 --- a/lib/cdist/test/object/__init__.py +++ b/lib/cdist/test/object/__init__.py @@ -198,5 +198,5 @@ class ObjectTestCase(test.CdistTestCase): other_name = '__first/man' other_object = self.cdist_object.object_from_name(other_name) self.assertTrue(isinstance(other_object, core.CdistObject)) - self.assertEqual(other_object.type.name, '__first') + self.assertEqual(other_object.cdist_type.name, '__first') self.assertEqual(other_object.object_id, 'man') From 2fce038423813a0d07c294ac1d08e5731ec77367 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 10:43:42 +0100 Subject: [PATCH 56/98] correct catching exception to IllegalObjectIdError Signed-off-by: Nico Schottelius --- lib/cdist/test/emulator/__init__.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/cdist/test/emulator/__init__.py b/lib/cdist/test/emulator/__init__.py index c0037b68..f1ea5832 100644 --- a/lib/cdist/test/emulator/__init__.py +++ b/lib/cdist/test/emulator/__init__.py @@ -79,7 +79,7 @@ class EmulatorTestCase(test.CdistTestCase): os.environ.update(self.env) os.environ['require'] = '__file' emu = emulator.Emulator(argv) - self.assertRaises(emulator.IllegalRequirementError, emu.run) + self.assertRaises(core.IllegalObjectIdError, emu.run) def test_singleton_object_requirement(self): argv = ['__file', '/tmp/foobar'] From 2d6107002357af985d7695082e98caea99ae4a31 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 10:47:40 +0100 Subject: [PATCH 57/98] remove old IllegalRequirementError exception Signed-off-by: Nico Schottelius --- lib/cdist/emulator.py | 10 +--------- 1 file changed, 1 insertion(+), 9 deletions(-) diff --git a/lib/cdist/emulator.py b/lib/cdist/emulator.py index 5e95e31c..8daa61fb 100644 --- a/lib/cdist/emulator.py +++ b/lib/cdist/emulator.py @@ -26,15 +26,6 @@ import os import cdist from cdist import core - -class IllegalRequirementError(cdist.Error): - def __init__(self, requirement, message=None): - self.requirement = requirement - self.message = message or 'Illegal requirement' - - def __str__(self): - return '%s: %s' % (self.message, self.requirement) - class Emulator(object): def __init__(self, argv): self.argv = argv @@ -155,6 +146,7 @@ class Emulator(object): # Raises an error, if object cannot be created self.cdist_object.object_from_name(requirement) + self.log.debug("Recording requirement: " + requirement) self.cdist_object.requirements.append(requirement) From 95cbdeba277b04535f60068e725b07b43138c2c5 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 11:30:11 +0100 Subject: [PATCH 58/98] document /, // behaviour of object id Signed-off-by: Nico Schottelius --- doc/changelog | 3 + doc/dev/todo/niconext | 2 - doc/man/cdist-reference.text.sh | 138 ++++++++++++++++---------------- 3 files changed, 74 insertions(+), 69 deletions(-) diff --git a/doc/changelog b/doc/changelog index dace28dd..899b4b21 100644 --- a/doc/changelog +++ b/doc/changelog @@ -9,7 +9,10 @@ Changelog * Bugfix __user: Correct shadow field in explorer (Matt Coddington) * Bugfix __link: Properly handle existing links (Steven Armstrong) * Bugfix __key_value: More robust implementation (Steven Armstrong) + * Bugfix __user: Fix for changing a user's group by name (Matt Coddington) * New Type: __package_pip + * Bugfix/Cleanup: Correctly allow Object ID to start and end with /, but + not contain //. 2.0.6: 2012-01-28 * Bugfix __apt_ppa: diff --git a/doc/dev/todo/niconext b/doc/dev/todo/niconext index dd20026c..6dafda9a 100644 --- a/doc/dev/todo/niconext +++ b/doc/dev/todo/niconext @@ -1,7 +1,5 @@ - cleanup object_id handling - have a look at singletons - - double check verification - - adjust tests - remove useless ERROR: monitoring02: Code that raised the error: diff --git a/doc/man/cdist-reference.text.sh b/doc/man/cdist-reference.text.sh index 898771c7..bf8d250e 100755 --- a/doc/man/cdist-reference.text.sh +++ b/doc/man/cdist-reference.text.sh @@ -49,10 +49,10 @@ The following global explorers are available: eof ( - cd ../../conf/explorer - for explorer in *; do - echo "- $explorer" - done + cd ../../conf/explorer + for explorer in *; do + echo "- $explorer" + done ) cat << eof @@ -62,77 +62,77 @@ PATHS If not specified otherwise, all paths are relative to the checkout directory. conf/:: - Contains the (static) configuration like manifests, types and explorers. + Contains the (static) configuration like manifests, types and explorers. conf/manifest/init:: - This is the central entry point used by cdist-manifest-init(1). - It is an executable (+x bit set) shell script that can use - values from the explorers to decide which configuration to create - for the specified target host. - It should be primary used to define mapping from configurations to hosts. + This is the central entry point used by cdist-manifest-init(1). + It is an executable (+x bit set) shell script that can use + values from the explorers to decide which configuration to create + for the specified target host. + It should be primary used to define mapping from configurations to hosts. conf/manifest/*:: - All other files in this directory are not directly used by cdist, but you - can seperate configuration mappings, if you have a lot of code in the - manifest/init file. This may also be helpful to have different admins - maintain different groups of hosts. + All other files in this directory are not directly used by cdist, but you + can seperate configuration mappings, if you have a lot of code in the + manifest/init file. This may also be helpful to have different admins + maintain different groups of hosts. conf/explorer/:: - Contains explorers to be run on the target hosts, see cdist-explorer(7). + Contains explorers to be run on the target hosts, see cdist-explorer(7). conf/type/:: - Contains all available types, which are used to provide - some kind of functionality. See cdist-type(7). + Contains all available types, which are used to provide + some kind of functionality. See cdist-type(7). conf/type//:: - Home of the type . + Home of the type . - This directory is referenced by the variable __type (see below). + This directory is referenced by the variable __type (see below). conf/type//man.text:: - Manpage in Asciidoc format (required for inclusion into upstream) + Manpage in Asciidoc format (required for inclusion into upstream) conf/type//manifest:: - Used to generate additional objects from a type. + Used to generate additional objects from a type. conf/type//gencode-local:: - Used to generate code to be executed on the server. + Used to generate code to be executed on the server. conf/type//gencode-remote:: - Used to generate code to be executed on the client. + Used to generate code to be executed on the client. conf/type//parameters/required:: - Parameters required by type, \n seperated list. + Parameters required by type, \n seperated list. conf/type//parameters/optional:: - Parameters optionally accepted by type, \n seperated list. + Parameters optionally accepted by type, \n seperated list. conf/type//explorer:: - Location of the type specific explorers. - This directory is referenced by the variable __type_explorer (see below). - See cdist-explorer(7). + Location of the type specific explorers. + This directory is referenced by the variable __type_explorer (see below). + See cdist-explorer(7). out/:: - This directory contains output of cdist and is usually located - in a temporary directory and thus will be removed after the run. - This directory is referenced by the variable __global (see below). + This directory contains output of cdist and is usually located + in a temporary directory and thus will be removed after the run. + This directory is referenced by the variable __global (see below). out/explorer:: - Output of general explorers. + Output of general explorers. out/object:: - Objects created for the host. + Objects created for the host. out/object/:: - Contains all object specific information. - This directory is referenced by the variable __object (see below). + Contains all object specific information. + This directory is referenced by the variable __object (see below). out/object//explorers:: - Output of type specific explorers, per object. + Output of type specific explorers, per object. tmp_dir:: - A tempdir and a tempfile is used by cdist internally, - which will be removed when the scripts end automatically. + A tempdir and a tempfile is used by cdist internally, + which will be removed when the scripts end automatically. TYPES ----- @@ -141,13 +141,13 @@ The following types are available: eof for type in man7/cdist-type__*.text; do - no_dir="${type#man7/}"; - no_type="${no_dir#cdist-type}"; - name="${no_type%.text}"; - name_no_underline="$(echo $name | sed 's/^__/\\__/g')" - man="${no_dir%.text}(7)" + no_dir="${type#man7/}"; + no_type="${no_dir#cdist-type}"; + name="${no_type%.text}"; + name_no_underline="$(echo $name | sed 's/^__/\\__/g')" + man="${no_dir%.text}(7)" - echo "- $name_no_underline" "($man)" + echo "- $name_no_underline" "($man)" done cat << eof @@ -159,43 +159,47 @@ For object to object communication and tests, the following paths are usable within a object directory: changed:: - This empty file exists in an object directory, if the object has - code to be excuted (either remote or local) + This empty file exists in an object directory, if the object has + code to be excuted (either remote or local) ENVIRONMENT VARIABLES --------------------- __explorer:: - Directory that contains all global explorers. - Available for: explorer + Directory that contains all global explorers. + Available for: explorer __manifest:: - Directory that contains the initial manifest. - Available for: initial manifest + Directory that contains the initial manifest. + Available for: initial manifest __global:: - Directory that contains generic output like explorer. - Available for: initial manifest, type manifest, type gencode + Directory that contains generic output like explorer. + Available for: initial manifest, type manifest, type gencode __object:: - Directory that contains the current object. - Available for: type manifest, type explorer, type gencode + Directory that contains the current object. + Available for: type manifest, type explorer, type gencode __object_id:: - The type unique object id. - Available for: type manifest, type explorer, type gencode - Note: The leading "/" will always be stripped. + The type unique object id. + Available for: type manifest, type explorer, type gencode + + Note: The leading and the trailing "/" will always be stripped (caused by + the filesystem database and ensured by the core). + + Note: Double slashes ("//") will not be fixed and result in an error. __self:: - DEPRECATED: Same as __object_name, do not use anymore, use __object_name instead. - Will be removed in cdist 3.x. + DEPRECATED: Same as __object_name, do not use anymore, use __object_name instead. + Will be removed in cdist 3.x. __object_name:: - The full qualified name of the current object. - Available for: type manifest, type explorer, type gencode + The full qualified name of the current object. + Available for: type manifest, type explorer, type gencode __target_host:: - The host we are deploying to. - Available for: initial manifest, type manifest, type gencode + The host we are deploying to. + Available for: initial manifest, type manifest, type gencode __type:: - Path to the current type. - Available for: type manifest, type gencode + Path to the current type. + Available for: type manifest, type gencode __type_explorer:: - Directory that contains the type explorers. - Available for: type explorer + Directory that contains the type explorers. + Available for: type explorer SEE ALSO From e3ab8ef77ba80301e08ac65d16bc668e22ed2e7c Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 14:25:11 +0100 Subject: [PATCH 59/98] version increment Signed-off-by: Nico Schottelius --- lib/cdist/__init__.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/cdist/__init__.py b/lib/cdist/__init__.py index 664b6456..800bdaa2 100644 --- a/lib/cdist/__init__.py +++ b/lib/cdist/__init__.py @@ -19,7 +19,7 @@ # # -VERSION = "2.0.6" +VERSION = "2.0.7" BANNER = """ .. . .x+=:. s From c8ec4c200aa9b369f9fd3926b18f641598a3cd59 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 14:28:30 +0100 Subject: [PATCH 60/98] repair manpage for __package_pip Signed-off-by: Nico Schottelius --- conf/type/__package_pip/man.text | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/conf/type/__package_pip/man.text b/conf/type/__package_pip/man.text index 1822ffca..5ce45c50 100644 --- a/conf/type/__package_pip/man.text +++ b/conf/type/__package_pip/man.text @@ -1,5 +1,5 @@ cdist-type__package_pip(7) -============================= +========================== Nico Schottelius From f9ab756ee5c6528de17e0c54bc1ddab6b7b03eec Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 14:29:04 +0100 Subject: [PATCH 61/98] cleanup todo Signed-off-by: Nico Schottelius --- doc/dev/todo/niconext | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/doc/dev/todo/niconext b/doc/dev/todo/niconext index 6dafda9a..f81c7570 100644 --- a/doc/dev/todo/niconext +++ b/doc/dev/todo/niconext @@ -1,16 +1,16 @@ +2.0.8 features / cleanups: + - cleanup object_id handling - have a look at singletons - remove useless ERROR: monitoring02: Code that raised the error: --------------------------------------------------------------------------------- - -- __user - add option to include --create-home - ensure that all types, which support --state support present and absent (consistent look and feel) +-------------------------------------------------------------------------------- + - update/create docs - cdist-cache:: How to get use information about the hosts we have been working on [advanced] From 84b6df2e815d8c69d5c004883b62995c354cd24e Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 14:29:44 +0100 Subject: [PATCH 62/98] ++todo for anyone Signed-off-by: Nico Schottelius --- doc/dev/todo/TAKEME | 2 ++ 1 file changed, 2 insertions(+) diff --git a/doc/dev/todo/TAKEME b/doc/dev/todo/TAKEME index 95bda7fb..b40936f6 100644 --- a/doc/dev/todo/TAKEME +++ b/doc/dev/todo/TAKEME @@ -35,3 +35,5 @@ USER INTERFACE TYPES ------ - Add testing framework (proposed by Evax Software) +- __user + add option to include --create-home From 632146114ca07254b0119510758316ffc68ffc37 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 14:30:27 +0100 Subject: [PATCH 63/98] update copyright Signed-off-by: Nico Schottelius --- lib/cdist/core/cdist_object.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/cdist/core/cdist_object.py b/lib/cdist/core/cdist_object.py index 3c2de01b..9937c823 100644 --- a/lib/cdist/core/cdist_object.py +++ b/lib/cdist/core/cdist_object.py @@ -1,7 +1,7 @@ # -*- coding: utf-8 -*- # # 2011 Steven Armstrong (steven-cdist at armstrong.cc) -# 2011 Nico Schottelius (nico-cdist at schottelius.org) +# 2011-2012 Nico Schottelius (nico-cdist at schottelius.org) # # This file is part of cdist. # From 06cf5ec3c94435e1cc82cd349302cb09d2200135 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 14:37:10 +0100 Subject: [PATCH 64/98] check release before releasing... Signed-off-by: Nico Schottelius --- build | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build b/build index ea4ca83c..7da51ded 100755 --- a/build +++ b/build @@ -85,7 +85,7 @@ case "$1" in ;; release) - "$0" clean && "$0" man && "$0" web + ./doc/dev/releasechecklist && "$0" clean && "$0" man && "$0" web ;; speeches) From f8de3afb5f3712eda304b5592682a51a5c1c1645 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 14:37:30 +0100 Subject: [PATCH 65/98] +releasedate Signed-off-by: Nico Schottelius --- doc/changelog | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/changelog b/doc/changelog index 899b4b21..00823886 100644 --- a/doc/changelog +++ b/doc/changelog @@ -4,7 +4,7 @@ Changelog * Changes are always commented with their author in (braces) * Exception: No braces means author == Nico Schottelius -2.0.7: +2.0.7: 2012-02-13 * Bugfix __file: Use chmod after chown/chgrp (Matt Coddington) * Bugfix __user: Correct shadow field in explorer (Matt Coddington) * Bugfix __link: Properly handle existing links (Steven Armstrong) From 762b8e0a3ad9d414281f8b7443254c98a878767e Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 14:48:22 +0100 Subject: [PATCH 66/98] also check date on release Signed-off-by: Nico Schottelius --- doc/dev/releasechecklist | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/doc/dev/releasechecklist b/doc/dev/releasechecklist index 19ab7b18..3473ae0f 100755 --- a/doc/dev/releasechecklist +++ b/doc/dev/releasechecklist @@ -15,11 +15,21 @@ changelog_version=$(grep '^[[:digit:]]' doc/changelog | head -n1 | sed 's/:.*//' #git_version=$(git describe) lib_version=$(grep ^VERSION lib/cdist/__init__.py | sed -e 's/.*= //' -e 's/"//g') +# get date +date_today="$(date +%Y-%m-%d)" +date_changelogn=$(grep '^[[:digit:]]' doc/changelog | head -n1 | sed 's/.*: //') + echo "Ensure you fixed/prepared version files: $files" echo "changelog: $changelog_version" #echo "git: $git_version" echo "lib: $lib_version" +if [ "$date_today" != "$date_changelog" ]; then + echo "Messed up date, not releasing:" + echo "Changelog: $date_changelog" + exit 1 +fi + if [ "$lib_version" != "$changelog_version" ]; then echo "Messed up versions, not releasing" exit 1 From 992584582853f41b1491f80a31384fc19555f55b Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 14:49:36 +0100 Subject: [PATCH 67/98] only need release script for release Signed-off-by: Nico Schottelius --- build | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build b/build index 7da51ded..6b415391 100755 --- a/build +++ b/build @@ -85,7 +85,7 @@ case "$1" in ;; release) - ./doc/dev/releasechecklist && "$0" clean && "$0" man && "$0" web + ./doc/dev/releasechecklist ;; speeches) From edd93aa1f899ca05dd9bf7487bbbf3b67336115a Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 14:55:41 +0100 Subject: [PATCH 68/98] -typo Signed-off-by: Nico Schottelius --- doc/dev/releasechecklist | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/dev/releasechecklist b/doc/dev/releasechecklist index 3473ae0f..eba81dc0 100755 --- a/doc/dev/releasechecklist +++ b/doc/dev/releasechecklist @@ -17,7 +17,7 @@ lib_version=$(grep ^VERSION lib/cdist/__init__.py | sed -e 's/.*= //' -e 's/"//g # get date date_today="$(date +%Y-%m-%d)" -date_changelogn=$(grep '^[[:digit:]]' doc/changelog | head -n1 | sed 's/.*: //') +date_changelog=$(grep '^[[:digit:]]' doc/changelog | head -n1 | sed 's/.*: //') echo "Ensure you fixed/prepared version files: $files" echo "changelog: $changelog_version" From f8868349e6f1fa7694a5aef3220990ec6b8039f6 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 15:01:45 +0100 Subject: [PATCH 69/98] cdist_object.type => cdist_object.cdist_type Signed-off-by: Nico Schottelius --- lib/cdist/config_install.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/cdist/config_install.py b/lib/cdist/config_install.py index f27fff77..7cce240e 100644 --- a/lib/cdist/config_install.py +++ b/lib/cdist/config_install.py @@ -112,7 +112,7 @@ class ConfigInstall(object): # TODO: remove once we are sure that this really never happens. raise cdist.Error("Attempting to run an already finished object: %s", cdist_object) - cdist_type = cdist_object.type + cdist_type = cdist_object.cdist_type # Generate self.log.info("Generating and executing code for " + cdist_object.name) From ba0130594cb51d826f311116dc73caacf2ca518e Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 15:20:33 +0100 Subject: [PATCH 70/98] remove latest before linking to prevent symlink below latest/ Signed-off-by: Nico Schottelius --- build | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build b/build index 6b415391..b994ce00 100755 --- a/build +++ b/build @@ -123,7 +123,7 @@ case "$1" in # Fix ikiwiki, which does not like symlinks for pseudo security ssh tee.schottelius.org \ "cd /home/services/www/nico/www.nico.schottelius.org/www/software/cdist/man && - ln -sf "$version" latest" + rm -f latest && ln -sf "$version" latest" ;; p|pu|pub) From 08612764362c629b9b144db64277abbe7f200b9c Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 16:14:48 +0100 Subject: [PATCH 71/98] remove obsolete MissingEnvironmentVariableError() Signed-off-by: Nico Schottelius --- lib/cdist/__init__.py | 10 ---------- lib/cdist/emulator.py | 2 +- 2 files changed, 1 insertion(+), 11 deletions(-) diff --git a/lib/cdist/__init__.py b/lib/cdist/__init__.py index 800bdaa2..973b61f8 100644 --- a/lib/cdist/__init__.py +++ b/lib/cdist/__init__.py @@ -44,16 +44,6 @@ class Error(Exception): """Base exception class for this project""" pass - -class MissingEnvironmentVariableError(Error): - """Raised when a required environment variable is not set.""" - - def __init__(self, name): - self.name = name - - def __str__(self): - return 'Missing required environment variable: ' + str(self.name) - def file_to_list(filename): """Return list from \n seperated file""" if os.path.isfile(filename): diff --git a/lib/cdist/emulator.py b/lib/cdist/emulator.py index 8daa61fb..687aee93 100644 --- a/lib/cdist/emulator.py +++ b/lib/cdist/emulator.py @@ -1,6 +1,6 @@ # -*- coding: utf-8 -*- # -# 2011 Nico Schottelius (nico-cdist at schottelius.org) +# 2011-2012 Nico Schottelius (nico-cdist at schottelius.org) # # This file is part of cdist. # From d51a177a9545f9d534c24c25239144a6f8bd4b3d Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 16:22:14 +0100 Subject: [PATCH 72/98] invent a generic CdistObjectError and point to definition source (easier debugging) Signed-off-by: Nico Schottelius --- lib/cdist/__init__.py | 12 ++++++++++++ lib/cdist/resolver.py | 2 +- 2 files changed, 13 insertions(+), 1 deletion(-) diff --git a/lib/cdist/__init__.py b/lib/cdist/__init__.py index 973b61f8..4742a937 100644 --- a/lib/cdist/__init__.py +++ b/lib/cdist/__init__.py @@ -44,6 +44,18 @@ class Error(Exception): """Base exception class for this project""" pass +class CdistObjectError(Error): + """Something went wrong with an object""" + + def __init__(self, cdist_object, message): + self.name = cdist_object.name + self.source = " ".join(cdist_object.source) + self.message = message + + + def __str__(self): + return '%s: %s (defined at %s)' % (self.name, self.message, self.source) + def file_to_list(filename): """Return list from \n seperated file""" if os.path.isfile(filename): diff --git a/lib/cdist/resolver.py b/lib/cdist/resolver.py index 24a5e496..368c9eb8 100644 --- a/lib/cdist/resolver.py +++ b/lib/cdist/resolver.py @@ -125,7 +125,7 @@ class DependencyResolver(object): resolved.append(cdist_object) unresolved.remove(cdist_object) except RequirementNotFoundError as e: - raise cdist.Error(cdist_object.name + " requires non-existing " + e.requirement) + raise cdist.CdistObjectError(cdist_object, "requires non-existing " + e.requirement) def __iter__(self): """Iterate over all unique objects while resolving dependencies. From 8f1735fab2b69e4b5c21cacb97230626e08d0cde Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 16:22:46 +0100 Subject: [PATCH 73/98] ++changes(2.0.8) Signed-off-by: Nico Schottelius --- doc/changelog | 3 +++ 1 file changed, 3 insertions(+) diff --git a/doc/changelog b/doc/changelog index 00823886..c241624a 100644 --- a/doc/changelog +++ b/doc/changelog @@ -4,6 +4,9 @@ Changelog * Changes are always commented with their author in (braces) * Exception: No braces means author == Nico Schottelius +2.0.8: + * Cleanup: Better hint to source of error + 2.0.7: 2012-02-13 * Bugfix __file: Use chmod after chown/chgrp (Matt Coddington) * Bugfix __user: Correct shadow field in explorer (Matt Coddington) From c9ae06db6428855a3d9d849efd1019346b203c06 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Mon, 13 Feb 2012 16:27:41 +0100 Subject: [PATCH 74/98] do not setup __debug - let the user do if required - do not interfere type with core Signed-off-by: Nico Schottelius --- doc/changelog | 2 ++ lib/cdist/core/code.py | 3 --- lib/cdist/core/explorer.py | 2 -- 3 files changed, 2 insertions(+), 5 deletions(-) diff --git a/doc/changelog b/doc/changelog index c241624a..2d2d7a48 100644 --- a/doc/changelog +++ b/doc/changelog @@ -6,6 +6,8 @@ Changelog 2.0.8: * Cleanup: Better hint to source of error + * Cleanup: Remove support for __debug variable in manifests (Type != Core + debugging) 2.0.7: 2012-02-13 * Bugfix __file: Use chmod after chown/chgrp (Matt Coddington) diff --git a/lib/cdist/core/code.py b/lib/cdist/core/code.py index 7e69f21c..2ffef9cf 100644 --- a/lib/cdist/core/code.py +++ b/lib/cdist/core/code.py @@ -92,9 +92,6 @@ class Code(object): '__global': self.local.out_path, } - if log.getEffectiveLevel() == logging.DEBUG: - self.env.update({'__debug': "yes" }) - def _run_gencode(self, cdist_object, which): cdist_type = cdist_object.cdist_type script = os.path.join(self.local.type_path, getattr(cdist_type, 'gencode_%s_path' % which)) diff --git a/lib/cdist/core/explorer.py b/lib/cdist/core/explorer.py index bbd2108c..d49b7ac4 100644 --- a/lib/cdist/core/explorer.py +++ b/lib/cdist/core/explorer.py @@ -73,8 +73,6 @@ class Explorer(object): '__target_host': self.target_host, '__explorer': self.remote.global_explorer_path, } - if self.log.getEffectiveLevel() == logging.DEBUG: - self.env.update({'__debug': "yes" }) self._type_explorers_transferred = [] ### global From 861b13ffe48ae5ed5867ec9efd9f0fa92145fc71 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Tue, 14 Feb 2012 11:12:17 +0100 Subject: [PATCH 75/98] record sanitised object, not the user supplied one, as requirement Signed-off-by: Nico Schottelius --- lib/cdist/emulator.py | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/lib/cdist/emulator.py b/lib/cdist/emulator.py index 687aee93..0979182a 100644 --- a/lib/cdist/emulator.py +++ b/lib/cdist/emulator.py @@ -145,10 +145,14 @@ class Emulator(object): if len(requirement) == 0: continue # Raises an error, if object cannot be created - self.cdist_object.object_from_name(requirement) + cdist_object = self.cdist_object.object_from_name(requirement) self.log.debug("Recording requirement: " + requirement) - self.cdist_object.requirements.append(requirement) + + # Save the sanitised version, not the user supplied one + # (__file//bar => __file/bar) + # This ensures pattern matching is done against sanitised list + self.cdist_object.requirements.append(cdist_object.name) def record_auto_requirements(self): """An object shall automatically depend on all objects that it defined in it's type manifest. From df54ab328435781f0e098c60894f95382c8e3cc4 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Tue, 14 Feb 2012 11:15:02 +0100 Subject: [PATCH 76/98] mark same algorithmus for deps in logs Signed-off-by: Nico Schottelius --- doc/dev/logs/2012-02-13.dependencies | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) create mode 100644 doc/dev/logs/2012-02-13.dependencies diff --git a/doc/dev/logs/2012-02-13.dependencies b/doc/dev/logs/2012-02-13.dependencies new file mode 100644 index 00000000..3b0f3f21 --- /dev/null +++ b/doc/dev/logs/2012-02-13.dependencies @@ -0,0 +1,23 @@ +possible dependencies: + + - unix pattern __foo/* + - object: __foo//bar, __foo/bar + - singleton with object_id: __foo/singleton + - singleton without object_id: __foo/ + +solving dependencies: + + solve_dep(object, run_list): + - list = [me] + - if status == IN_DEPENDENCY: + fail: circular dependency + - status = IN_DEPENDENCY + - create_list_of_deps(object) + - try pattern expansion + - for each dependency: + if object does not exist: + fail + else: + list.append(solve_dep(object, run_list)): + - status == IN_LIST + - return [me, dependencies [, dependencies of dependencies]] From 0082b7f07cd821b80f24fb8d23524706bba531d9 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Tue, 14 Feb 2012 12:41:13 +0100 Subject: [PATCH 77/98] allow objects to start with /, but not to contain //; sanitise after validation Signed-off-by: Nico Schottelius --- lib/cdist/core/cdist_object.py | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/lib/cdist/core/cdist_object.py b/lib/cdist/core/cdist_object.py index 9937c823..e12bcfbd 100644 --- a/lib/cdist/core/cdist_object.py +++ b/lib/cdist/core/cdist_object.py @@ -102,8 +102,6 @@ class CdistObject(object): """Validate the given object_id and raise IllegalObjectIdError if it's not valid. """ if self.object_id: - if self.object_id.startswith('/'): - raise IllegalObjectIdError(self.object_id, 'object_id may not start with /') if OBJECT_MARKER in self.object_id.split(os.sep): raise IllegalObjectIdError(self.object_id, 'object_id may not contain \'%s\'' % OBJECT_MARKER) if '//' in self.object_id: @@ -119,8 +117,8 @@ class CdistObject(object): self.base_path = base_path self.object_id = object_id - self.sanitise_object_id() self.validate_object_id() + self.sanitise_object_id() self.name = self.join_name(self.cdist_type.name, self.object_id) self.path = os.path.join(self.cdist_type.path, self.object_id, OBJECT_MARKER) From 365c629db9578790725e8dd981894f62abc1b97e Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Tue, 14 Feb 2012 13:55:50 +0100 Subject: [PATCH 78/98] update variable availbility list in reference Signed-off-by: Nico Schottelius --- doc/man/cdist-reference.text.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/doc/man/cdist-reference.text.sh b/doc/man/cdist-reference.text.sh index bf8d250e..81e58ab2 100755 --- a/doc/man/cdist-reference.text.sh +++ b/doc/man/cdist-reference.text.sh @@ -167,7 +167,7 @@ ENVIRONMENT VARIABLES --------------------- __explorer:: Directory that contains all global explorers. - Available for: explorer + Available for: explorer, type explorer __manifest:: Directory that contains the initial manifest. Available for: initial manifest @@ -193,7 +193,7 @@ __object_name:: Available for: type manifest, type explorer, type gencode __target_host:: The host we are deploying to. - Available for: initial manifest, type manifest, type gencode + Available for: explorer, initial manifest, type explorer, type manifest, type gencode __type:: Path to the current type. Available for: type manifest, type gencode From 2b0c2737151b52d38aa449b9cefc42fa19957cbb Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Tue, 14 Feb 2012 18:04:00 +0100 Subject: [PATCH 79/98] state_should is being populated in manifest, if not given Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/gencode-remote | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/conf/type/__start_on_boot/gencode-remote b/conf/type/__start_on_boot/gencode-remote index 09c4912d..6618b9b0 100755 --- a/conf/type/__start_on_boot/gencode-remote +++ b/conf/type/__start_on_boot/gencode-remote @@ -19,12 +19,7 @@ # # -if [ -f "$__object/parameter/state" ]; then - state_should="$(cat "$__object/parameter/state")" -else - state_should="present" -fi - +state_should="$(cat "$__object/parameter/state")" state_is=$(cat "$__object/explorer/state") # Nothing todo, go away From 2f16b08bb0247e7ba5454f43b2dea6bf33691636 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Tue, 14 Feb 2012 20:31:02 +0100 Subject: [PATCH 80/98] also copy over the .css for manpages Signed-off-by: Nico Schottelius --- build | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/build b/build index b994ce00..2d98e862 100755 --- a/build +++ b/build @@ -113,8 +113,8 @@ case "$1" in # cp ${SPEECHESDIR}/*.pdf ${WEBDIR}/${WEBBASE}/speeches # git describe > ${WEBDIR}/${WEBBASE}/man/VERSION - cp ${MAN1DSTDIR}/*.html ${WEBMAN}/man1 - cp ${MAN7DSTDIR}/*.html ${WEBMAN}/man7 + cp ${MAN1DSTDIR}/*.html ${MAN1DSTDIR}/*.css ${WEBMAN}/man1 + cp ${MAN7DSTDIR}/*.html ${MAN7DSTDIR}/*.css ${WEBMAN}/man7 cd ${WEBDIR} && git add ${WEBBASE} cd ${WEBDIR} && git commit -m "cdist update" ${WEBBASE} ${WEBPAGE} From 5d47eb849f5f8f78a8a63932316e14da894323f9 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Tue, 14 Feb 2012 20:31:16 +0100 Subject: [PATCH 81/98] some stuff to be fixed Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/gencode-remote | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/conf/type/__start_on_boot/gencode-remote b/conf/type/__start_on_boot/gencode-remote index 6618b9b0..3db7293f 100755 --- a/conf/type/__start_on_boot/gencode-remote +++ b/conf/type/__start_on_boot/gencode-remote @@ -35,13 +35,13 @@ case "$state_should" in echo sed -i /etc/rc.conf \'s/^\\(DAEMONS=.*\\))/\\1 $name)/\' ;; debian|ubuntu) - # This does not work as expected: + # FIXME: This does not work as expected: # insserv: warning: current start runlevel(s) (3 4 5) of script `postfix' overwrites defaults (2 3 4 5). #echo update-rc.d \"$name\" defaults echo update-rc.d \"$name\" defaults ;; -# Disabled until the explorer is checked +# FIXME: Disabled until the explorer is checked # gentoo) # echo rc-update add \"$name\" default # ;; @@ -60,13 +60,14 @@ case "$state_should" in absent) case "$os" in archlinux) - echo sed -i /etc/rc.conf -e \"s/ $name / /g\" -e \"s/($name/(/\" -e \"s/ $name)/)/\" + # Replace a) at the beginning b) in the middle c) end d) only + echo "sed -i /etc/rc.conf -e 's/^\(DAEMONS=(\)$name /\1/' -e 's/^\(DAEMONS=(.* \)$name \(.*\)/\1\2/' -e 's/^\(DAEMONS=(.*\) $name)/\1)/' -e 's/^\(DAEMONS=(\)$name)/\1)/'" ;; debian|ubuntu) echo update-rc.d -f \"$name\" remove ;; -# Disabled until the explorer is checked +# FIXME: Disabled until the explorer is checked # gentoo) # echo rc-update del \"$name\" # ;; From d427af2ee33875f271c413ecde5421640448ae72 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 15 Feb 2012 08:50:03 +0100 Subject: [PATCH 82/98] add hint on incomplete type Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/man.text | 3 +++ 1 file changed, 3 insertions(+) diff --git a/conf/type/__start_on_boot/man.text b/conf/type/__start_on_boot/man.text index e9691401..0e75c9ab 100644 --- a/conf/type/__start_on_boot/man.text +++ b/conf/type/__start_on_boot/man.text @@ -13,6 +13,9 @@ DESCRIPTION This cdist type allows you to enable or disable stuff to be started at boot of your operating system. +Warning: This type has not been tested intensively and is not fully +supported (i.e. gentoo and *bsd are not implemented). + REQUIRED PARAMETERS ------------------- From 824ec459ea3ce1dbc2c2751071a42eb235eae66e Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 15 Feb 2012 08:50:26 +0100 Subject: [PATCH 83/98] cleanups in gencode Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/gencode-remote | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/conf/type/__start_on_boot/gencode-remote b/conf/type/__start_on_boot/gencode-remote index 3db7293f..f1788d4b 100755 --- a/conf/type/__start_on_boot/gencode-remote +++ b/conf/type/__start_on_boot/gencode-remote @@ -32,13 +32,10 @@ case "$state_should" in present) case "$os" in archlinux) - echo sed -i /etc/rc.conf \'s/^\\(DAEMONS=.*\\))/\\1 $name)/\' + echo "sed -i /etc/rc.conf \'s/^\\(DAEMONS=.*\\))/\\1 $name)/\'" ;; debian|ubuntu) - # FIXME: This does not work as expected: - # insserv: warning: current start runlevel(s) (3 4 5) of script `postfix' overwrites defaults (2 3 4 5). - #echo update-rc.d \"$name\" defaults - echo update-rc.d \"$name\" defaults + echo "update-rc.d \"$name\" defaults >/dev/null" ;; # FIXME: Disabled until the explorer is checked @@ -61,7 +58,7 @@ case "$state_should" in case "$os" in archlinux) # Replace a) at the beginning b) in the middle c) end d) only - echo "sed -i /etc/rc.conf -e 's/^\(DAEMONS=(\)$name /\1/' -e 's/^\(DAEMONS=(.* \)$name \(.*\)/\1\2/' -e 's/^\(DAEMONS=(.*\) $name)/\1)/' -e 's/^\(DAEMONS=(\)$name)/\1)/'" + echo "sed -i /etc/rc.conf -e 's/^\\(DAEMONS=(\\)$name /\\1/' -e 's/^\\(DAEMONS=(.* \\)$name \\(.*\\)/\\1\\2/' -e 's/^\\(DAEMONS=(.*\\) $name)/\\1)/' -e 's/^\\(DAEMONS=(\\)$name)/\\1)/'" ;; debian|ubuntu) echo update-rc.d -f \"$name\" remove From be670597253d1e713ba79416b2392f51108e4ae7 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 15 Feb 2012 09:27:11 +0100 Subject: [PATCH 84/98] print name, not object (user does not need to see python way of things) Signed-off-by: Nico Schottelius --- lib/cdist/emulator.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/cdist/emulator.py b/lib/cdist/emulator.py index 0979182a..6d6050e8 100644 --- a/lib/cdist/emulator.py +++ b/lib/cdist/emulator.py @@ -125,7 +125,7 @@ class Emulator(object): if self.cdist_object.exists: if self.cdist_object.parameters != self.parameters: raise cdist.Error("Object %s already exists with conflicting parameters:\n%s: %s\n%s: %s" - % (self.cdist_object, " ".join(self.cdist_object.source), self.cdist_object.parameters, self.object_source, self.parameters) + % (self.cdist_object.name, " ".join(self.cdist_object.source), self.cdist_object.parameters, self.object_source, self.parameters) ) else: self.cdist_object.create() From 46e6ea4308dd95462e74e3292a5754c4e21cdcc0 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 15 Feb 2012 09:27:11 +0100 Subject: [PATCH 85/98] print name, not object (user does not need to see python way of things) Signed-off-by: Nico Schottelius --- lib/cdist/emulator.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/cdist/emulator.py b/lib/cdist/emulator.py index 0979182a..6d6050e8 100644 --- a/lib/cdist/emulator.py +++ b/lib/cdist/emulator.py @@ -125,7 +125,7 @@ class Emulator(object): if self.cdist_object.exists: if self.cdist_object.parameters != self.parameters: raise cdist.Error("Object %s already exists with conflicting parameters:\n%s: %s\n%s: %s" - % (self.cdist_object, " ".join(self.cdist_object.source), self.cdist_object.parameters, self.object_source, self.parameters) + % (self.cdist_object.name, " ".join(self.cdist_object.source), self.cdist_object.parameters, self.object_source, self.parameters) ) else: self.cdist_object.create() From 67abdb339978f231ce64cf0940ee9e85ba9f59c8 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 15 Feb 2012 12:46:36 +0100 Subject: [PATCH 86/98] +lunchlogfile Signed-off-by: Nico Schottelius --- doc/dev/logs/2012-02-15.steven | 120 +++++++++++++++++++++++++++++++++ 1 file changed, 120 insertions(+) create mode 100644 doc/dev/logs/2012-02-15.steven diff --git a/doc/dev/logs/2012-02-15.steven b/doc/dev/logs/2012-02-15.steven new file mode 100644 index 00000000..96bccb9f --- /dev/null +++ b/doc/dev/logs/2012-02-15.steven @@ -0,0 +1,120 @@ +- parameter/setting default from manifest + - current bug + - proposal 1: parameter/default/$name (for optional ones) + - new way + - catches --state absent|present + - needs changes of types + - also possible for explorer + - support for it in core? + - handling of ${o} $o "$o" ? + - handling which variables? + - introduction of "templating language" + - aka macros + - possible problems: + - inconsistency + - redoing shell functionality + - raising expectations for more templating from users + - possible benefit + - no need for eval + - once in core, not everytime in type + - OTOH: one extra word. + - a=$(cat $__object/parameter/name) vs. $(eval $(cat $__object/parameter/name)) + - only possible for static defaults + - --name overrides name not possible vs. object_id + - Is this the only case???? + - if yes: don't care. + - possible solution: + - echo '/$__object_id' > typename/parameter/default/name + - eval $(cat $__object/parameter/name) + - probably allows code injection + - is possible anyway??? + - $(cat /etc/shadow) + - other eval side effects??? + - none: go for it + - some: have headache + - many: don't do + - proposal 2: 2 dbs (user input vs. stuff changable by type) + - explicit 2nd db [parameter_user and parameter/] + - not very clean (both agreed) + - proposal 3: parameter are read-only + - breaks current types (in core probably elsewhere) + - can't enforce, but user is on his own => breaks, her problem + + clean seperation between core and type (nico) + - parameter belongs to type not core (steven) + - proposal 4: core ignores changes in parameter/* of object + - implicit 2nd db [see automagic below] + - steven+++ + - does not work with divergent emulator not being in core + - because emulators primary db __is__ fs. + +1 manifest: + +__foo bar == emulator +echo present > $__global/object/__foo/bar/parameter/state + +# fails +__foo bar == emulator + +! automagic / filesystem + ! fsproperty: + - kill, write explicitly to disk + + - implicit/automatic writes/read to fs + - explicit interfaces are better then implicit + - same problems as in cdist 1.x to 2.x move! (environment!) + - format on disk should not change/dictate code flow + - degrade python to shell (nico++! steven--) + - user should not care about python, ruby, .net or ASM implementation (steven++ nico++) + + ? proposal 1: diverge emulator / core + - emulator verifies input + - emulator writes to fs + - core reads/syncs from/to fs before passing control to user + + ? proposal 2: emulator is dumb and passes data to core + - core creates objects + - no fs involved + - core reads/syncs from/to fs before passing control to user + - passing: + - full objects via pickle + - parameters only + - how??? + - unix socket? + - not everywhere possible? + - tcp / ip + - not everywhere possible + - chroot / local only + - rfc 1149 + - not everywhere possible + - missing avian carriers + - 0mq + - not everywhere possible + - not installed + - shm (ipcs and friends) + - not everywhere possible + - no /dev/shm, different libraries? cleanups needed... + - what speaks against FS? + - emulator_input/.../ + + - nico: to fancy probably + +! boolean implementation + - nico: + - parameters/boolean: document + - argparse changes (consider parameters/boolean) + - create + - can be implemented with changes in emulator + - use store_true, del if false => never seen by core + - INDEPENDENT INDEPENDT OF FS.PROPERTIES!!111111! + +- emulator: + - how much integrated into core + - also: using CdistObject???? + - dependency on filesystem: good (nico) | bad (steven) + +- singleton / support without object_id + + +- logging divergent between emulator / core + - no problem (nico) + - may be helpful (steven) From 6ec57acce6fbd52211c95cbb9f4124f8288d741f Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 15 Feb 2012 13:08:29 +0100 Subject: [PATCH 87/98] ++logchanges Signed-off-by: Nico Schottelius --- doc/dev/logs/2012-02-15.steven | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/doc/dev/logs/2012-02-15.steven b/doc/dev/logs/2012-02-15.steven index 96bccb9f..2d513728 100644 --- a/doc/dev/logs/2012-02-15.steven +++ b/doc/dev/logs/2012-02-15.steven @@ -1,4 +1,7 @@ - parameter/setting default from manifest + ==> BRANCH[feature_default_parameters], + ==> PERSON[Steven or Nico] + ==> PROPOSAL(1) - current bug - proposal 1: parameter/default/$name (for optional ones) - new way @@ -58,6 +61,9 @@ __foo bar == emulator ! automagic / filesystem ! fsproperty: - kill, write explicitly to disk + ==> BRANCH[cleanup_fsproperty] + ==> PERSON[Steven] + ==> PROPOSAL(just cleanup) - implicit/automatic writes/read to fs - explicit interfaces are better then implicit @@ -99,6 +105,8 @@ __foo bar == emulator - nico: to fancy probably ! boolean implementation + ==> BRANCH[feature_boolean_parameter] + ==> PERSON[Steven] - nico: - parameters/boolean: document - argparse changes (consider parameters/boolean) @@ -113,7 +121,11 @@ __foo bar == emulator - dependency on filesystem: good (nico) | bad (steven) - singleton / support without object_id + - not discussed +- __apt_ppa: + ==> BRANCH[bugfix_do_not_change_state_in_manifest] + ==> PERSON[Nico] - logging divergent between emulator / core - no problem (nico) From ddb5bd16c923c5aabe465115ca1cb0819dde2cc3 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 15 Feb 2012 13:36:05 +0100 Subject: [PATCH 88/98] also support @daemon syntax from rc.conf Signed-off-by: Nico Schottelius --- conf/type/__start_on_boot/gencode-remote | 3 ++- doc/dev/todo/niconext | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/conf/type/__start_on_boot/gencode-remote b/conf/type/__start_on_boot/gencode-remote index f1788d4b..be2bd98b 100755 --- a/conf/type/__start_on_boot/gencode-remote +++ b/conf/type/__start_on_boot/gencode-remote @@ -58,7 +58,8 @@ case "$state_should" in case "$os" in archlinux) # Replace a) at the beginning b) in the middle c) end d) only - echo "sed -i /etc/rc.conf -e 's/^\\(DAEMONS=(\\)$name /\\1/' -e 's/^\\(DAEMONS=(.* \\)$name \\(.*\\)/\\1\\2/' -e 's/^\\(DAEMONS=(.*\\) $name)/\\1)/' -e 's/^\\(DAEMONS=(\\)$name)/\\1)/'" + # Support @name as well...makes it more ugly, but well... + echo "sed -i /etc/rc.conf -e 's/^\\(DAEMONS=(\\)@\\{0,1\\}$name /\\1/' -e 's/^\\(DAEMONS=(.* \\)@\\{0,1\\}$name \\(.*\\)/\\1\\2/' -e 's/^\\(DAEMONS=(.*\\) @\\{0,1\\}$name)/\\1)/' -e 's/^\\(DAEMONS=(\\)@\\{0,1\\}$name)/\\1)/'" ;; debian|ubuntu) echo update-rc.d -f \"$name\" remove diff --git a/doc/dev/todo/niconext b/doc/dev/todo/niconext index f81c7570..828ff917 100644 --- a/doc/dev/todo/niconext +++ b/doc/dev/todo/niconext @@ -1,4 +1,4 @@ -2.0.8 features / cleanups: +- introduce default parameters - cleanup object_id handling - have a look at singletons From 362bdcdbdddcc013e66d79877c38549f5dc1b8de Mon Sep 17 00:00:00 2001 From: Steven Armstrong Date: Wed, 15 Feb 2012 13:57:45 +0100 Subject: [PATCH 89/98] implement boolean parameters Signed-off-by: Steven Armstrong --- .../fixtures/conf/type/__arguments_boolean/parameter/boolean | 2 ++ .../fixtures/conf/type/__arguments_optional/parameter/optional | 1 + .../fixtures/conf/type/__arguments_required/parameter/required | 2 ++ .../type/fixtures/__with_boolean_parameters/parameter/boolean | 2 ++ lib/cdist/test/type/fixtures/__without_boolean_parameters/.keep | 0 5 files changed, 7 insertions(+) create mode 100644 lib/cdist/test/emulator/fixtures/conf/type/__arguments_boolean/parameter/boolean create mode 100644 lib/cdist/test/emulator/fixtures/conf/type/__arguments_optional/parameter/optional create mode 100644 lib/cdist/test/emulator/fixtures/conf/type/__arguments_required/parameter/required create mode 100644 lib/cdist/test/type/fixtures/__with_boolean_parameters/parameter/boolean create mode 100644 lib/cdist/test/type/fixtures/__without_boolean_parameters/.keep diff --git a/lib/cdist/test/emulator/fixtures/conf/type/__arguments_boolean/parameter/boolean b/lib/cdist/test/emulator/fixtures/conf/type/__arguments_boolean/parameter/boolean new file mode 100644 index 00000000..3215c409 --- /dev/null +++ b/lib/cdist/test/emulator/fixtures/conf/type/__arguments_boolean/parameter/boolean @@ -0,0 +1,2 @@ +boolean1 +boolean2 diff --git a/lib/cdist/test/emulator/fixtures/conf/type/__arguments_optional/parameter/optional b/lib/cdist/test/emulator/fixtures/conf/type/__arguments_optional/parameter/optional new file mode 100644 index 00000000..31647628 --- /dev/null +++ b/lib/cdist/test/emulator/fixtures/conf/type/__arguments_optional/parameter/optional @@ -0,0 +1 @@ +optional1 diff --git a/lib/cdist/test/emulator/fixtures/conf/type/__arguments_required/parameter/required b/lib/cdist/test/emulator/fixtures/conf/type/__arguments_required/parameter/required new file mode 100644 index 00000000..e0fba2c9 --- /dev/null +++ b/lib/cdist/test/emulator/fixtures/conf/type/__arguments_required/parameter/required @@ -0,0 +1,2 @@ +required1 +required2 diff --git a/lib/cdist/test/type/fixtures/__with_boolean_parameters/parameter/boolean b/lib/cdist/test/type/fixtures/__with_boolean_parameters/parameter/boolean new file mode 100644 index 00000000..3215c409 --- /dev/null +++ b/lib/cdist/test/type/fixtures/__with_boolean_parameters/parameter/boolean @@ -0,0 +1,2 @@ +boolean1 +boolean2 diff --git a/lib/cdist/test/type/fixtures/__without_boolean_parameters/.keep b/lib/cdist/test/type/fixtures/__without_boolean_parameters/.keep new file mode 100644 index 00000000..e69de29b From 0760ff3c94edefc815697caae1807ae7894771c0 Mon Sep 17 00:00:00 2001 From: Steven Armstrong Date: Wed, 15 Feb 2012 14:44:16 +0100 Subject: [PATCH 90/98] implement boolean parameters, forgotten files ;-) Signed-off-by: Steven Armstrong --- lib/cdist/core/cdist_type.py | 17 +++++++++ lib/cdist/emulator.py | 5 ++- lib/cdist/test/emulator/__init__.py | 58 ++++++++++++++++++++++++++++- lib/cdist/test/type/__init__.py | 11 ++++++ 4 files changed, 89 insertions(+), 2 deletions(-) diff --git a/lib/cdist/core/cdist_type.py b/lib/cdist/core/cdist_type.py index 55609e7e..1d2472c4 100644 --- a/lib/cdist/core/cdist_type.py +++ b/lib/cdist/core/cdist_type.py @@ -82,6 +82,7 @@ class CdistType(object): self.__explorers = None self.__required_parameters = None self.__optional_parameters = None + self.__boolean_parameters = None def __repr__(self): return '' % self.name @@ -144,3 +145,19 @@ class CdistType(object): finally: self.__optional_parameters = parameters return self.__optional_parameters + + @property + def boolean_parameters(self): + """Return a list of boolean parameters""" + if not self.__boolean_parameters: + parameters = [] + try: + with open(os.path.join(self.absolute_path, "parameter", "boolean")) as fd: + for line in fd: + parameters.append(line.strip()) + except EnvironmentError: + # error ignored + pass + finally: + self.__boolean_parameters = parameters + return self.__boolean_parameters diff --git a/lib/cdist/emulator.py b/lib/cdist/emulator.py index 6d6050e8..c4b84feb 100644 --- a/lib/cdist/emulator.py +++ b/lib/cdist/emulator.py @@ -87,7 +87,7 @@ class Emulator(object): def commandline(self): """Parse command line""" - parser = argparse.ArgumentParser(add_help=False) + parser = argparse.ArgumentParser(add_help=False, argument_default=argparse.SUPPRESS) for parameter in self.cdist_type.optional_parameters: argument = "--" + parameter @@ -95,6 +95,9 @@ class Emulator(object): for parameter in self.cdist_type.required_parameters: argument = "--" + parameter parser.add_argument(argument, dest=parameter, action='store', required=True) + for parameter in self.cdist_type.boolean_parameters: + argument = "--" + parameter + parser.add_argument(argument, dest=parameter, action='store_const', const='') # If not singleton support one positional parameter if not self.cdist_type.is_singleton: diff --git a/lib/cdist/test/emulator/__init__.py b/lib/cdist/test/emulator/__init__.py index f1ea5832..370d3d82 100644 --- a/lib/cdist/test/emulator/__init__.py +++ b/lib/cdist/test/emulator/__init__.py @@ -126,7 +126,7 @@ class AutoRequireEmulatorTestCase(test.CdistTestCase): self.assertEqual(sorted(cdist_object.requirements), sorted(expected)) -class ArgumentsWithDashesTestCase(test.CdistTestCase): +class ArgumentsTestCase(test.CdistTestCase): def setUp(self): self.temp_dir = self.mkdtemp() @@ -159,3 +159,59 @@ class ArgumentsWithDashesTestCase(test.CdistTestCase): cdist_type = core.CdistType(self.local.type_path, '__arguments_with_dashes') cdist_object = core.CdistObject(cdist_type, self.local.object_path, 'some-id') self.assertTrue('with-dash' in cdist_object.parameters) + + def test_boolean(self): + type_name = '__arguments_boolean' + object_id = 'some-id' + argv = [type_name, object_id, '--boolean1'] + os.environ.update(self.env) + emu = emulator.Emulator(argv) + emu.run() + + cdist_type = core.CdistType(self.local.type_path, type_name) + cdist_object = core.CdistObject(cdist_type, self.local.object_path, object_id) + self.assertTrue('boolean1' in cdist_object.parameters) + self.assertFalse('boolean2' in cdist_object.parameters) + # empty file -> True + self.assertTrue(cdist_object.parameters['boolean1'] == '') + + def test_required(self): + type_name = '__arguments_required' + object_id = 'some-id' + value = 'some value' + argv = [type_name, object_id, '--required1', value, '--required2', value] + os.environ.update(self.env) + emu = emulator.Emulator(argv) + emu.run() + + cdist_type = core.CdistType(self.local.type_path, type_name) + cdist_object = core.CdistObject(cdist_type, self.local.object_path, object_id) + self.assertTrue('required1' in cdist_object.parameters) + self.assertTrue('required2' in cdist_object.parameters) + self.assertEqual(cdist_object.parameters['required1'], value) + self.assertEqual(cdist_object.parameters['required2'], value) + +# def test_required_missing(self): +# type_name = '__arguments_required' +# object_id = 'some-id' +# value = 'some value' +# argv = [type_name, object_id, '--required1', value] +# os.environ.update(self.env) +# emu = emulator.Emulator(argv) +# +# self.assertRaises(SystemExit, emu.run) + + def test_optional(self): + type_name = '__arguments_optional' + object_id = 'some-id' + value = 'some value' + argv = [type_name, object_id, '--optional1', value] + os.environ.update(self.env) + emu = emulator.Emulator(argv) + emu.run() + + cdist_type = core.CdistType(self.local.type_path, type_name) + cdist_object = core.CdistObject(cdist_type, self.local.object_path, object_id) + self.assertTrue('optional1' in cdist_object.parameters) + self.assertFalse('optional2' in cdist_object.parameters) + self.assertEqual(cdist_object.parameters['optional1'], value) diff --git a/lib/cdist/test/type/__init__.py b/lib/cdist/test/type/__init__.py index 2ef14a4c..5e774aa9 100644 --- a/lib/cdist/test/type/__init__.py +++ b/lib/cdist/test/type/__init__.py @@ -145,3 +145,14 @@ class TypeTestCase(test.CdistTestCase): base_path = fixtures cdist_type = core.CdistType(base_path, '__without_optional_parameters') self.assertEqual(cdist_type.optional_parameters, []) + + def test_with_boolean_parameters(self): + base_path = fixtures + cdist_type = core.CdistType(base_path, '__with_boolean_parameters') + self.assertEqual(cdist_type.boolean_parameters, ['boolean1', 'boolean2']) + + def test_without_boolean_parameters(self): + base_path = fixtures + cdist_type = core.CdistType(base_path, '__without_boolean_parameters') + self.assertEqual(cdist_type.boolean_parameters, []) + From a4882e7e30a40c453735f4e727f267a9e759dcd8 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 15 Feb 2012 16:17:49 +0100 Subject: [PATCH 91/98] remove useless script printing and reuse run() method Signed-off-by: Nico Schottelius --- doc/dev/todo/niconext | 3 --- lib/cdist/exec/local.py | 21 +-------------------- lib/cdist/exec/remote.py | 28 ++-------------------------- 3 files changed, 3 insertions(+), 49 deletions(-) diff --git a/doc/dev/todo/niconext b/doc/dev/todo/niconext index 828ff917..bead6d72 100644 --- a/doc/dev/todo/niconext +++ b/doc/dev/todo/niconext @@ -3,9 +3,6 @@ - cleanup object_id handling - have a look at singletons -- remove useless - ERROR: monitoring02: Code that raised the error: - - ensure that all types, which support --state support present and absent (consistent look and feel) diff --git a/lib/cdist/exec/local.py b/lib/cdist/exec/local.py index cdf06205..e24ae484 100644 --- a/lib/cdist/exec/local.py +++ b/lib/cdist/exec/local.py @@ -119,26 +119,7 @@ class Local(object): command = ["/bin/sh", "-e"] command.append(script) - self.log.debug("Local run script: %s", command) - - if env is None: - env = os.environ.copy() - # Export __target_host for use in __remote_{copy,exec} scripts - env['__target_host'] = self.target_host - - self.log.debug("Local run script env: %s", env) - - try: - if return_output: - return subprocess.check_output(command, env=env).decode() - else: - subprocess.check_call(command, env=env) - except subprocess.CalledProcessError as error: - script_content = self.run(["cat", script], return_output=True) - self.log.error("Code that raised the error:\n%s", script_content) - raise LocalScriptError(script, command, script_content) - except EnvironmentError as error: - raise cdist.Error(" ".join(command) + ": " + error.args[1]) + self.run(command, env, return_output) def link_emulator(self, exec_path): """Link emulator to types""" diff --git a/lib/cdist/exec/remote.py b/lib/cdist/exec/remote.py index 69dc5dda..0fb93e10 100644 --- a/lib/cdist/exec/remote.py +++ b/lib/cdist/exec/remote.py @@ -139,32 +139,8 @@ class Remote(object): Return the output as a string. """ - command = self._exec.split() - command.append(self.target_host) - # export target_host for use in __remote_{exec,copy} scripts - os_environ = os.environ.copy() - os_environ['__target_host'] = self.target_host - - self.log.debug("Remote run script: %s", command) - - # can't pass environment to remote side, so prepend command with - # variable declarations - if env: - self.log.debug("Remote run script env: %s", env) - command.extend(["%s=%s" % item for item in env.items()]) - - command.extend(["/bin/sh", "-e"]) + command = ["/bin/sh", "-e"] command.append(script) - try: - if return_output: - return subprocess.check_output(command, env=os_environ).decode() - else: - subprocess.check_call(command, env=os_environ) - except subprocess.CalledProcessError as error: - script_content = self.run(["cat", script], return_output=True) - self.log.error("Code that raised the error:\n%s", script_content) - raise RemoteScriptError(script, command, script_content) - except EnvironmentError as error: - raise cdist.Error(" ".join(command) + ": " + error.args[1]) + self.run(command, env, return_output) From ab48a72ce135df073b3be572e8fe24bcc6296421 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 15 Feb 2012 16:25:18 +0100 Subject: [PATCH 92/98] return results from run() Signed-off-by: Nico Schottelius --- lib/cdist/exec/local.py | 2 +- lib/cdist/exec/remote.py | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/cdist/exec/local.py b/lib/cdist/exec/local.py index e24ae484..7fb63429 100644 --- a/lib/cdist/exec/local.py +++ b/lib/cdist/exec/local.py @@ -119,7 +119,7 @@ class Local(object): command = ["/bin/sh", "-e"] command.append(script) - self.run(command, env, return_output) + return self.run(command, env, return_output) def link_emulator(self, exec_path): """Link emulator to types""" diff --git a/lib/cdist/exec/remote.py b/lib/cdist/exec/remote.py index 0fb93e10..47b670b0 100644 --- a/lib/cdist/exec/remote.py +++ b/lib/cdist/exec/remote.py @@ -143,4 +143,4 @@ class Remote(object): command = ["/bin/sh", "-e"] command.append(script) - self.run(command, env, return_output) + return self.run(command, env, return_output) From f031a40746c30beec6ccdc4d282a475ff9bb9eb6 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 15 Feb 2012 17:01:03 +0100 Subject: [PATCH 93/98] rebuild the command string Signed-off-by: Nico Schottelius --- lib/cdist/exec/remote.py | 49 ++++++++++++++++------------------------ 1 file changed, 19 insertions(+), 30 deletions(-) diff --git a/lib/cdist/exec/remote.py b/lib/cdist/exec/remote.py index 47b670b0..7cd9052d 100644 --- a/lib/cdist/exec/remote.py +++ b/lib/cdist/exec/remote.py @@ -28,17 +28,6 @@ import logging import cdist - -class RemoteScriptError(cdist.Error): - def __init__(self, script, command, script_content): - self.script = script - self.command = command - self.script_content = script_content - - def __str__(self): - plain_command = " ".join(self.command) - return "Remote script execution failed: %s" % plain_command - class DecodeError(cdist.Error): def __init__(self, command): self.command = command @@ -91,6 +80,17 @@ class Remote(object): command.extend(["-r", source, self.target_host + ":" + destination]) self._run_command(command) + def run_script(self, script, env=None, return_output=False): + """Run the given script with the given environment on the remote side. + Return the output as a string. + + """ + + command = ["/bin/sh", "-e"] + command.append(script) + + return self.run(command, env, return_output) + def run(self, command, env=None, return_output=False): """Run the given command with the given environment on the remote side. Return the output as a string. @@ -99,7 +99,15 @@ class Remote(object): # prefix given command with remote_exec cmd = self._exec.split() cmd.append(self.target_host) + + # can't pass environment to remote side, so prepend command with + # variable declarations + if env: + remote_env = ["%s=%s" % item for item in env.items()] + cmd.append(remote_env) + cmd.extend(command) + return self._run_command(cmd, env=env, return_output=return_output) def _run_command(self, command, env=None, return_output=False): @@ -113,14 +121,6 @@ class Remote(object): os_environ = os.environ.copy() os_environ['__target_host'] = self.target_host - # can't pass environment to remote side, so prepend command with - # variable declarations - if env: - cmd = ["%s=%s" % item for item in env.items()] - cmd.extend(command) - else: - cmd = command - self.log.debug("Remote run: %s", command) try: if return_output: @@ -133,14 +133,3 @@ class Remote(object): raise cdist.Error(" ".join(*args) + ": " + error.args[1]) except UnicodeDecodeError: raise DecodeError(command) - - def run_script(self, script, env=None, return_output=False): - """Run the given script with the given environment on the remote side. - Return the output as a string. - - """ - - command = ["/bin/sh", "-e"] - command.append(script) - - return self.run(command, env, return_output) From 72fb77f13552bc5fbc240e8c584c94cc4b3ce16c Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 15 Feb 2012 17:02:21 +0100 Subject: [PATCH 94/98] extend not append Signed-off-by: Nico Schottelius --- lib/cdist/exec/remote.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/cdist/exec/remote.py b/lib/cdist/exec/remote.py index 7cd9052d..124c1b4f 100644 --- a/lib/cdist/exec/remote.py +++ b/lib/cdist/exec/remote.py @@ -104,7 +104,7 @@ class Remote(object): # variable declarations if env: remote_env = ["%s=%s" % item for item in env.items()] - cmd.append(remote_env) + cmd.extend(remote_env) cmd.extend(command) From 64bb1741aa0fb201b5e0f683f607f05c534a7038 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 15 Feb 2012 17:05:22 +0100 Subject: [PATCH 95/98] cleanup local Signed-off-by: Nico Schottelius --- lib/cdist/exec/local.py | 14 +------------- 1 file changed, 1 insertion(+), 13 deletions(-) diff --git a/lib/cdist/exec/local.py b/lib/cdist/exec/local.py index 7fb63429..d3c6a0ce 100644 --- a/lib/cdist/exec/local.py +++ b/lib/cdist/exec/local.py @@ -32,18 +32,6 @@ import logging import cdist from cdist import core - -class LocalScriptError(cdist.Error): - def __init__(self, script, command, script_content): - self.script = script - self.command = command - self.script_content = script_content - - def __str__(self): - plain_command = " ".join(self.command) - return "Local script execution failed: %s" % plain_command - - class Local(object): """Execute commands locally. @@ -131,4 +119,4 @@ class Local(object): try: os.symlink(src, dst) except OSError as e: - raise cdist.Error("Linking emulator from " + src + " to " + dst + " failed: " + e.__str__()) + raise cdist.Error("Linking emulator from %s to %s failed: %s" % (src, dst, e.__str__())) From 4a844ef2650314ed995608c5150e9cdf5121afb6 Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Wed, 15 Feb 2012 17:06:58 +0100 Subject: [PATCH 96/98] ++changes(2.0.8) Signed-off-by: Nico Schottelius --- doc/changelog | 1 + 1 file changed, 1 insertion(+) diff --git a/doc/changelog b/doc/changelog index 2d2d7a48..507726bc 100644 --- a/doc/changelog +++ b/doc/changelog @@ -6,6 +6,7 @@ Changelog 2.0.8: * Cleanup: Better hint to source of error + * Cleanup: Do not output failing script, but path to script only * Cleanup: Remove support for __debug variable in manifests (Type != Core debugging) From 79dedb5bb52cd856ecef5e12340e2c38a42bf0a0 Mon Sep 17 00:00:00 2001 From: Steven Armstrong Date: Thu, 16 Feb 2012 10:17:09 +0100 Subject: [PATCH 97/98] document boolean parameters Signed-off-by: Steven Armstrong --- doc/man/cdist-reference.text.sh | 7 ++++-- doc/man/man7/cdist-type.text | 41 +++++++++++++++++++++++++++------ 2 files changed, 39 insertions(+), 9 deletions(-) diff --git a/doc/man/cdist-reference.text.sh b/doc/man/cdist-reference.text.sh index 81e58ab2..a76e7941 100755 --- a/doc/man/cdist-reference.text.sh +++ b/doc/man/cdist-reference.text.sh @@ -101,12 +101,15 @@ conf/type//gencode-local:: conf/type//gencode-remote:: Used to generate code to be executed on the client. -conf/type//parameters/required:: +conf/type//parameter/required:: Parameters required by type, \n seperated list. -conf/type//parameters/optional:: +conf/type//parameter/optional:: Parameters optionally accepted by type, \n seperated list. +conf/type//parameter/boolean:: + Boolean parameters accepted by type, \n seperated list. + conf/type//explorer:: Location of the type specific explorers. This directory is referenced by the variable __type_explorer (see below). diff --git a/doc/man/man7/cdist-type.text b/doc/man/man7/cdist-type.text index 48d412f1..1147511e 100644 --- a/doc/man/man7/cdist-type.text +++ b/doc/man/man7/cdist-type.text @@ -40,7 +40,7 @@ A list of supported types can be found in the cdist-reference(7) manpage. SINGLETON TYPES --------------- -If a type is flagged as a singleton, it may be used only +If a type is flagged as a singleton, it may be used only once per host. This is useful for types which can be used only once on a system. Singleton types do not take an object name as argument. @@ -72,15 +72,42 @@ To begin a new type, just create the directory **conf/type/__NAME**. DEFINING PARAMETERS ------------------- -Every type consists of optional and required parameters, which must -be created in a newline seperated file in ***parameters/required*** and -***parameters/optional***. If either or both missing, the type will have -no required, no optional or no parameters at all. +Every type consists of required, optional and boolean parameters, which must +be created in a newline seperated file in ***parameter/required***, +***parameter/optional*** and ***parameter/boolean***. If either is missing, +the type will have no required, no optional, no boolean or no parameters at +all. Example: -------------------------------------------------------------------------------- echo servername >> conf/type/__nginx_vhost/parameter/required echo logdirectory >> conf/type/__nginx_vhost/parameter/optional +echo use_ssl >> conf/type/__nginx_vhost/parameter/boolean +-------------------------------------------------------------------------------- + + +USING PARAMETERS +---------------- +The parameters given to a type can be accessed and used in all type scripts +(e.g manifest, gencode-*, explorer/*). Note that boolean parameters are +represented by file existence. File exists -> True, +file does not exist -> False + +Example: (e.g. in conf/type/__nginx_vhost/manifest) +-------------------------------------------------------------------------------- +# required parameter +servername="$(cat "$__object/parameter/servername")" + +# optional parameter +if [ -f "$__object/parameter/logdirectory" ]; then + logdirectory="$(cat "$__object/parameter/logdirectory")" +fi + +# boolean parameter +if [ -f "$__object/parameter/use_ssl" ]; then + # file exists -> True + # do some fancy ssl stuff +fi -------------------------------------------------------------------------------- @@ -116,7 +143,7 @@ SINGLETON - ONLY INSTANCE ONLY ------------------------------ If you want to ensure that a type can only be used once per target, you can mark it as a singleton: Just create the (empty) file "singleton" in your type -directory: +directory: -------------------------------------------------------------------------------- touch conf/type/__NAME/singleton @@ -128,7 +155,7 @@ This will also change the way your type must be called: __YOURTYPE --parameter value -------------------------------------------------------------------------------- -As you can see, the object ID is omitted, because it does not make any sense, +As you can see, the object ID is omitted, because it does not make any sense, if your type can be used only once. From baf8614e6cfab4467a62c57c66f82cd4940939ee Mon Sep 17 00:00:00 2001 From: Nico Schottelius Date: Thu, 16 Feb 2012 11:13:50 +0100 Subject: [PATCH 98/98] ++changes(2.0.8) Signed-off-by: Nico Schottelius --- doc/changelog | 1 + 1 file changed, 1 insertion(+) diff --git a/doc/changelog b/doc/changelog index 507726bc..ab006435 100644 --- a/doc/changelog +++ b/doc/changelog @@ -9,6 +9,7 @@ Changelog * Cleanup: Do not output failing script, but path to script only * Cleanup: Remove support for __debug variable in manifests (Type != Core debugging) + * Feature Core: Support boolean parameters (Steven Armstrong) 2.0.7: 2012-02-13 * Bugfix __file: Use chmod after chown/chgrp (Matt Coddington)