[Cluster-devel] conga/luci storage/form-chooser storage/form-m ...

kupcevic at sourceware.org kupcevic at sourceware.org
Thu Aug 3 18:56:11 UTC 2006


CVSROOT:	/cvs/cluster
Module name:	conga
Changes by:	kupcevic at sourceware.org	2006-08-03 18:56:10

Modified files:
	luci/storage   : form-chooser form-macros index_html 
	luci/site/luci/Extensions: HelperFunctions.py StorageReport.py 
	                           conga_storage_constants.py 
	                           storage_adapters.py 

Log message:
	Change Storage Front Page

Patches:
http://sourceware.org/cgi-bin/cvsweb.cgi/conga/luci/storage/form-chooser.diff?cvsroot=cluster&r1=1.1&r2=1.2
http://sourceware.org/cgi-bin/cvsweb.cgi/conga/luci/storage/form-macros.diff?cvsroot=cluster&r1=1.3&r2=1.4
http://sourceware.org/cgi-bin/cvsweb.cgi/conga/luci/storage/index_html.diff?cvsroot=cluster&r1=1.5&r2=1.6
http://sourceware.org/cgi-bin/cvsweb.cgi/conga/luci/site/luci/Extensions/HelperFunctions.py.diff?cvsroot=cluster&r1=1.1&r2=1.2
http://sourceware.org/cgi-bin/cvsweb.cgi/conga/luci/site/luci/Extensions/StorageReport.py.diff?cvsroot=cluster&r1=1.5&r2=1.6
http://sourceware.org/cgi-bin/cvsweb.cgi/conga/luci/site/luci/Extensions/conga_storage_constants.py.diff?cvsroot=cluster&r1=1.2&r2=1.3
http://sourceware.org/cgi-bin/cvsweb.cgi/conga/luci/site/luci/Extensions/storage_adapters.py.diff?cvsroot=cluster&r1=1.2&r2=1.3

--- conga/luci/storage/form-chooser	2006/06/30 17:00:02	1.1
+++ conga/luci/storage/form-chooser	2006/08/03 18:56:09	1.2
@@ -5,7 +5,12 @@
   <body>
  
   <metal:choose-form metal:define-macro="main-form">
-
+    
+    <span tal:omit-tag=""
+          tal:define="global preferred_size_units python:here.set_persistant_var('preferred_size_units', 'GB')"/>
+    <span tal:omit-tag=""
+          tal:define="global preferred_path_display python:here.set_persistant_var('preferred_path_display', 'path')"/>
+    
 <!--
     <span tal:omit-tag="" tal:condition="python: storage_report == None and storagename != None">
       <div metal:use-macro="here/form-macros/macros/error-form"/>
--- conga/luci/storage/form-macros	2006/07/18 20:33:05	1.3
+++ conga/luci/storage/form-macros	2006/08/03 18:56:09	1.4
@@ -99,7 +99,19 @@
 
 
 <div metal:define-macro="commit-changes">
-   commiting changes...
+   <table style="width: 100%;">
+    <tr>
+     <td align="center">
+      <img src="100wait.gif" style="padding-top: 1cm;"/>
+     </td>
+    </tr>
+    <tr>
+     <td align="center">
+      <div style="padding-bottom: 4cm;">Commiting Changes</div>
+     </td>
+    </tr>
+   </table>
+
   <span tal:define="main_URL context/storage/index_html/absolute_url" 
         tal:replace="structure python:here.apply(ricci, storage_report, request, main_URL)">
    here.apply() response
@@ -164,75 +176,97 @@
 
 
   <div metal:define-macro="systems-form">
-   <table cellpadding="4"
-          tal:define="sort_by request/sort_by|nothing">
-    <tr tal:define="main_url context/storage/index_html/absolute_url">
-     <th>
-      <a tal:condition="python:sort_by == 'hostname' or sort_by == None"
-         tal:attributes="href python:main_url + '?pagetype=' + str(pagetype) + '&sort_by=hostname_reverse'">
-       Hostname
-      </a>
-      <a tal:condition="python:sort_by != 'hostname' and sort_by != None" 
-         tal:attributes="href python:main_url + '?pagetype=' + str(pagetype) + '&sort_by=hostname'">
-       Hostname
-      </a>
-     </th>
-     <th>
-      <a tal:condition="python:sort_by == 'OS'"
-         tal:attributes="href python:main_url + '?pagetype=' + str(pagetype) + '&sort_by=OS_reverse'">
-       Operating System
-      </a>
-      <a tal:condition="python:sort_by != 'OS'"
-         tal:attributes="href python:main_url + '?pagetype=' + str(pagetype) + '&sort_by=OS'">
-       Operating System
-      </a>
-     </th>
-     <th>
-      <a tal:condition="python:sort_by == 'cluster_name'"
-         tal:attributes="href python:main_url + '?pagetype=' + str(pagetype) + '&sort_by=cluster_name_reverse'">
-       Cluster Name
-      </a>
-      <a tal:condition="python:sort_by != 'cluster_name'"
-         tal:attributes="href python:main_url + '?pagetype=' + str(pagetype) + '&sort_by=cluster_name'">
-       Cluster Name
-      </a>
-     </th>
-     <th>
-      <a tal:condition="python:sort_by == 'cluster_alias'"
-         tal:attributes="href python:main_url + '?pagetype=' + str(pagetype) + '&sort_by=cluster_alias_reverse'">
-       Cluster Alias
-      </a>
-      <a tal:condition="python:sort_by != 'cluster_alias'"
-         tal:attributes="href python:main_url + '?pagetype=' + str(pagetype) + '&sort_by=cluster_alias'">
-       Cluster Alias
-      </a>
-     </th>
-    </tr>
-    <span tal:omit-tag="" 
-          tal:repeat="sys python:here.build_systems_list(sort_by, allowed_systems)">
-     <tr>
-      <td tal:define="tmp_host sys/hostname">
-       <a tal:condition="sys/available"
-          tal:attributes="href python:request['URL'] + '?pagetype=44&storagename=' + tmp_host">
-        <span tal:replace="tmp_host"/>
-       </a>
-       <span style="color:red" tal:condition="not: sys/available" tal:content="tmp_host"/>
-      </td>
-      <td>
-       <span tal:condition="sys/available" tal:replace="sys/OS"/>
-       <span style="color:red" tal:condition="not: sys/available" tal:content="sys/OS"/>
-      </td>
-      <td>
-       <span tal:replace="sys/cluname"/>
-      </td>
-      <td>
-       <span tal:replace="sys/clualias"/>
-      </td>
-     </tr>
-    </span>
-   </table>
-  </div> 
 
+   <fieldset>
+    <legend>
+     Storage Configuration Preferences
+    </legend>
+    <form>
+     <table>
+      <tr>
+       <td>
+        Display Sizes in
+       </td>
+       <td>
+        <select name="preferred_size_units" onchange="this.form.submit()">
+         <option value="MB" 
+                 tal:attributes="selected python:preferred_size_units == 'MB'">MB - MegaBytes</option>
+         <option value="GB" 
+                 tal:attributes="selected python:preferred_size_units == 'GB'">GB - GigaBytes</option>
+        </select>
+       </td>
+      </tr>
+      <tr>
+       <td>
+        Display Devices by
+       </td>
+       <td>
+        <select name="preferred_path_display" onchange="this.form.submit()">
+         <option value="path" 
+                 tal:attributes="selected python:preferred_path_display == 'path'">Device Path</option>
+         <option value="scsi" 
+                 tal:attributes="selected python:preferred_path_display == 'scsi'">SCSI ID</option>
+        </select>
+       </td>
+      </tr>
+     </table>
+    </form>
+   </fieldset> 
+   
+   <dl tal:define="tmp_triple   python:here.group_systems_by_cluster(allowed_systems);
+                   nonclu_list  python:tmp_triple[0];
+                   clu_list     python:tmp_triple[1];
+                   bad_list     python:tmp_triple[2]">
+    
+    <dt>
+     You are authorized to administer Storage Systems on the list to the left
+    </dt>
+    <dd>
+     Please, select one to administer
+    </dd>
+    
+    <dt>
+     <span tal:condition="not: bad_list">
+      All systems are up and running
+     </span>
+     <span tal:condition="bad_list">
+      You are authorized but unable to modify following systems:
+     </span>
+    </dt>
+    <dd>
+     <table tal:condition="bad_list">
+      <tr>
+       <th>
+        Hostname
+       </th>
+       <th>
+        Reason
+       </th>
+      </tr>
+      <span tal:omit-tag=""
+            tal:repeat="b bad_list">
+       <tr>
+        <td>
+         <span style="color: red;"
+               tal:content="b/hostname"></span> 
+        </td>
+        <td>
+         <span tal:omit-tag=""
+               tal:condition="b/available">
+          Requires System Reauthentication
+         </span>
+         <span tal:omit-tag=""
+               tal:condition="not: b/available">
+          Inaccessible
+         </span>
+        </td>
+       </tr>
+      </span>
+     </table>
+    </dd>
+   </dl>
+  </div> 
+ 
 
   <div metal:define-macro="error-form">
    <h2>Error Form</h2>
@@ -770,16 +804,18 @@
                                  value       prop/value;
                                  onkeypress  python:'return validate_text_keypress(this, event, 2, \'' + prop['validation']['illegal_chars'] + '\', ' + str(prop['validation']['max_length']) + ')';
                                  onblur      python:'validate_text(this, 2, \'' + prop['validation']['illegal_chars'] + '\', \'' + prop['validation']['reserved_words'] + '\', ' + str(prop['validation']['min_length']) + ', ' + str(prop['validation']['max_length']) + ')'"/>
-
+          
+          
+          
           <input tal:condition="python:prop_type == 'int'"
                  tal:attributes="name   p; 
                                  type   string:text; 
                                  value  prop/value;
                                  onblur python:'validate_int(this, 2, ' + str(prop['validation']['min']) + ', ' + str(prop['validation']['max']) + ', ' + str(prop['validation']['step']) + ')'"
                  onkeypress="return validate_int_keypress(this, event, 2)"/>
-
-
-
+          
+          
+          
           <span tal:condition="python:prop_type == 'select'">
            <select tal:define="prop_options prop/value"
                    tal:attributes="name p">
@@ -810,73 +846,7 @@
    <span tal:omit-tag=""
          tal:define="predefines_test python:'display-props: ' + str(props) + prefix + properties_span_id"/>
    <table>
-    <span tal:omit-tag="" 
-          tal:repeat="p props">
-     <tr tal:define="prop python:props[p];
-                     prop_pr_name prop/pretty_name">
-      <td tal:content="prop_pr_name"/>
-      <td tal:define="prop_type prop/type;
-                      prop_units prop/units">
-       <table>
-        <tr>
-         <td>
-          <span tal:condition="python:prop_type == 'label'">
-           <span tal:omit-tag=""
-                 tal:condition="prop/replacements|nothing">
-            <input tal:attributes="type string:hidden;
-                                   name p;
-                                   value prop/value"/>
-            <select tal:define="repls prop/replacements;
-                                select_id python:prefix + '_select_replace_block_' + p"
-                    tal:attributes="id       select_id;
-                                    onfocus  python:'replace_properties_block__old_select_value = this.value';
-                                    onchange python:'replace_properties_block(\'' + properties_span_id + '\', \'' + select_id + '\')'">
-             <span tal:omit-tag="" 
-                   tal:repeat="repl_name repls/repl_names">
-              <option tal:attributes="value python:repls[repl_name]['path']"/><span tal:replace="repl_name"/>
-             </span>
-            </select>
-           </span>
-           <span tal:condition="not: prop/replacements|nothing"
-                 tal:replace="prop/value"/>
-          </span>
-
-
-
-          <input tal:condition="python:prop_type == 'text'"
-                 tal:attributes="name        p; 
-                                 type        string:text; 
-                                 value       prop/value;
-                                 onkeypress  python:'return validate_text_keypress(this, event, 2, \'' + prop['validation']['illegal_chars'] + '\', ' + str(prop['validation']['max_length']) + ')';
-                                 onblur      python:'validate_text(this, 2, \'' + prop['validation']['illegal_chars'] + '\', \'' + prop['validation']['reserved_words'] + '\', ' + str(prop['validation']['min_length']) + ', ' + str(prop['validation']['max_length']) + ')'"/>
-
-          <input tal:condition="python:prop_type == 'int'"
-                 tal:attributes="name   p; 
-                                 type   string:text; 
-                                 value  prop/value;
-                                 onblur python:'validate_int(this, 2, ' + str(prop['validation']['min']) + ', ' + str(prop['validation']['max']) + ', ' + str(prop['validation']['step']) + ')'"
-                 onkeypress="return validate_int_keypress(this, event, 2)"/>
-
-
-
-          <span tal:condition="python:prop_type == 'select'">
-           <select tal:define="prop_options prop/value"
-                   tal:attributes="name p">
-            <span tal:omit-tag="" 
-                  tal:repeat="prop_opt prop_options">
-             <option tal:attributes="value prop_opt"/><span tal:replace="prop_opt"/>
-            </span>
-           </select>
-          </span>
-         </td>
-         <td>
-          <span tal:replace="prop_units"/>
-         </td>
-        </tr>
-       </table>
-      </td>
-     </tr>
-    </span>
+    <div metal:use-macro="here/form-macros/macros/display-props-tableless"/>
    </table>
   </div>
 
--- conga/luci/storage/index_html	2006/08/02 17:01:58	1.5
+++ conga/luci/storage/index_html	2006/08/03 18:56:09	1.6
@@ -213,7 +213,7 @@
                       Page body text
                     </metal:bodytext>
                     <span tal:omit-tag="" tal:condition="not: storagename">
-                      <h1>Choose a storage system to administer</h1>
+                      <h1>Welcome to Storage Configuration Interface</h1>
                     </span>
                     <span tal:omit-tag="" tal:condition="storagename">
                       <h1 tal:content="storagename"></h1>
--- conga/luci/site/luci/Extensions/HelperFunctions.py	2006/05/30 20:17:21	1.1
+++ conga/luci/site/luci/Extensions/HelperFunctions.py	2006/08/03 18:56:10	1.2
@@ -21,5 +21,72 @@
 def access_to_host_allowed(self, hostname, allowed_systems):
   for system in allowed_systems:
     if system[0] == hostname:
-      return True
+      if len(self.allowed_systems(None, [system])) == 1:
+          return True
+      else:
+          return False
   return False
+
+
+
+# removes systems that user is not authorized access to
+def get_systems_statuses(self, systems):
+    ss = {}
+    ass = self.allowed_systems(self, None, systems)
+    for system in ass:
+        hostname = system[0]
+        OS = ''
+        cluname = ''
+        cluali = ''
+        authed = False
+        ricci = self.get_ricci_communicator(hostname, ass)
+        if ricci != None:
+            OS = ricci.os()
+            cluname = ricci.cluster_info()[0]
+            cluali = ricci.cluster_info()[1]
+            authed = ricci.authed()
+        else:
+            OS = 'System not accessible'
+        s = {'hostname' : hostname,
+             'OS'       : OS,
+             'cluname'  : cluname,
+             'clualias' : cluali, 
+             'available': ricci != None,
+             'authed'   : authed}
+        ss[hostname] = s
+        pass
+    ss_list = []
+    sorted_keys = ss.keys()
+    sorted_keys.sort()
+    for name in sorted_keys:
+        ss_list.append(ss[name])
+    return ss_list
+
+
+
+
+def set_persistant_var(self,
+                       var_name,
+                       default_value):
+    request = self.REQUEST
+    response = request.RESPONSE
+    session = request.SESSION
+    
+    # TODO: add username into cookie_prefix, so users don't overwrite each other
+    cookie_prefix = '__luci_storage_cookie_'
+    
+    value = default_value
+    if request.has_key(var_name):
+        value = request[var_name]
+    elif session.has_key(var_name):
+        value = session[var_name]
+    elif request.cookies.has_key(cookie_prefix + var_name):
+        value = request.cookies[cookie_prefix + var_name]
+    
+    session.set(var_name,
+                value)
+    response.setCookie(cookie_prefix + var_name,
+                       value, 
+                       expires='Tue, 30 Jun 2020 12:00:00 GMT')
+    
+    return value
--- conga/luci/site/luci/Extensions/StorageReport.py	2006/08/02 23:18:57	1.5
+++ conga/luci/site/luci/Extensions/StorageReport.py	2006/08/03 18:56:10	1.6
@@ -1480,7 +1480,6 @@
     return data
 
 
-
 def get_props_data_internal(session, xml_tag):
     data = {}
     removable = False
@@ -1704,83 +1703,48 @@
     return name, id
 
 
-def build_systems_list(self, sort_by, allowed_systems):
-    sysl = []
-    for sys in allowed_systems:
-        hostname = sys[0]
-        OS = ''
-        cluname = ''
-        cluali = ''
-        ricci = self.get_ricci_communicator(hostname, allowed_systems)
-        if ricci != None:
-            OS = ricci.os()
-            cluname = ricci.cluster_info()[0]
-            cluali = ricci.cluster_info()[1]
+
+def group_systems_by_cluster(self, allowed_systems, cache_it=False):
+    CACHED_INDEX = '_group_systems_by_cluster_cached_result_'
+    session = self.REQUEST.SESSION
+    if session.has_key(CACHED_INDEX):
+        res = session[CACHED_INDEX]
+        if res != None:
+            session.set(CACHED_INDEX, None)
+            return res
+        pass
+    
+    ss = get_systems_statuses(self, allowed_systems)
+    clusters = {}
+    bad_list = []
+    for s in ss:
+        if s['authed']:
+            cluname = s['cluname']
+            if cluname not in clusters:
+                clusters[cluname] = []
+            clusters[cluname].append(s)
         else:
-            OS = 'System not accessible'
-        s = {'hostname' : hostname,
-             'OS'       : OS,
-             'cluname'  : cluname,
-             'clualias' : cluali, 
-             'available': ricci != None}
-        sysl.append(s)
-    
-    sorted = []
-    
-    if sort_by == 'OS' or sort_by == 'OS_reverse':
-        s_l = []
-        for sys in sysl:
-            os = sys['OS']
-            if os not in s_l:
-                s_l.append(os)
-        s_l.sort()
-        if sort_by == 'OS_reverse':
-            s_l.reverse()
-        for s in s_l:
-            for sys in sysl:
-                if sys['OS'] == s:
-                    sorted.append(sys)
-    elif sort_by == 'cluster_name' or sort_by == 'cluster_name_reverse':
-        s_l = []
-        for sys in sysl:
-            os = sys['cluname']
-            if os not in s_l:
-                s_l.append(os)
-        s_l.sort()
-        if sort_by == 'cluster_name_reverse':
-            s_l.reverse()
-        for s in s_l:
-            for sys in sysl:
-                if sys['cluname'] == s:
-                    sorted.append(sys)
-    elif sort_by == 'cluster_alias' or sort_by == 'cluster_alias_reverse':
-        s_l = []
-        for sys in sysl:
-            os = sys['clualias']
-            if os not in s_l:
-                s_l.append(os)
-        s_l.sort()
-        if sort_by == 'cluster_alias_reverse':
-            s_l.reverse()
-        for s in s_l:
-            for sys in sysl:
-                if sys['clualias'] == s:
-                    sorted.append(sys)
-    else:
-        s_l = []
-        for sys in sysl:
-            os = sys['hostname']
-            if os not in s_l:
-                s_l.append(os)
-        s_l.sort()
-        if sort_by == 'hostname_reverse':
-            s_l.reverse()
-        for s in s_l:
-            for sys in sysl:
-                if sys['hostname'] == s:
-                    sorted.append(sys)
+            bad_list.append(s)
+    clu_list = []
+    nonclu_list = []
+    for cluname in clusters:
+        if cluname == '':
+            nonclu_list = clusters[cluname]
+        else:
+            cl = {'name'  : cluname,
+                  'alias' : clusters[cluname][0]['clualias'], 
+                  'nodes' : clusters[cluname]}
+            clu_list.append(cl)
     
-    return sorted
+    ret = [nonclu_list, clu_list, bad_list]
+    
+    if cache_it:
+        session.set(CACHED_INDEX, ret)
+        pass
+    
+    return ret
+
+
 
 
 def get_mappings_info(self,
--- conga/luci/site/luci/Extensions/conga_storage_constants.py	2006/07/12 23:12:01	1.2
+++ conga/luci/site/luci/Extensions/conga_storage_constants.py	2006/08/03 18:56:10	1.3
@@ -57,6 +57,7 @@
 STORAGESYS="0"
 STORAGE_CONFIG="43"
 STORAGE="44"
+CLUSTER_STORAGE="45"
 
 STORAGE_COMMIT_CHANGES='commit_changes'
 
--- conga/luci/site/luci/Extensions/storage_adapters.py	2006/07/25 00:52:52	1.2
+++ conga/luci/site/luci/Extensions/storage_adapters.py	2006/08/03 18:56:10	1.3
@@ -8,6 +8,7 @@
 from conga_storage_constants import *
 from ricci_defines import *
 from Variable import parse_variable
+from HelperFunctions import get_systems_statuses
 
 
 
@@ -39,7 +40,7 @@
     pagetype = request[PAGETYPE]
   except KeyError, e:
     pagetype = "0"
-
+  
   sdata = {}
   sdata['Title'] = "System List"
   sdata['cfg_type'] = "storages"
@@ -54,24 +55,28 @@
   else:
     sdata['show_children'] = False
   
-  # loop through systems
+  
   syslist= list()
-  for system in systems:
-    ssys = {}
-    ssys['Title'] = system[0]
-    ssys['cfg_type'] = "storage"
-    ssys['absolute_url'] = url + '?' + PAGETYPE + '=' + STORAGE + "&" + STONAME + "=" + system[0]
-    ssys['Description'] = "Configure storage on " + system[0]
-    
-    if pagetype == STORAGE:
-      if stoname == system[0]:
-        ssys['currentItem'] = True
-      else:
-        ssys['currentItem'] = False
+  if sdata['show_children']:
+    #display_clusters = True
+    display_clusters = False
+    if display_clusters:
+      sorted_data = self.group_systems_by_cluster(systems, cache_it=True)
+      for sdl in sorted_data[:2]:
+        for data in sdl:
+          createStorageChooser_inner(url,
+                                     pagetype,
+                                     stoname,
+                                     data,
+                                     syslist)
     else:
-      ssys['currentItem'] = False
-    syslist.append(ssys)
-
+      sorted_data = get_systems_statuses(self, systems)
+      for data in sorted_data:
+        createStorageChooser_inner(url,
+                                   pagetype,
+                                   stoname,
+                                   data,
+                                   syslist)
   sdata['children'] = syslist
   
   mylist = list()
@@ -83,7 +88,47 @@
   return dummynode
 
 
-
+def createStorageChooser_inner(url,
+                               pagetype,
+                               stoname,
+                               system_data,
+                               syslist):
+  ssys = {}
+  if 'nodes' in system_data:
+    title = system_data['name']
+    if system_data['alias'] != '':
+      title = system_data['alias'] + ' (' + title + ')'
+    ssys['Title'] = 'Cluster ' + title
+    ssys['cfg_type'] = "storage"
+    ssys['absolute_url'] = url + '?' + PAGETYPE + '=' + CLUSTER_STORAGE + "&" + CLUNAME + "=" + system_data['name']
+    ssys['Description'] = "Configure shared storage of cluster " + title
+    ssys['currentItem'] = False
+    ssys['show_children'] = True
+    kids = []
+    for node in system_data['nodes']:
+      createStorageChooser_inner(url,
+                                 pagetype,
+                                 stoname,
+                                 node,
+                                 kids)
+    ssys['children'] = kids
+  else:
+    if system_data['authed'] == False:
+      return
+    ssys['Title'] = system_data['hostname']
+    ssys['cfg_type'] = "storage"
+    ssys['absolute_url'] = url + '?' + PAGETYPE + '=' + STORAGE + "&" + STONAME + "=" + system_data['hostname']
+    ssys['Description'] = "Configure storage on " + system_data['hostname']
+    
+    if pagetype == STORAGE:
+      if stoname == system[0]:
+        ssys['currentItem'] = True
+      else:
+        ssys['currentItem'] = False
+    else:
+      ssys['currentItem'] = False
+  syslist.append(ssys)
+  return
 
 
 




More information about the Cluster-devel mailing list