Shares without type setting should still show up in list
[pyTivo.git] / plugins / admin / admin.py
blobbfc694950b7944c9c25760da8795e6b8eb194c1b
1 import os, socket, re, sys, ConfigParser, config
2 from ConfigParser import NoOptionError
3 from Cheetah.Template import Template
4 from plugin import Plugin
5 from urllib import unquote_plus, quote, unquote
6 from xml.sax.saxutils import escape
7 from lrucache import LRUCache
9 SCRIPTDIR = os.path.dirname(__file__)
11 CLASS_NAME = 'Admin'
13 p = os.path.dirname(__file__)
14 p = p.split(os.path.sep)
15 p.pop()
16 p.pop()
17 p = os.path.sep.join(p)
18 config_file_path = os.path.join(p, 'pyTivo.conf')
20 class Admin(Plugin):
21 CONTENT_TYPE = 'text/html'
23 def Restart(self, handler, query):
24 config.reset()
25 handler.server.reset()
26 handler.send_response(200)
27 handler.end_headers()
29 def Admin(self, handler, query):
30 #Read config file new each time in case there was any outside edits
31 config = ConfigParser.ConfigParser()
32 config.read(config_file_path)
34 shares_data = []
35 for section in config.sections():
36 if not(section.startswith('_tivo_') or section.startswith('Server')):
37 if not(config.has_option(section,'type')):
38 shares_data.append((section, dict(config.items(section, raw=True))))
39 elif config.get(section,'type').lower() != 'admin':
40 shares_data.append((section, dict(config.items(section, raw=True))))
42 subcname = query['Container'][0]
43 cname = subcname.split('/')[0]
44 handler.send_response(200)
45 handler.end_headers()
46 t = Template(file=os.path.join(SCRIPTDIR,'templates', 'settings.tmpl'))
47 t.container = cname
48 t.server_data = dict(config.items('Server', raw=True))
49 t.server_known = ["port", "guid", "ffmpeg", "beacon", "hack83", "debug", \
50 "optres", "audio_br", "video_br", "max_video_br", "width",\
51 "height", "ffmpeg_prams", "bufsize"]
52 t.shares_data = shares_data
53 t.shares_known = ["type", "path", "auto_subshares"]
54 t.tivos_data = [ (section, dict(config.items(section, raw=True))) for section in config.sections() \
55 if section.startswith('_tivo_')]
56 t.tivos_known = ["aspect169", "audio_br", "video_br", "width", "height", "ffmpeg_prams"]
57 handler.wfile.write(t)
59 def QueryContainer(self, handler, query):
60 #Read config file new each time in case there was any outside edits
61 config = ConfigParser.ConfigParser()
62 config.read(config_file_path)
64 def build_inputs(settings, data, section):
65 output = ''
66 for key in settings:
67 try:
68 output += "<tr><td>" + key + ": </td><td><input type='text' name='" + section + "." + key + "' value='" + data[key] +"'></td></tr>"
69 del data[key]
70 except:
71 output += "<tr><td>" + key + ": </td><td><input type='text' name='" + section + "." + key + "' value=''></td></tr>"
72 #print remaining miscellaneous settings
73 if len(data) > 0:
74 output += '<tr><td colspan="2" align="center">User Defined Settings</td></tr>'
75 for item in data:
76 output += "<tr><td>" + item + ": </td><td><input type='text' name='" + section + "." + item + "' value='" + data[item] +"'></td></tr>"
77 output += '<tr><td colspan="2" align="center">Add a User Defined Setting to this Share</td></tr>'
78 output += "<tr><td><input type='text' name='" + section + ".new__setting' value=''></td><td><input type='text' name='" + section + ".new__value' value=''></td></tr>"
79 return output
81 server_data = dict(config.items('Server'))
82 server = ''
83 #build an array with configuration settings to use
84 settings = ["port", "guid", "ffmpeg", "beacon", "hack83", "debug", "optres", "audio_br", "video_br", "max_video_br", "width", "height", "ffmpeg_prams", "bufsize"]
85 server += build_inputs(settings, server_data, 'Server')
87 #Keep track of the different sections
88 section_map = ''
89 section_count = 1
91 shares_data = [ (section, dict(config.items(section))) for section in config.sections() if not(section.startswith('_tivo_') or section.startswith('Server')) and (config.has_option(section,'type') and config.get(section,'type').lower() != 'admin')]
92 shares =''
93 for name, data in shares_data:
94 shares += '<tr><td colspan="2" align="center">----------------------------------</td></tr>'
95 shares += '<tr><td colspan="2" align="center">[<input type="text" id="section_' + str(section_count) + '" name="section-' + str(section_count) + '" value="' + name + '">]</td></tr>'
96 #build an array with configuration settings to use
97 settings = ["type", "path", "auto_subshares"]
98 shares += build_inputs(settings, data, "section-" + str(section_count))
99 shares += '<tr><td colspan="2" align="center">Mark this share for deletion <input type="button" value="Delete" onclick="deleteme(\'section_' + str(section_count) + '\')"></td></tr>'
100 section_map += "section-" + str(section_count) + ":" + name + "/"
101 section_count += 1
103 tivos_data = [ (section, dict(config.items(section))) for section in config.sections() if section.startswith('_tivo_')]
104 tivos =''
105 for name, data in tivos_data:
106 tivos += '<tr><td colspan="2" align="center">----------------------------------</td></tr>'
107 tivos += '<tr><td colspan="2" align="center">[<input type="text" id="section_' + str(section_count) + '" name="section-' + str(section_count) + '" value="' + name + '">]</td></tr>'
108 #build an array with configuration settings to use
109 settings = ["aspect169", "audio_br", "video_br", "width", "height", "ffmpeg_prams"]
110 tivos += build_inputs(settings, data, "section-" + str(section_count))
111 tivos += '<tr><td colspan="2" align="center">Mark this TiVo for deletion <input type="button" value="Delete" onclick="deleteme(\'section_' + str(section_count) + '\')"></td></tr>'
112 section_map += "section-" + str(section_count) + ":" + name + "/"
113 section_count += 1
115 subcname = query['Container'][0]
116 cname = subcname.split('/')[0]
117 handler.send_response(200)
118 handler.end_headers()
119 t = Template(file=os.path.join(SCRIPTDIR,'templates', 'admin.tmpl'))
120 t.container = cname
121 t.server = server
122 t.shares = shares
123 t.tivos = tivos
124 t.section_map = section_map
125 handler.wfile.write(t)
126 config.read(config_file_path + '.dist')
128 def UpdateSettings(self, handler, query):
129 config = ConfigParser.ConfigParser()
130 config.read(config_file_path)
131 for key in query:
132 if key.startswith('Server.'):
133 section, option = key.split('.')
134 if option == "new__setting":
135 new_setting = query[key][0]
136 continue
137 if option == "new__value":
138 new_value = query[key][0]
139 continue
140 if query[key][0] == " ":
141 config.remove_option(section, option)
142 else:
143 config.set(section, option, query[key][0])
144 if not(new_setting == ' ' and new_value == ' '):
145 config.set('Server', new_setting, new_value)
147 sections = query['Section_Map'][0].split('/')
148 sections.pop() #last item is junk
149 for section in sections:
150 ID, name = section.split(':')
151 if query[ID][0] == "Delete_Me":
152 config.remove_section(name)
153 continue
154 if query[ID][0] != name:
155 config.remove_section(name)
156 config.add_section(query[ID][0])
157 for key in query:
158 if key.startswith(ID + '.'):
159 junk, option = key.split('.')
160 if option == "new__setting":
161 new_setting = query[key][0]
162 continue
163 if option == "new__value":
164 new_value = query[key][0]
165 continue
166 if query[key][0] == " ":
167 config.remove_option(query[ID][0], option)
168 else:
169 config.set(query[ID][0], option, query[key][0])
170 if not(new_setting == ' ' and new_value == ' '):
171 config.set(query[ID][0], new_setting, new_value)
172 if query['new_Section'][0] != " ":
173 config.add_section(query['new_Section'][0])
174 f = open(config_file_path, "w")
175 config.write(f)
176 f.close()
178 subcname = query['Container'][0]
179 cname = subcname.split('/')[0]
180 handler.send_response(200)
181 handler.end_headers()
182 t = Template(file=os.path.join(SCRIPTDIR,'templates', 'redirect.tmpl'))
183 t.container = cname
184 handler.wfile.write(t)