Alexandre
2009-Dec-09 09:44 UTC
[Puppet Users] How to override / redefine outside child class (usecase and example detailled)
The use case i try to illustrate is when to declare some item (eq mysqld service) with a default configuration that could be included on every node (class stripdown in the example, for basenode), and still be able to override this same item in some specific class (eg mysql::server), to be included by specific nodes (eg myserver.local) I illustrated this use case with the example below. But of course, Puppet parsing fails because the Service[mysql] is included twice. And of course, class mysql::server Is there a way to override the Service["mysql"], or mark it as the main one, or whatever ? I was thinking about the virtual items and the realize function, but it only permits apply an item multiple times, not to redefine or override. class stripdown { service {"mysql": enable => "false", ensure => "stopped" } } class mysql::server { service { mysqld: enable => true, ensure => running, hasrestart => true, hasstatus => true, path => "/etc/init.d/mysql", require => Package["mysql-server"], } } node basenode { include stripdown } node myserver.local inherits basenode { include mysql::server # <- boom, fails here because of Service["mysql"] redefinition } -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
Silviu Paragina
2009-Dec-09 12:27 UTC
Re: [Puppet Users] How to override / redefine outside child class (usecase and example detailled)
On 09.12.2009 11:44, Alexandre wrote:> The use case i try to illustrate is when to declare some item (eq > mysqld service) with a default configuration that could be included on > every node (class stripdown in the example, for basenode), and still > be able to override this same item in some specific class (eg > mysql::server), to be included by specific nodes (eg myserver.local) > > I illustrated this use case with the example below. But of course, > Puppet parsing fails because the Service[mysql] is included twice. And > of course, class mysql::server > > Is there a way to override the Service["mysql"], or mark it as the > main one, or whatever ? > I was thinking about the virtual items and the realize function, but > it only permits apply an item multiple times, not to redefine or > override. > > class stripdown { > service {"mysql": enable => "false", ensure => "stopped" } > } >Not tested but it should be like class stripdown { include mysql::server *S*ervice {"mysql": enable => "false", ensure => "stopped" } } Check the language tutorial for overriding. Note that is a big "S" not a small "s". Or you may do it the other way around. (Include stripdown into mysql::server. (this probably the solution you want) Or define a third skeleton class which starts with same bare definitions, and the other two override them Silviu> class mysql::server { > service { mysqld: > enable => true, > ensure => running, > hasrestart => true, > hasstatus => true, > path => "/etc/init.d/mysql", > require => Package["mysql-server"], > } > } > > node basenode { > include stripdown > } > > node myserver.local inherits basenode { > include mysql::server #<- boom, fails here > because of Service["mysql"] redefinition > } > > -- > > You received this message because you are subscribed to the Google Groups "Puppet Users" group. > To post to this group, send email to puppet-users@googlegroups.com. > To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. > For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en. > > >-- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
jcbollinger
2009-Dec-09 14:28 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
On Dec 9, 6:27 am, Silviu Paragina <sil...@paragina.ro> wrote:> Not tested but it should be like > > class stripdown { > include mysql::server > *S*ervice {"mysql": enable => "false", ensure => "stopped" } > > } > > Check the language tutorial for overriding. Note that is a big "S" not a > small "s".As far as I know, overriding only works in a subclass, so it would need to be: class stripdown inherits mysql::server { Service { "mysqld": enable => "false", ensure => "stopped" } } Obviously, that''s messy and it doesn''t scale for multiple overrides. It may also have other, unwanted effects.> Or you may do it the other way around. (Include stripdown into > mysql::server. (this probably the solution you want)It would indeed make more sense for mysql::server to inherit stripdown and override it, but again this does not scale. If stripdown declares any resources then I think you will get resource conflicts again if you include multiple subclasses in the same manifest (e.g. mysql::server and http::server, both inheriting stripdown).> Or define a third skeleton class which starts with same bare > definitions, and the other two override themAnd in this case, the manifest needs to use a conditional to select which subclass to include. I think that''s the best general approach, but if you''re going to do that then you don''t need to subclass or override anything. Just have separate classes mysql::server and mysql::server::disabled, and include exactly one, as appropriate. Note also that any approach that forces mysqld to be disabled on machines that aren''t supposed to be mysql servers requires that mysql nevertheless be *installed* on those machines. Many admins would argue that it shouldn''t be present at all if it''s not supposed to run. -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
Silviu Paragina
2009-Dec-09 16:19 UTC
Re: [Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
On 09.12.2009 16:28, jcbollinger wrote:> As far as I know, overriding only works in a subclass, so it would > need to be: > > class stripdown inherits mysql::server { > Service { "mysqld": enable => "false", ensure => "stopped" } > } > > > Obviously, that''s messy and it doesn''t scale for multiple overrides. > It may also have other, unwanted effects. >Yep, sorry I''ve had some bad concepts about overriding. Sorry for posting bad stuff on the list. Testing on a 0.25.1 I got to this class s_test1::stripdown { service { "mysqld": name => "mysql", enable => false, ensure => stopped, } #other definitions that make sure that the service is not working } class s_test1::client inherits s_test1::stripdown { #definition overrides to install the client part } class s_test1::server inherits s_test1::client { #if this is the server the client part should be also included #that''s why we inherit from s_test1::client #overrides definitions Service ["mysqld"] { enable => true, ensure => running } } of course you should create a class stripdown which includes stripdown for each service you want. I think this is the usual style of defining stuff in puppet as I''ve seen it in a lot of places. Now if you include both s_test1::stripdown and s_test::server server will take precedence. (actually it may start as s_test1::stripdown and then "add to it" s_test1::server, but the behavior is respected no matter what the order of includes). Silviu -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
jcbollinger
2009-Dec-10 16:46 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
On Dec 9, 10:19 am, Silviu Paragina <sil...@paragina.ro> wrote:> I think this is the usual style of defining stuff in puppet as I''ve seen > it in a lot of places.I have often seen the model of class some_facility::base {} class some_facility::server {} class some_facility::client {} I have not noticed class inheritance routinely being used in such a setup, but I may have just overlooked it. If client and server classes simply "include" the base class, though, then that achieves everything that inheriting would do except allowing resource overrides. I don''t have any objection to the client and server classes both inheriting the base class, but it is conceptually wrong for server to inherit client, for the server machines do not need to also be clients. For general-purpose overrides (as opposed to node-specific ones), the best practices recommend something of the form class some_facility::server::disabled inherits some_facility::server { [resource overrides here] }> Now if you include both s_test1::stripdown and s_test::server server > will take precedence. (actually it may start as s_test1::stripdown and > then "add to it" s_test1::server, but the behavior is respected no > matter what the order of includes).Somewhat to my surprise, that works. On the other hand, the fact that I find it surprising is enough reason for me, personally, to never use that motif. To be clear: the surprising thing to me is that Puppet does not complain about including both s_test1::stripdown and s_test1::server in the same catalog, even though they define conflicting properties for Service["mysqld"]. (It can be made to complain about conflicting properties if you structure the classes and overrides differently, though.) How to approach this kind of issue is surely a matter of opinion and preference, but for me it doesn''t make sense to have a blanket disable for a service that isn''t necessarily even installed. Thus, I would do something more like this: class mysql::server { package { "mysql-server": ensure => "latest" } service { "myslqd": name => "mysql", require => Package["mysql-server"], enable => true, ensure => "running", } class mysql::server::disable inherits mysql::server { Service { "mysqld": enable => false, ensure => "stopped" } } There are then three options for each node: 1) The mysql server is unmanaged, or forced not present if package purging is enabled. This happens if neither mysql::server nor mysql::server::disable is included. 2) The mysql server is installed, enabled, and running. This happens if mysql::server is included and mysql::server::disable is not. 3) The mysql server is installed but disabled and not running. This happens if mysql::server::disable is included. YMWV -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
Alexandre
2009-Dec-15 10:03 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
I though i found a way to do it, and i would like to show it here, but unfortunately it does not exactly work well, see the comment in uppercase: global variables seems to be set even if no class from the .pp file is included. And i also think now i am going to far into akwardness, just trying to work around some Puppet limitations, or maybe thinking of Puppet beyond its scope, as if it was a full featured language I am wondering now if it is always a good idea to try to do everything within Puppet. I think if i get time, i will do a generic script to address this problem, which would be deployed with the usual set of scripts i deploy on each server, and run it from Puppet. I also recently went onto another set of Puppet problem, to which i began implementing a define to do some processing, and ended up having this define only get the parameters and give it all to a deployed script that does the processing (just because i needed to loop on the items of a puppet array). Anyway, here was my last, and almost working to get the default stripdown (shows relevant parts) : ## ## mysqld.pp ## # This variable is global, not defined inside the class, otherwise it will never be seen as set, due to the dynamic scope $_service_is_managed_mysqld=1 class mysql::server inherits mysql { # (...) } ## ## stripdown.pp ## define stripdown_service ( $pattern="" ) { if $pattern == "" { exec { "stripdown $name stop": command => "service $name stop", onlyif => "service $name status", path => "/usr/bin:/usr/sbin:/bin:/sbin", } } else { exec { "stripdown $name stop": command => "service $name stop", onlyif => "pgrep -f \"$name\"", path => "/usr/bin:/usr/sbin:/bin:/sbin", } } exec { "stripdown $name deactivate": command => "chkconfig $name off", onlyif => "chkconfig $name", path => "/usr/bin:/usr/sbin:/bin:/sbin", } } class stripdown_services::centos { service { "autofs": enable => "false", ensure => "stopped"; "avahi-daemon": enable => "false", ensure => "stopped"; # (...) } # THIS $_service_is_managed_xxx THING DOES NOT WORK : EVEN IF NOT CLASS NOT INCLUDED IN THE NODE, THE VARIABLE SEEMS TO BE SET !!! if $_service_is_managed_squid != 1 { stripdown_service{squid:} } if $_service_is_managed_lighttpd != 1 { stripdown_service {lighttpd: pattern=>"lighttpd.conf"} } if $_service_is_managed_mysqld != 1 { stripdown_service{mysqld:} } # (...) } -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
jcbollinger
2009-Dec-15 14:56 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
On Dec 15, 4:03 am, Alexandre <alexandre.fou...@gmail.com> wrote:> I though i found a way to do it, and i would like to show it here, > but unfortunately it does not exactly work well, see the comment in > uppercase: global variables seems to be set even if no class from > the .pp file is included.Yes. Modules and manifest files do not provide scoping.> And i also think now i am going to far into akwardness, just tryingI agree (a bit more on that below).> to work around some Puppet limitations, or maybe thinking of Puppet > beyond its scope, as if it was a full featured languagePuppet is a declarative language. Users who come from a programming background seem sometimes to have difficulty coming to grips with that. If you ever find yourself thinking "how do a make Puppet do foo?" then you are off to a wobbly start. A better question is usually "how do I explain foo to Puppet?".> I am wondering now if it is always a good idea to try to do > everything within Puppet.Puppet does have limits to what it can do natively for you (though it is also highly extensible). Where it is possible, using Puppet types other than Exec to get the work done has several advantages. [...]> and ended up having this > define only get the parameters and give it all to a deployed script > that does the processing (just because i needed to loop on the items > of a puppet array).Puppet is not built to do user-defined processing, except inasmuch as you can always create your own types and / or providers.> Anyway, here was my last, and almost working to get the default > stripdown (shows relevant parts) :[...]> # This variable is global, not defined inside the class, otherwise it > will never be seen as set, due to the dynamic scope > $_service_is_managed_mysqld=1So the idea is that you have a variable for each service that later instructs Puppet whether to run "stripdown" commands for that service? And that implies that somewhere you dynamically choose a value for this variable based on the facts presented to the puppetmaster? That seems awfully convoluted. Why not use that same decision logic to dynamically choose whether to include a class? Furthermore, if you have to make that decision dynamically, then it is no harder to choose between two alternative classes than to make only a yes/no decision about a single class. That leads to having two alternative classes, one declaring "stripdown"-configured resources and the other declaring enabled resources, where you dynamically decide which to include for each node. And that''s what I have been recommending all along. [...]> if $pattern == "" { > exec { "stripdown $name stop": > command => "service $name stop", > onlyif => "service $name status", > path => "/usr/bin:/usr/sbin:/bin:/sbin", > } > }[etc.] I''m not seeing what that "stripdown" define does for you that the Service type doesn''t, unless .... Please tell me that you''re not using these Execs to change the state of Services declared elsewhere! That way lies madness. I guess I''m at a loss as to what problem you''re trying to solve any more. Silviu and I offered two solutions to you, either one of which will work cleanly and entirely within Puppet to solve your problem as I understood it. What more are you looking for that neither of these provides? -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
Alexandre
2009-Dec-17 03:17 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
Yes all of this is very convoluted, but not because of my mind, just because Puppet PARSER is too strict and prevents states that can exists in the real. No, i do not try to use exec to change the change the state of the service which is -executed- elsewhere (i aggree it would be stupid and impossible, a ressource can not have two different status at the same time), but i do use exec to set services that are -declared- elsewhere in puppet, but not included(executed). So that the state of the service is the one of the exec. Unfortunately, i had to do that, because otherwise Puppet would complain at -parsing- time, not execute time, since it does not want to have the same ressource(here service) declared twice, even if one is not included for the node, nor be overriden if not in a child class (and i understand very well the logic behind that, it makes sense, if we do not consider that we could assign priorities or precedences on puppet ressources (but then it could be a mess :-/)) I also checked your solutions, but it does not solve what i wanted to achieve. What i wanted is per node : - if i want to include a class (eg mysql::server), then i include it. - If it is missing(not included or required by some other included class), then have the default global stripdown executed. As i understood, your solution says that if i do not want a service in a node, then i should include the disabled class (eg mysql::server::disabled). This is not what i want, what i want is my nodes definition to be agnostic of what could have been included previously in the past or may already be present on the server. I do not want for each node to declare every ressource that exist in my puppet repo to be disabled (Eg if only 1 node of my 100 needs mysql running, i do not wish to have to include mysql::server::disabled in the 99 other nodes definitions. But i want to ensure the mysqld service is down for these 99 nodes, in case it was running on the node for whatever reason). Of course, we need to accept that puppet will try to stripdown services that are not even installed, but i do not see it as a problem. I think this is good general practice of sysadmin to ensure everything on a linux system that is not needed should be removed, restricted or disabled (services, users, dir permissions). As we see here, it seems Puppet can not fullfill this need, except by listing explicitely and exhaustively what needs to be or not be activated for each node. So of course, one way or another, there is a place where i need to tell what should be stripdowned. But i want it to be accepted as the default -state- of the node, unless specified otherwise by including a class which redefines some of the ressources that need to be activated. I do not want my nodes.pp to be 1000000 lines and unmaintanable. I understand the meaning of declarative language. I just miss the fact that i can not declare something like if something is not included, then apply this whole set of declarations. -> Unfortunately for me, there might be a way to do this "default state"/"included state" scheme in Puppet, or by including ruby or facter or ..., but i am not a puppet expert. This could maybe be the subject of another thread On 15 déc, 22:56, jcbollinger <John.Bollin...@stJude.org> wrote:> On Dec 15, 4:03 am, Alexandre <alexandre.fou...@gmail.com> wrote: > > > I though i found a way to do it, and i would like to show it here, > > but unfortunately it does not exactly work well, see the comment in > > uppercase: global variables seems to be set even if no class from > > the .pp file is included. > > Yes. Modules and manifest files do not provide scoping. > > > And i also think now i am going to far into akwardness, just trying > > I agree (a bit more on that below). > > > to work around some Puppet limitations, or maybe thinking of Puppet > > beyond its scope, as if it was a full featured language > > Puppet is a declarative language. Users who come from a programming > background seem sometimes to have difficulty coming to grips with > that. If you ever find yourself thinking "how do a make Puppet do > foo?" then you are off to a wobbly start. A better question is > usually "how do I explain foo to Puppet?". > > > I am wondering now if it is always a good idea to try to do > > everything within Puppet. > > Puppet does have limits to what it can do natively for you (though it > is also highly extensible). Where it is possible, using Puppet types > other than Exec to get the work done has several advantages. > > [...] > > > and ended up having this > > define only get the parameters and give it all to a deployed script > > that does the processing (just because i needed to loop on the items > > of a puppet array). > > Puppet is not built to do user-defined processing, except inasmuch as > you can always create your own types and / or providers. > > > Anyway, here was my last, and almost working to get the default > > stripdown (shows relevant parts) : > > [...] > > > # This variable is global, not defined inside the class, otherwise it > > will never be seen as set, due to the dynamic scope > > $_service_is_managed_mysqld=1 > > So the idea is that you have a variable for each service that later > instructs Puppet whether to run "stripdown" commands for that > service? And that implies that somewhere you dynamically choose a > value for this variable based on the facts presented to the > puppetmaster? > > That seems awfully convoluted. Why not use that same decision logic > to dynamically choose whether to include a class? Furthermore, if you > have to make that decision dynamically, then it is no harder to choose > between two alternative classes than to make only a yes/no decision > about a single class. That leads to having two alternative classes, > one declaring "stripdown"-configured resources and the other declaring > enabled resources, where you dynamically decide which to include for > each node. And that''s what I have been recommending all along. > > [...] > > > if $pattern == "" { > > exec { "stripdown $name stop": > > command => "service $name stop", > > onlyif => "service $name status", > > path => "/usr/bin:/usr/sbin:/bin:/sbin", > > } > > } > > [etc.] > > I''m not seeing what that "stripdown" define does for you that the > Service type doesn''t, unless .... Please tell me that you''re not > using these Execs to change the state of Services declared elsewhere! > That way lies madness. > > I guess I''m at a loss as to what problem you''re trying to solve any > more. Silviu and I offered two solutions to you, either one of which > will work cleanly and entirely within Puppet to solve your problem as > I understood it. What more are you looking for that neither of these > provides?-- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
Peter Meier
2009-Dec-17 08:51 UTC
Re: [Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
-----BEGIN PGP SIGNED MESSAGE----- Hash: SHA1> [...] > I think this is good general practice of sysadmin to ensure > everything on a linux system that is not needed should be removed, > restricted or disabled (services, users, dir permissions). As we see > here, it seems Puppet can not fullfill this need, except by listing > explicitely and exhaustively what needs to be or not be activated for > each node. So of course, one way or another, there is a place where i > need to tell what should be stripdowned. But i want it to be accepted > as the default -state- of the node, unless specified otherwise by > including a class which redefines some of the ressources that need to > be activated. I do not want my nodes.pp to be 1000000 lines and > unmaintanable.How about doing it the other way round? Generally include the stripped-down classes and then include additionally per node the mysql class which inherits the stripped down class but overwrites the resources to manage mysql: node default { include configsets } node mysqlserver { include configsets::mysqlserver } class configsets { include mysql::server } class configsets::mysqlserver { include config include mysql::server::present } class mysql::server { package{''mysql-server'': ensure => absent } service{''mysql-server'': ensure => stopped, enable => false, require => Package[''mysql-server''], } } class mysql::server::present inherits mysql::server { Package[''mysql-server'']{ ensure => installed } Service[''mysql-server'']{ ensure => running, enable => true, } file{''/etc/my.conf'': source => "...." notify => Service[''mysql-server''], } } Naming convention could be better, but I think this should generally work. You simply include every resource you manage in the general class configsets, which gets applied to every node (also due to inheritance, reinclusion) but include the "present" class in nodes that need it.> I do not want my nodes.pp to be 1000000 lines and unmaintanable.I would generally avoid putting too much into nodes. My nodes look like: node default { $some_var_1 = ''aaa'' $some_var_2 = ''bbb'' include configsets } node foobar { $some_var_1 = ''foo'' $some_var_2 = ''bar'' include configsets::foobar } And all the actual service includes are done in the module called configesets, which can have further abstraction like node-types, i.e. physical nodes (class is included depending on the virtual fact) etc., inheritance and so on. Did I miss some circumstances why this shouldn''t work? cheers pete. -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.4.9 (GNU/Linux) Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org iEYEARECAAYFAksp8QQACgkQbwltcAfKi383ZwCdHOZO8yYdo6zooR07tgy5OE7/ ZhgAoJzWrZoO2ikcrO/ZRJVLE/fPcufr =/lYm -----END PGP SIGNATURE----- -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
jcbollinger
2009-Dec-17 14:18 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
On Dec 17, 2:51 am, Peter Meier <peter.me...@immerda.ch> wrote:> How about doing it the other way round? Generally include the > stripped-down classes and then include additionally per node the mysql > class which inherits the stripped down class but overwrites the > resources to manage mysql:[...] This is precisely what Sliviu recommended, and, as far as I can tell, it''s exactly what Alexandre is asking for. The general approach demonstrably works, which is why I am confused by Alexandre''s claim that Puppet can''t do what he wants. John -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
jcbollinger
2009-Dec-17 14:34 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
On Dec 16, 9:17 pm, Alexandre <alexandre.fou...@gmail.com> wrote: [...]> because otherwise Puppet would complain at -parsing- time, not execute > time, since it does not want to have the same ressource(here service) > declared twice, even if one is not included for the node,Puppet does not exhibit this problem for me. The only way I have been able to elicit a resource conflict error from Puppet is to have one node include two classes each declaring a resource of the same type and name. It is not enough to cause such an error (in my tests) simply for two classes to define the same resource -- both must be included in the same node to get the error. If you find differently then I encourage you to file a bug report. John -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
jcbollinger
2009-Dec-17 16:39 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
On Dec 16, 9:17 pm, Alexandre <alexandre.fou...@gmail.com> wrote:> I understand the meaning of declarative language. I just miss the > fact that i can not declare something like if something is not > included, then apply this whole set of declarations.From the glass-half-full department, I''d like to point out that this is only an issue in the first place because the Puppet language is rich enough that there can be some uncertainty about whether a particular class will be included for a particular node. You cannot solve your problem in the particular way you were trying to do, but that does not mean that you cannot solve it within Puppet, nor even that you cannot solve it within Puppet in a concise and maintainable way. The structure of the Puppet language strongly encourages modularity, in the sense of putting related logic and declarations in the same place. If you try to go against that grain, as it appears you did, then you are indeed likely to become frustrated. Nevertheless, you may be able to make that approach work with use of the built-in "defined" function or by writing your own custom function. I think the alternatives that Silviu and I, and now Peter, are suggesting are better aligned with with the language structure, however. John -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
jcbollinger
2009-Dec-17 17:57 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
On Dec 17, 8:34 am, jcbollinger <John.Bollin...@stJude.org> wrote:> On Dec 16, 9:17 pm, Alexandre <alexandre.fou...@gmail.com> wrote: > [...] > > > because otherwise Puppet would complain at -parsing- time, not execute > > time, since it does not want to have the same ressource(here service) > > declared twice, even if one is not included for the node, > > Puppet does not exhibit this problem for me. The only way I have been > able to elicit a resource conflict error from Puppet is to have one > node include two classes each declaring a resource of the same type > and name.I just had an additional thought about this one: are you putting all your declarations into classes? Anything that is outside a class definition is global, so if that file is parsed, such resources (and variables, etc.) apply to all nodes. Incidentally, please do not take this as a cue to attempt to influence global declarations by controlling which files get parsed. You will drive yourself nuts that way. For the most part, you should just put everything into classes. There are some uses for global declarations, but all the ones I can think of have these characteristics: 1) not harmful if applied when unneeded 2) certain to be parsed if needed Resource parameter defaults can sometimes fall into this category, for instance. John -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
Alexandre
2009-Dec-18 03:08 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
Yes, in fact this is exactly what i have for the services -i want to install or manage-. A base class with common stuff (eg mysql user, group, pkg, test directories ... and service disabled by default), and a child class ...::server with typically just include the service specific config file and override Service[] to enable it But this was not my original problem. Let''s take an example : 1) i want to apply a general linux stripdown 2) i get a server, which had already stuff on it, maybe services activated but not used, and on which sometimes people get on and modify things (file permissions, start services, ...) 3) I want to apply the general stripdown to this server, without having to know what is there and create a special stripdown just for this server 4) I still want to install or activate services on this server, while having the general stripdown still active So far i can do 1), 2) and 3) with puppet, very simply. My problem is 4). All implementations of 4) i saw in this discussion say i have for each node, specify exactly what i want to disable and enable, so that if i have 100 nodes, i have to create 100 different stripdown. While it is easy saying a node what it should include so that it provides the needed services, it is big task and unmaintanable to specify exhaustively what nodes should not include. Especially that these nodes are used by some people that need some priviledges, but do not always clean after work or are not sysadmins On Dec 17, 4:51 pm, Peter Meier <peter.me...@immerda.ch> wrote:> -----BEGIN PGP SIGNED MESSAGE----- > Hash: SHA1 > > > [...] > > I think this is good general practice of sysadmin to ensure > > everything on a linux system that is not needed should be removed, > > restricted or disabled (services, users, dir permissions). As we see > > here, it seems Puppet can not fullfill this need, except by listing > > explicitely and exhaustively what needs to be or not be activated for > > each node. So of course, one way or another, there is a place where i > > need to tell what should be stripdowned. But i want it to be accepted > > as the default -state- of the node, unless specified otherwise by > > including a class which redefines some of the ressources that need to > > be activated. I do not want my nodes.pp to be 1000000 lines and > > unmaintanable. > > How about doing it the other way round? Generally include the > stripped-down classes and then include additionally per node the mysql > class which inherits the stripped down class but overwrites the > resources to manage mysql: > > node default { > include configsets > > } > > node mysqlserver { > include configsets::mysqlserver > > } > > class configsets { > include mysql::server > > } > > class configsets::mysqlserver { > include config > include mysql::server::present > > } > > class mysql::server { > package{''mysql-server'': ensure => absent } > service{''mysql-server'': > ensure => stopped, > enable => false, > require => Package[''mysql-server''], > } > > } > > class mysql::server::present inherits mysql::server { > Package[''mysql-server'']{ ensure => installed } > Service[''mysql-server'']{ > ensure => running, > enable => true, > } > file{''/etc/my.conf'': > source => "...." > notify => Service[''mysql-server''], > } > > } > > Naming convention could be better, but I think this should generally > work. You simply include every resource you manage in the general class > configsets, which gets applied to every node (also due to inheritance, > reinclusion) but include the "present" class in nodes that need it. > > > I do not want my nodes.pp to be 1000000 lines and unmaintanable. > > I would generally avoid putting too much into nodes. My nodes look like: > > node default { > $some_var_1 = ''aaa'' > $some_var_2 = ''bbb'' > include configsets > > } > > node foobar { > $some_var_1 = ''foo'' > $some_var_2 = ''bar'' > include configsets::foobar > > } > > And all the actual service includes are done in the module called > configesets, which can have further abstraction like node-types, i.e. > physical nodes (class is included depending on the virtual fact) etc., > inheritance and so on. > > Did I miss some circumstances why this shouldn''t work? > > cheers pete. > -----BEGIN PGP SIGNATURE----- > Version: GnuPG v1.4.9 (GNU/Linux) > Comment: Using GnuPG with Mozilla -http://enigmail.mozdev.org > > iEYEARECAAYFAksp8QQACgkQbwltcAfKi383ZwCdHOZO8yYdo6zooR07tgy5OE7/ > ZhgAoJzWrZoO2ikcrO/ZRJVLE/fPcufr > =/lYm > -----END PGP SIGNATURE------- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
Alexandre
2009-Dec-18 03:19 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
it was because the case $mysql_enabled = 1 class mysql::server { service{mysqld: blablabla activate} } class stripdown{ if $mysql_enabled == 1 { service{mysqld: blablabla deactivate} } } node somenode { include mysql::server include stripdown } So you see in the case above, the parser will fail because service [mysql] is included and defined twice (of course, since it is grammar parser and not an AI ;-). But it would have worked if executed ( But i know the whole thing with variables is maybe a wrong implementation of the problem ) On Dec 17, 10:34 pm, jcbollinger <John.Bollin...@stJude.org> wrote:> On Dec 16, 9:17 pm, Alexandre <alexandre.fou...@gmail.com> wrote: > [...] > > > because otherwise Puppet would complain at -parsing- time, not execute > > time, since it does not want to have the same ressource(here service) > > declared twice, even if one is not included for the node, > > Puppet does not exhibit this problem for me. The only way I have been > able to elicit a resource conflict error from Puppet is to have one > node include two classes each declaring a resource of the same type > and name. It is not enough to cause such an error (in my tests) > simply for two classes to define the same resource -- both must be > included in the same node to get the error. If you find differently > then I encourage you to file a bug report. > > John-- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
Alexandre
2009-Dec-18 03:24 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
Yes, i try to be as modular and generic as possible. I do not put anything global, every thing is either a class or a define, and variables are usually only set in nodes, either as flags or to be used in templates. The only exception are the global variables (eg $_service_is_managed_mysqld=1) , which i described above but i removed them because the whole thing is too convoluted and does not work anyway. On Dec 18, 1:57 am, jcbollinger <John.Bollin...@stJude.org> wrote:> On Dec 17, 8:34 am, jcbollinger <John.Bollin...@stJude.org> wrote: > > > On Dec 16, 9:17 pm, Alexandre <alexandre.fou...@gmail.com> wrote: > > [...] > > > > because otherwise Puppet would complain at -parsing- time, not execute > > > time, since it does not want to have the same ressource(here service) > > > declared twice, even if one is not included for the node, > > > Puppet does not exhibit this problem for me. The only way I have been > > able to elicit a resource conflict error from Puppet is to have one > > node include two classes each declaring a resource of the same type > > and name. > > I just had an additional thought about this one: are you putting all > your declarations into classes? Anything that is outside a class > definition is global, so if that file is parsed, such resources (and > variables, etc.) apply to all nodes. > > Incidentally, please do not take this as a cue to attempt to influence > global declarations by controlling which files get parsed. You will > drive yourself nuts that way. For the most part, you should just put > everything into classes. There are some uses for global declarations, > but all the ones I can think of have these characteristics: > > 1) not harmful if applied when unneeded > 2) certain to be parsed if needed > > Resource parameter defaults can sometimes fall into this category, for > instance. > > John-- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
Peter Meier
2009-Dec-18 10:02 UTC
Re: [Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
-----BEGIN PGP SIGNED MESSAGE----- Hash: SHA1> it was because the case > > $mysql_enabled = 1 > class mysql::server { > service{mysqld: blablabla activate} > } > > class stripdown{ > if $mysql_enabled == 1 { > service{mysqld: blablabla deactivate} > } > } > > node somenode { > include mysql::server > include stripdown > } > > So you see in the case above, the parser will fail because service > [mysql] is included and defined twice (of course, since it is grammar > parser and not an AI ;-). But it would have worked if executed > ( But i know the whole thing with variables is maybe a wrong > implementation of the problem )why don''t you include a stripped down mysql class instead of defining the service twice? I don''t get it: $mysql_enabled = 1 class mysql::stripdown { service{mysqld: blablabla deactivate} } class mysql::server inherits mysql::stripdown{ Service[mysqld]{ blablabla activate} } class stripdown{ if $mysql_enabled == 1 { include mysql::stripdown } } node somenode { include mysql::server include stripdown } but I don''t like this $mysql_enable at all, in your productive setup is it a fact or do you set the variable? cheers pete -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.4.9 (GNU/Linux) Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org iEYEARECAAYFAksrUzMACgkQbwltcAfKi39/rQCcC9sRnnfrgmqH4uKAPZu1iYlh bnMAn3tc2KsZDGgA9uWDBw3GrdwriYHy =NuYW -----END PGP SIGNATURE----- -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
jcbollinger
2009-Dec-18 14:39 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
On Dec 17, 9:19 pm, Alexandre <alexandre.fou...@gmail.com> wrote:> it was because the case > > $mysql_enabled = 1 > class mysql::server { > service{mysqld: blablabla activate} > > } > > class stripdown{ > if $mysql_enabled == 1 { > service{mysqld: blablabla deactivate} > } > > } > > node somenode { > include mysql::server > include stripdown > > } > > So you see in the case above, the parser will fail because service > [mysql] is included and defined twice (of course, since it is grammar > parser and not an AI ;-). But it would have worked if executed > ( But i know the whole thing with variables is maybe a wrong > implementation of the problem )I agree that variables are not likely constitute a viable approach to solving this problem. I''m also not all that enthusiastic about the use of a general stripdown, but that''s a personal preference thing. Since you seem to be intent on that manner of solution, have you tried something along these lines: class stripdown { # turn off everything we care about managing service { "mysqld": <deactivate> } service { "apache": <deactivate> } ... } class mysql::server inherits stripdown { Service ["mysqld"] { <activate> } } class apache::server inherits stripdown { Service ["apache"] { <activate> } } node foo { include stripdown } node bar { include stripdown include mysql::server } node baz { include stripdown include mysql::server include apache::server } In other words, all your some_facility::server classes inherit from the same general stripdown and override different (that''s important) resources. Each node then includes the stripdown and the service- specific classes for those services it should run. -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
jcbollinger
2009-Dec-18 15:02 UTC
[Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
On Dec 17, 9:08 pm, Alexandre <alexandre.fou...@gmail.com> wrote:> 4). All implementations of 4) i saw in this discussion say i have for > each node, specify exactly what i want to disable and enable, so that > if i have 100 nodes, i have to create 100 different stripdown.I think the result is rather that if you have 100 different *services* you want to manage via Puppet, then you need a stripdown for each one. And any way around that''s true; it''s merely a question of whether you put all those services'' stripdowns in the same class or in separate classes. You probably have a lot fewer than 100 services. Personally, if I am interested in the mysql service, then for each node I would prefer to see one of: node foo { include mysql::server ... } or node foo { include mysql::server::disabled ... } or maybe node foo { include mysql::server::absent ... } You prefer to not be explicit about the latter two cases, and that''s fine, but it doesn''t change the number of different combinations of services your various nodes offer.> While it is easy saying a node what it should include so that it > provides the needed services, it is big task and unmaintanable to > specify exhaustively what nodes should not include.How maintainable it is depends in part on how many distinct configurations you need to manage. Do be aware that nodes that are configured identically do not need separate entries in the node list: node node1, node2 { include mysql::server } If you have more than a handful of distinct configurations, though, then you might be well served by an external node classifier. That''s a program you provide that Puppet uses to dynamically determine which classes should be included for each node. John -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
Eric Gerlach
2009-Dec-18 15:55 UTC
Re: [Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
I''d like to weigh in on this discussion a little bit. First of all, Alexandre, you might feel more at home with bcfg2. Bcfg2 by default manages *everything*, and tells you if something appears that is unmanaged, forcing you to either manage it or remove it. We looked at bcfg2, and whereas I liked its model, the puppet community is better, and bcfg2 uses XML files for configuration *shudder*. That is a feature I''d love to see in puppet. If unknown and new things appear on one of my systems, I''d love to know about it. That way I can either decide to add it to a manifest, or remove it. That, to me, is better than applying a general stripdown. A general stripdown (other than "remove everything not explicitly managed") doesn''t deal with the unknowns, and the "remove everything not explicitly managed" doesn''t allow for emergency fixes. tl;dr: I want to know when *anything* on my system changes, puppet doesn''t let me do that. Cheers, Eric On Thu, Dec 17, 2009 at 07:08:51PM -0800, Alexandre wrote:> Yes, in fact this is exactly what i have for the services -i want to > install or manage-. A base class with common stuff (eg mysql user, > group, pkg, test directories ... and service disabled by default), and > a child class ...::server with typically just include the service > specific config file and override Service[] to enable it > > But this was not my original problem. Let''s take an example : > 1) i want to apply a general linux stripdown > 2) i get a server, which had already stuff on it, maybe services > activated but not used, and on which sometimes people get on and > modify things (file permissions, start services, ...) > 3) I want to apply the general stripdown to this server, without > having to know what is there and create a special stripdown just for > this server > 4) I still want to install or activate services on this server, while > having the general stripdown still active > > So far i can do 1), 2) and 3) with puppet, very simply. My problem is > 4). All implementations of 4) i saw in this discussion say i have for > each node, specify exactly what i want to disable and enable, so that > if i have 100 nodes, i have to create 100 different stripdown. > While it is easy saying a node what it should include so that it > provides the needed services, it is big task and unmaintanable to > specify exhaustively what nodes should not include. Especially that > these nodes are used by some people that need some priviledges, but do > not always clean after work or are not sysadmins > > > > On Dec 17, 4:51 pm, Peter Meier <peter.me...@immerda.ch> wrote: > > -----BEGIN PGP SIGNED MESSAGE----- > > Hash: SHA1 > > > > > [...] > > > I think this is good general practice of sysadmin to ensure > > > everything on a linux system that is not needed should be removed, > > > restricted or disabled (services, users, dir permissions). As we see > > > here, it seems Puppet can not fullfill this need, except by listing > > > explicitely and exhaustively what needs to be or not be activated for > > > each node. So of course, one way or another, there is a place where i > > > need to tell what should be stripdowned. But i want it to be accepted > > > as the default -state- of the node, unless specified otherwise by > > > including a class which redefines some of the ressources that need to > > > be activated. I do not want my nodes.pp to be 1000000 lines and > > > unmaintanable. > > > > How about doing it the other way round? Generally include the > > stripped-down classes and then include additionally per node the mysql > > class which inherits the stripped down class but overwrites the > > resources to manage mysql: > > > > node default { > > include configsets > > > > } > > > > node mysqlserver { > > include configsets::mysqlserver > > > > } > > > > class configsets { > > include mysql::server > > > > } > > > > class configsets::mysqlserver { > > include config > > include mysql::server::present > > > > } > > > > class mysql::server { > > package{''mysql-server'': ensure => absent } > > service{''mysql-server'': > > ensure => stopped, > > enable => false, > > require => Package[''mysql-server''], > > } > > > > } > > > > class mysql::server::present inherits mysql::server { > > Package[''mysql-server'']{ ensure => installed } > > Service[''mysql-server'']{ > > ensure => running, > > enable => true, > > } > > file{''/etc/my.conf'': > > source => "...." > > notify => Service[''mysql-server''], > > } > > > > } > > > > Naming convention could be better, but I think this should generally > > work. You simply include every resource you manage in the general class > > configsets, which gets applied to every node (also due to inheritance, > > reinclusion) but include the "present" class in nodes that need it. > > > > > I do not want my nodes.pp to be 1000000 lines and unmaintanable. > > > > I would generally avoid putting too much into nodes. My nodes look like: > > > > node default { > > $some_var_1 = ''aaa'' > > $some_var_2 = ''bbb'' > > include configsets > > > > } > > > > node foobar { > > $some_var_1 = ''foo'' > > $some_var_2 = ''bar'' > > include configsets::foobar > > > > } > > > > And all the actual service includes are done in the module called > > configesets, which can have further abstraction like node-types, i.e. > > physical nodes (class is included depending on the virtual fact) etc., > > inheritance and so on. > > > > Did I miss some circumstances why this shouldn''t work? > > > > cheers pete. > > -----BEGIN PGP SIGNATURE----- > > Version: GnuPG v1.4.9 (GNU/Linux) > > Comment: Using GnuPG with Mozilla -http://enigmail.mozdev.org > > > > iEYEARECAAYFAksp8QQACgkQbwltcAfKi383ZwCdHOZO8yYdo6zooR07tgy5OE7/ > > ZhgAoJzWrZoO2ikcrO/ZRJVLE/fPcufr > > =/lYm > > -----END PGP SIGNATURE----- > > -- > > You received this message because you are subscribed to the Google Groups "Puppet Users" group. > To post to this group, send email to puppet-users@googlegroups.com. > To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. > For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en. > >-- Eric Gerlach, Network Administrator Federation of Students University of Waterloo p: (519) 888-4567 x36329 e: egerlach@feds.uwaterloo.ca -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.
Peter Meier
2009-Dec-18 16:05 UTC
Re: [Puppet Users] Re: How to override / redefine outside child class (usecase and example detailled)
> That is a feature I''d love to see in puppet. If unknown and new > things appear > on one of my systems, I''d love to know about it. That way I can > either decide > to add it to a manifest, or remove it. > [...] > tl;dr: I want to know when *anything* on my system changes, puppet > doesn''t let > me do that.Generally I like the idea, but I didn''t yet think of it in every detail. maybe it could be a bit more elaborated and then a feature request could be filed? cheers pete -- You received this message because you are subscribed to the Google Groups "Puppet Users" group. To post to this group, send email to puppet-users@googlegroups.com. To unsubscribe from this group, send email to puppet-users+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/puppet-users?hl=en.