support user created conf_files for slices
[plcapi.git] / PLC / ConfFiles.py
1 #
2 # Functions for interacting with the conf_files table in the database
3 #
4 # Mark Huang <mlhuang@cs.princeton.edu>
5 # Copyright (C) 2006 The Trustees of Princeton University
6 #
7 # $Id: ConfFiles.py 5574 2007-10-25 20:33:17Z thierry $
8 #
9
10 from PLC.Faults import *
11 from PLC.Parameter import Parameter
12 from PLC.Filter import Filter
13 from PLC.Table import Row, Table
14 from PLC.Nodes import Node, Nodes
15 from PLC.NodeGroups import NodeGroup, NodeGroups
16
17 class ConfFile(Row):
18     """
19     Representation of a row in the conf_files table. To use,
20     instantiate with a dict of values.
21     """
22
23     table_name = 'conf_files'
24     primary_key = 'conf_file_id'
25     join_tables = ['conf_file_node', 'conf_file_nodegroup']
26     fields = {
27         'conf_file_id': Parameter(int, "Configuration file identifier"),
28         'enabled': Parameter(bool, "Configuration file is active"),
29         'source': Parameter(str, "Relative path on the boot server where file can be downloaded", max = 255),
30         'dest': Parameter(str, "Absolute path where file should be installed", max = 255),
31         'file_permissions': Parameter(str, "chmod(1) permissions", max = 20),
32         'file_owner': Parameter(str, "chown(1) owner", max = 50),
33         'file_group': Parameter(str, "chgrp(1) owner", max = 50),
34         'preinstall_cmd': Parameter(str, "Shell command to execute prior to installing", max = 1024, nullok = True),
35         'postinstall_cmd': Parameter(str, "Shell command to execute after installing", max = 1024, nullok = True),
36         'error_cmd': Parameter(str, "Shell command to execute if any error occurs", max = 1024, nullok = True),
37         'ignore_cmd_errors': Parameter(bool, "Install file anyway even if an error occurs"),
38         'always_update': Parameter(bool, "Always attempt to install file even if unchanged"),
39         'site_id': Parameter(int, "Identifier of the site to which this conf file belongs"),
40         'creator_id': Parameter(int, "Identifer of the person who created this conf file"),
41         'last_modified_by_id': Parameter(int, "Identifier of the person who last updated this conf file"),
42         'date_created': Parameter(int, "Date and time when this conf file was created", ro = True), 
43         'last_modified': Parameter(int, "Date and time when this conf file was last modified", ro = True), 
44         'node_ids': Parameter(int, "List of nodes linked to this file"),
45         'nodegroup_ids': Parameter(int, "List of node groups linked to this file"),
46         }
47
48     def add_node(self, node, commit = True):
49         """
50         Add configuration file to node.
51         """
52
53         assert 'conf_file_id' in self
54         assert isinstance(node, Node)
55         assert 'node_id' in node
56
57         conf_file_id = self['conf_file_id']
58         node_id = node['node_id']
59
60         if node_id not in self['node_ids']:
61             self.api.db.do("INSERT INTO conf_file_node (conf_file_id, node_id)" \
62                            " VALUES(%(conf_file_id)d, %(node_id)d)",
63                            locals())
64
65             if commit:
66                 self.api.db.commit()
67
68             self['node_ids'].append(node_id)
69             node['conf_file_ids'].append(conf_file_id)
70
71     def remove_node(self, node, commit = True):
72         """
73         Remove configuration file from node.
74         """
75
76         assert 'conf_file_id' in self
77         assert isinstance(node, Node)
78         assert 'node_id' in node
79
80         conf_file_id = self['conf_file_id']
81         node_id = node['node_id']
82
83         if node_id in self['node_ids']:
84             self.api.db.do("DELETE FROM conf_file_node" \
85                            " WHERE conf_file_id = %(conf_file_id)d" \
86                            " AND node_id = %(node_id)d",
87                            locals())
88
89             if commit:
90                 self.api.db.commit()
91
92             self['node_ids'].remove(node_id)
93             node['conf_file_ids'].remove(conf_file_id)
94
95     def add_nodegroup(self, nodegroup, commit = True):
96         """
97         Add configuration file to node group.
98         """
99
100         assert 'conf_file_id' in self
101         assert isinstance(nodegroup, NodeGroup)
102         assert 'nodegroup_id' in nodegroup
103
104         conf_file_id = self['conf_file_id']
105         nodegroup_id = nodegroup['nodegroup_id']
106
107         if nodegroup_id not in self['nodegroup_ids']:
108             self.api.db.do("INSERT INTO conf_file_nodegroup (conf_file_id, nodegroup_id)" \
109                            " VALUES(%(conf_file_id)d, %(nodegroup_id)d)",
110                            locals())
111
112             if commit:
113                 self.api.db.commit()
114
115             self['nodegroup_ids'].append(nodegroup_id)
116             nodegroup['conf_file_ids'].append(conf_file_id)
117
118     def remove_nodegroup(self, nodegroup, commit = True):
119         """
120         Remove configuration file from node group.
121         """
122
123         assert 'conf_file_id' in self
124         assert isinstance(nodegroup, NodeGroup)
125         assert 'nodegroup_id' in nodegroup
126
127         conf_file_id = self['conf_file_id']
128         nodegroup_id = nodegroup['nodegroup_id']
129
130         if nodegroup_id in self['nodegroup_ids']:
131             self.api.db.do("DELETE FROM conf_file_nodegroup" \
132                            " WHERE conf_file_id = %(conf_file_id)d" \
133                            " AND nodegroup_id = %(nodegroup_id)d",
134                            locals())
135
136             if commit:
137                 self.api.db.commit()
138
139             self['nodegroup_ids'].remove(nodegroup_id)
140             nodegroup['conf_file_ids'].remove(conf_file_id)
141
142     def update_last_modified():
143         """
144         Update last_updated field with current time
145         """
146
147         assert 'conf_file_id' in self
148         assert self.table_name
149
150         self.api.db.do("UPDATE %s SET last_modified = CURRENT_TIMESTAMP " % (self.table_name) + \
151                        " where conf_file_id = %d" % (self['conf_file_id']) )
152         self.sync(commit)
153
154     validate_date_created = Row.validate_timestamp
155     validate_last_updated = Row.validate_timestamp              
156
157 class ConfFiles(Table):
158     """
159     Representation of the conf_files table in the database.
160     """
161
162     def __init__(self, api, conf_file_filter = None, columns = None):
163         Table.__init__(self, api, ConfFile, columns)
164
165         sql = "SELECT %s FROM view_conf_files WHERE True" % \
166               ", ".join(self.columns)
167
168         if conf_file_filter is not None:
169             if isinstance(conf_file_filter, (list, tuple, set)):
170                 conf_file_filter = Filter(ConfFile.fields, {'conf_file_id': conf_file_filter})
171             elif isinstance(conf_file_filter, dict):
172                 conf_file_filter = Filter(ConfFile.fields, conf_file_filter)
173             sql += " AND (%s) %s" % conf_file_filter.sql(api)
174
175         self.selectall(sql)