Check-in [555911dff5]
Not logged in
Overview

SHA1 Hash:555911dff52103c7831b172659b1963ea2c48826
Date: 2007-11-21 03:01:40
User: drh
Comment:Render the header of every page using subscript. Add a setup page that for editing that subscript.
Timelines: ancestors | descendants | both | trunk
Other Links: files | ZIP archive | manifest

Tags And Properties
Changes
[hide diffs]

Modified src/cgi.c from [36809061c4] to [fb85a3385b].

@@ -358,10 +358,22 @@
 **
 ** Copies are made of both the zName and zValue parameters.
 */
 void cgi_set_parameter(const char *zName, const char *zValue){
   cgi_set_parameter_nocopy(mprintf("%s",zName), mprintf("%s",zValue));
+}
+
+/*
+** Replace a parameter with a new value.
+*/
+void cgi_replace_parameter(const char *zName, const char *zValue){
+  int i;
+  for(i=0; i<nUsedQP; i++){
+    if( strcmp(aParamQP[i].zName,zName)==0 ){
+      aParamQP[i].zValue = zValue;
+    }
+  }
 }
 
 /*
 ** Add a query parameter.  The zName portion is fixed but a copy
 ** must be made of zValue.

Modified src/setup.c from [24c8846279] to [d38440e1a3].

@@ -67,12 +67,14 @@
     "Control access settings.");
   setup_menu_entry("Configuration", "setup_config",
     "Configure the WWW components of the repository");
   setup_menu_entry("Tickets", "tktsetup",
     "Configure the trouble-ticketing system for this repository");
-  setup_menu_entry("CSS", "editcss",
+  setup_menu_entry("CSS", "setup_editcss",
     "Edit the Cascading Style Sheet used by all pages of this repository");
+  setup_menu_entry("Header", "setup_header",
+    "Edit HTML text inserted at the top of every page");
   @ </dl>
 
   style_footer();
 }
 
@@ -479,21 +481,23 @@
 static void textarea_attribute(
   const char *zLabel,   /* The text label on the textarea */
   int rows,             /* Rows in the textarea */
   int cols,             /* Columns in the textarea */
   const char *zVar,     /* The corresponding row in the VAR table */
-  const char *zQParm,   /* The query parameter */
+  const char *zQP,      /* The query parameter */
   char *zDflt           /* Default value if VAR table entry does not exist */
 ){
-  const char *zVal = db_get(zVar, zDflt);
-  const char *zQ = P(zQParm);
-  if( zQ && strcmp(zQ,zVal)!=0 ){
+  const char *z = db_get(zVar, zDflt);
+  const char *zQ = P(zQP);
+  if( zQ && strcmp(zQ,z)!=0 ){
     db_set(zVar, zQ, 0);
-    zVal = zQ;
+    z = zQ;
   }
-  @ <textarea name="%s(zQParm)" rows="%d(rows)" cols="%d(cols)">%h(zVal)</textarea>
-  @ %s(zLabel)
+  if( rows>0 && cols>0 ){
+    @ <textarea name="%s(zQP)" rows="%d(rows)" cols="%d(cols)">%h(z)</textarea>
+    @ %s(zLabel)
+  }
 }
 
 
 /*
 ** WEBPAGE: setup_access
@@ -550,11 +554,12 @@
   @ <hr />
   entry_attribute("Project Name", 60, "project-name", "pn", "");
   @ <p>Give your project a name so visitors know what this site is about.
   @ The project name will also be used as the RSS feed title.</p>
   @ <hr />
-  textarea_attribute("Project Description", 5, 60, "project-description", "pd", "");
+  textarea_attribute("Project Description", 5, 60,
+                     "project-description", "pd", "");
   @ <p>Describe your project. This will be used in page headers for search
   @ engines as well as a short RSS description.</p>
   @ <hr />
   @ <p><input type="submit"  name="submit" value="Apply Changes"></p>
   @ </form>
@@ -561,21 +566,59 @@
   db_end_transaction(0);
   style_footer();
 }
 
 /*
-** WEBPAGE: editcss
+** WEBPAGE: setup_editcss
 */
 void setup_editcss(void){
   login_check_credentials();
   if( !g.okSetup ){
     login_needed();
   }
   style_header("Edit CSS");
-  @ <form action="%s(g.zBaseURL)/editcss" method="POST">
+  @ <form action="%s(g.zBaseURL)/setup_editcss" method="POST">
   @ Edit the CSS:<br />
   textarea_attribute("", 40, 80, "css", "css", zDefaultCSS);
   @ <br />
   @ <input type="submit" name="submit" value="Apply Changes">
   @ </form>
+  @ <hr>
+  @ Here is the default CSS:
+  @ <blockquote><pre>
+  @ %h(zDefaultCSS)
+  @ </pre></blockquote>
   style_footer();
+}
+
+/*
+** WEBPAGE: setup_header
+*/
+void setup_header(void){
+  login_check_credentials();
+  if( !g.okSetup ){
+    login_needed();
+  }
+  db_begin_transaction();
+  if( P("clear")!=0 ){
+    db_multi_exec("DELETE FROM config WHERE name='header'");
+    cgi_replace_parameter("header", zDefaultHeader);
+  }else{
+    textarea_attribute(0, 0, 0, "header", "header", zDefaultHeader);
+  }
+  style_header("Edit Page Header");
+  @ <form action="%s(g.zBaseURL)/setup_header" method="POST">
+  @ <p>Edit HTML text with embedded subscript that will be used to
+  @ generate the beginning of every page through start of the main
+  @ menu.</p>
+  textarea_attribute("", 40, 80, "header", "header", zDefaultHeader);
+  @ <br />
+  @ <input type="submit" name="submit" value="Apply Changes">
+  @ <input type="submit" name="clear" value="Revert To Default">
+  @ </form>
+  @ <hr>
+  @ Here is the default page header:
+  @ <blockquote><pre>
+  @ %h(zDefaultHeader)
+  @ </pre></blockquote>
+  db_end_transaction(0);
 }

Modified src/style.c from [7ae579f21d] to [a2b3fea577].

@@ -69,65 +69,56 @@
 /*
 ** Draw the header.
 */
 void style_header(const char *zTitle){
   const char *zLogInOut = "Logout";
-  char *zProjectDescr = db_get("project-description", 0);
+  const char *zHeader = db_get("header", zDefaultHeader);
+  struct Subscript *p;
   login_check_credentials();
-  @ <html>
-  @ <head>
-  @ <title>%s(zTitle)</title>
-  @ <link rel="alternate" type="application/rss+xml" title="RSS Feed" href="%s(g.zBaseURL)/timeline.rss">
-  @ <link rel="stylesheet" href="%s(g.zBaseURL)/style.css" type="text/css" media="screen">
-  if( zProjectDescr != 0 ){
-    @ <meta name="description" content="%s(zProjectDescr)">
+
+  /* Generate the header up through the main menu */
+  p = SbS_Create();
+  SbS_Store(p, "title", zTitle, 0);
+  SbS_Store(p, "baseurl", g.zBaseURL, 0);
+  if( g.zLogin ){
+    SbS_Store(p, "login", g.zLogin, 0);
   }
-  @ </head>
-  @ <body>
-  @ <div id="page-title">%s(zTitle)</div>
-  @ <div id="login-status">
-  if( g.zLogin==0 ){
-    @ not logged in
-    zLogInOut = "Login";
-  }else{
-    @ logged in as %h(g.zLogin)
-  }
-  @ </div>
+  SbS_Render(p, zHeader);
+  SbS_Destroy(p);
+
+  /* Generate the main menu and the submenu (if any) */
   @ <div id="main-menu">
   @ <a href="%s(g.zBaseURL)/home">Home</a>
   if( g.okRead ){
-    @ | <a href="%s(g.zBaseURL)/leaves">Leaves</a>
-    @ | <a href="%s(g.zBaseURL)/timeline">Timeline</a>
+    @ <a href="%s(g.zBaseURL)/leaves">Leaves</a>
+    @ <a href="%s(g.zBaseURL)/timeline">Timeline</a>
   }
   if( g.okRdWiki ){
-    @ | <a href="%s(g.zBaseURL)/wiki">Wiki</a>
+    @ <a href="%s(g.zBaseURL)/wiki">Wiki</a>
   }
 #if 0
-  @ | <font color="#888888">Search</font>
-  @ | <font color="#888888">Ticket</font>
-  @ | <font color="#888888">Reports</font>
+  @ <font color="#888888">Search</font>
+  @ <font color="#888888">Ticket</font>
+  @ <font color="#888888">Reports</font>
 #endif
   if( g.okSetup ){
-    @ | <a href="%s(g.zBaseURL)/setup">Setup</a>
+    @ <a href="%s(g.zBaseURL)/setup">Setup</a>
   }
   if( !g.noPswd ){
-    @ | <a href="%s(g.zBaseURL)/login">%s(zLogInOut)</a>
+    @ <a href="%s(g.zBaseURL)/login">%s(zLogInOut)</a>
   }
   @ </div>
   if( nSubmenu>0 ){
     int i;
     @ <div id="sub-menu">
     qsort(aSubmenu, nSubmenu, sizeof(aSubmenu[0]), submenuCompare);
     for(i=0; i<nSubmenu; i++){
       struct Submenu *p = &aSubmenu[i];
-      char *zTail = i<nSubmenu-1 ? " | " : "";
       if( p->zLink==0 ){
         @ <span class="label">%h(p->zLabel)</span>
-        @ <span class="tail">%s(zTail)</span>
       }else{
         @ <a class="label" href="%s(p->zLink)">%h(p->zLabel)</a>
-        @ <span class="tail">%s(zTail)</span>
       }
     }
     @ </div>
   }
   @ <div id="page">
@@ -142,10 +133,33 @@
   @ </div>
   @ <div id="style-footer">
   @ Fossil version %s(MANIFEST_VERSION) %s(MANIFEST_DATE)
   @ </div>
 }
+
+/*
+** The default page header.
+*/
+const char zDefaultHeader[] =
+@ <html>
+@ <head>
+@ <title>Edit CSS</title>
+@ <link rel="alternate" type="application/rss+xml" title="RSS Feed"
+@       href="[baseurl puts]/timeline.rss">
+@ <link rel="stylesheet" href="[baseurl puts]/style.css" type="text/css"
+@       media="screen">
+@ </head>
+@ <body>
+@ <div id="page-title">[title html]</div>
+@ <div id="login-status">
+@ [/login exists enable_output]
+@ logged in as [0 /login get html]
+@ [/login exists not enable_output]
+@ not logged in
+@ [1 enable_output]
+@ </div>
+;
 
 /*
 ** The default Cascading Style Sheet.
 **
 ** Selector order: tags, ids, classes, other

Modified src/subscript.c from [2945fb3a8d] to [7a4e64645a].

@@ -377,10 +377,31 @@
   v.u.verb.pArg = pArg;
   return sbs_store(&p->symTab, zVerb, -1, &v);
 }
 
 /*
+** Store a value in an interpreter variable.
+*/
+int SbS_Store(
+  struct Subscript *p,   /* Store into this interpreter */
+  const char *zName,     /* Name of the variable */
+  const char *zValue,    /* Value of the variable */
+  int makeCopy           /* If true, interpreter makes its own copy */
+){
+  SbSValue v;
+  v.flags = SBSVAL_STR;
+  v.u.str.size = strlen(zValue);
+  if( makeCopy ){
+    v.u.str.z = mprintf("%s", zValue);
+    v.flags |= SBSVAL_DYN;
+  }else{
+    v.u.str.z = zValue;
+  }
+  return sbs_store(&p->symTab, zName, -1, &v);
+}
+
+/*
 ** Push a string value onto the stack.
 **
 ** If the 4th parameter is 0, then the string is static.
 ** If the 4th parameter is non-zero then the string was obtained
 ** from malloc and Subscript will take responsibility for freeing
@@ -778,19 +799,19 @@
 
 #if 0
     {
       int i, nElem;
       const char *zElem;
-      printf("TOKEN(%d): [%.*s]\n", ttype, n, zScript);
       if( p->nStack>0 ){
         printf("STACK:");
         for(i=0; i<p->nStack; i++){
           zElem = SbS_StackValue(p, i, &nElem);
           printf(" [%.*s]", nElem, zElem);
         }
         printf("\n");
       }
+      printf("TOKEN(%d): [%.*s]\n", ttype, n, zScript);
     }
 #endif
 
     switch( ttype ){
       case SBSTT_WHITESPACE: {
@@ -864,14 +885,16 @@
 int SbS_Render(struct Subscript *p, const char *z){
   int i = 0;
   int rc = SBS_OK;
   while( z[i] ){
     if( z[i]=='[' ){
-      if( g.cgiPanic ){
-        cgi_append_content(z, i);
-      }else{
-        fwrite(z, 1, i, stdout);
+      if( enableOutput ){
+        if( g.cgiPanic ){
+          cgi_append_content(z, i);
+        }else{
+          fwrite(z, 1, i, stdout);
+        }
       }
       z += i+1;
       for(i=0; z[i] && z[i]!=']'; i++){}
       rc = SbS_Eval(p, z, i);
       if( rc!=SBS_OK ) break;
@@ -880,11 +903,11 @@
       i = 0;
     }else{
       i++;
     }
   }
-  if( i>0 ){
+  if( i>0 && enableOutput ){
     if( g.cgiPanic ){
       cgi_append_content(z, i);
     }else{
       fwrite(z, 1, i, stdout);
     }