commit beef73b009b5e2df5bd4f62d45263267a6165a25
Author: David Sorber <david.sorber@gmail.com>
Date:   Sat Nov 7 14:14:07 2015 -0500

    Fixing the bookmark update redirect problem by adding an HTTP 307 redirect response to the UpdateBookmarkController. Also fixed a few other minor issues.

diff --git a/software/bookmark_library/bmklib/web/base_controller.py b/software/bookmark_library/bmklib/web/base_controller.py
index b8bc0e6..f1c5d13 100644
--- a/software/bookmark_library/bmklib/web/base_controller.py
+++ b/software/bookmark_library/bmklib/web/base_controller.py
@@ -2,7 +2,7 @@ import os
 
 from genshi.template import TemplateLoader
 
-BASE_PATH = '/home/dsorber/Documents/phalanx-repo/software/bookmark_library/'
+BASE_PATH = '/home/dsorber/Documents/repo/software/bookmark_library/'
 DB_PATH = os.path.join('/var/www', 'bookmarks.db')
 TEMPLATE_PATH = os.path.join(BASE_PATH, 'bmklib', 'web', 'templates')
 
@@ -36,7 +36,8 @@ class BaseHTMLController(object):
         
     def generate_response(self):
         """ This function generates the actual response which is made up of two
-        parts, the response headers and the response body.
+        parts, the response headers and the response body. It then returns the 
+        status along with the headers and body.
         """
         self.build_content()
         
@@ -47,8 +48,11 @@ class BaseHTMLController(object):
         # Set the appropriate response headers
         headers = [('Content-Type', 'text/html; charset=utf-8'),
                    ('Content-Length', str(len(body)))]
-                   
-        return headers, body
+
+        # Unless overridden status should be 200
+        status = '200 OK'
+
+        return status, headers, body
 
 
 class BaseTextController(object):
@@ -75,10 +79,11 @@ class BaseTextController(object):
         """
         self.build_content()
         
+        status = '200 OK'
         headers = [('Content-Type', 'text/plain'),
                    ('Content-Length', str(len(self.body)))]
                    
-        return headers, self.body
+        return status, headers, self.body
         
         
 class TestController(BaseTextController):
diff --git a/software/bookmark_library/bmklib/web/bmklib.wsgi b/software/bookmark_library/bmklib/web/bmklib.wsgi
index f8c314e..9139261 100644
--- a/software/bookmark_library/bmklib/web/bmklib.wsgi
+++ b/software/bookmark_library/bmklib/web/bmklib.wsgi
@@ -22,45 +22,45 @@ class Delegator(object):
         if not path or path == '/':
             # Main page
             controller = MainPageController(environ, self.conn)
-            response_headers, response_body = controller.generate_response()
+            status, headers, body = controller.generate_response()
 
         elif re.match('^/bookmark(s|(s/\d*))$', path):
             # All bookmarks page
             controller = AllBookmarksPageController(environ, self.conn)
-            response_headers, response_body = controller.generate_response()
+            status, headers, body = controller.generate_response()
         
         elif re.match('^/bookmar(k|(k/\d*))$', path):
             # Specific bookmark page
             controller = BookmarkPageController(environ, self.conn)
-            response_headers, response_body = controller.generate_response()
+            status, headers, body = controller.generate_response()
         
         elif re.match('^/update_bookmar(k|(k/))$', path):
             # Update bookmark
             controller = UpdateBookmarkController(environ, self.conn)
-            response_headers, response_body = controller.generate_response()
+            status, headers, body = controller.generate_response()
         
         elif re.match('^/tag(s|(s/))$', path):
             # All tags page
             controller = AllTagsPageController(environ, self.conn)
-            response_headers, response_body = controller.generate_response()
+            status, headers, body = controller.generate_response()
        
         elif re.match('^/tagge(d|(d/\d*))$', path):
             # All bookmarks tagged with tag page
             controller = TaggedPageController(environ, self.conn)
-            response_headers, response_body = controller.generate_response()
+            status, headers, body = controller.generate_response()
             
         else:
             # User supplied an invalid URL
-            response_body = 'Invalid URL "%s"' % environ['PATH_INFO']
-            response_headers = [('Content-Type', 'text/plain'),
-                                ('Content-Length', str(len(response_body)))]
-        # HTTP response code and message
-        status = '200 OK'
+            status = '200 OK'
+            body = 'Invalid URL "%s"' % environ['PATH_INFO']
+            headers = [('Content-Type', 'text/plain'),
+                                ('Content-Length', str(len(body)))]
+
         # Send the status and response headers to the server
-        start_response(status, response_headers)
+        start_response(status, headers)
         # Return the response body. (Notice it is wrapped in a list although it
         # could be any iterable.)
-        return [response_body]
+        return [body]
         
 
 # Set the callable object
diff --git a/software/bookmark_library/bmklib/web/controllers/bookmark.py b/software/bookmark_library/bmklib/web/controllers/bookmark.py
index edadbe6..a203736 100644
--- a/software/bookmark_library/bmklib/web/controllers/bookmark.py
+++ b/software/bookmark_library/bmklib/web/controllers/bookmark.py
@@ -18,6 +18,10 @@ class BookmarkPageController(BaseHTMLController):
         path = self.environ['PATH_INFO'][1:]
         path_parts = path.split('/')
         
+        # DEBUG remove me!
+        with open('/tmp/bmk_get_vars', 'w') as f:
+            f.write(repr(self.environ))
+        
         # Do some basic validation
         try:
             bmk_id = int(path_parts[1])
@@ -30,6 +34,13 @@ class BookmarkPageController(BaseHTMLController):
         else:
             self.content['invalid'] = False
             
+            # For now we are going to simplisticly assume that the bookmark
+            # page getting a POST request means it was redirected from the
+            # UpdateBookmarkController after a 307 temp redirect from a 
+            # successfuly update.
+            self.content['updated'] = (self.environ['REQUEST_METHOD'] == 'POST')
+            
+            
             # Build Bookmark object
             try:
                 bookmark = Bookmark(self.db_conn, id=bmk_id)
diff --git a/software/bookmark_library/bmklib/web/controllers/update_bookmark.py b/software/bookmark_library/bmklib/web/controllers/update_bookmark.py
index 0f1727c..e58377c 100644
--- a/software/bookmark_library/bmklib/web/controllers/update_bookmark.py
+++ b/software/bookmark_library/bmklib/web/controllers/update_bookmark.py
@@ -1,4 +1,5 @@
-from cgi import parse_qs, escape
+from urllib.parse import parse_qs
+from html import escape
 import os.path
 
 import sqlite3
@@ -31,9 +32,12 @@ class UpdateBookmarkController(BaseHTMLController):
             self.content['invalid'] = True
             self.content['error'] = 'Invalid post request (no ID specified)'
             return
-            
-        with open('/tmp/poopchute', 'w') as f:
-            f.write(str(post_vars))
+        
+        #~ # DEBUG - remove me
+        #~ with open('/tmp/bmk_post_vars', 'w') as f:
+            #~ f.write(str(post_vars))
+            #~ f.write('\n\n\n')
+            #~ f.write(repr(self.environ))
                 
         # Split the path so we can parse it below
         #~ path = self.environ['PATH_INFO'][1:]
@@ -51,12 +55,16 @@ class UpdateBookmarkController(BaseHTMLController):
         # Retrieve the specified Bookmark object and update its values
         try:
             bookmark = Bookmark(self.db_conn, id=bmk_id)
-            bookmark.url = escape(post_vars['url'][0])
-            bookmark.title = escape(post_vars['title'][0])
+            if 'url' in post_vars:
+                bookmark.url = escape(post_vars['url'][0])
+            if 'title' in post_vars:
+                bookmark.title = post_vars['title'][0]
             if 'description' in post_vars:
-                bookmark.description = escape(post_vars['description'][0])
+                bookmark.description = post_vars['description'][0]
             if 'deleted' in post_vars:
                 bookmark.deleted = bool(escape(post_vars['deleted'][0]))
+            if 'deleted' not in post_vars and bookmark.deleted:
+                bookmark.deleted = False
             bookmark.save()
             
             # Update category tags
@@ -88,3 +96,17 @@ class UpdateBookmarkController(BaseHTMLController):
             self.content['error'] = '{:d} is not a valid bookmark ID'.format(bmk_id)
         return
 
+    def generate_response(self):
+        """ This function generates the actual response which is made up of two
+        parts, the response headers and the response body.
+        """
+        self.build_content()
+        
+        # Set the appropriate response headers, in this case we are redirecting 
+        # back to the refering page
+        headers = [('Location', self.environ['HTTP_REFERER'])]
+
+        # Unless overridden status should be 200
+        status = '307 Temporary Redirect'
+
+        return status, headers, '1'
diff --git a/software/bookmark_library/bmklib/web/htdocs/css/bmk_form.css b/software/bookmark_library/bmklib/web/htdocs/css/bmk_form.css
index 18ca01c..3c883d3 100644
--- a/software/bookmark_library/bmklib/web/htdocs/css/bmk_form.css
+++ b/software/bookmark_library/bmklib/web/htdocs/css/bmk_form.css
@@ -88,3 +88,9 @@
         font-weight: bold;
         color: #666;
     }
+    
+    div#update {
+        background-color: #A1D490;
+        padding: 0.4em;
+        border: solid 2px #003399;
+    }
diff --git a/software/bookmark_library/bmklib/web/templates/bookmark.html b/software/bookmark_library/bmklib/web/templates/bookmark.html
index 47d73a5..8594add 100644
--- a/software/bookmark_library/bmklib/web/templates/bookmark.html
+++ b/software/bookmark_library/bmklib/web/templates/bookmark.html
@@ -24,10 +24,15 @@
         <input type="hidden" name="id" value="${bookmark.id}" />
         <div class="container">
             <p>Bookmark ID: ${bookmark.id}</p>
+            <py:choose test="updated">
+                <py:when test="True">
+                    <div id="update">Changes saved.</div>
+                </py:when>
+            </py:choose>
             <div class="not_first">
                 <div class="left">
                     <span class="form_label">Deleted:</span>
-                    <input class="checkbox" type="checkbox" name="deleted" />
+                    <input class="checkbox" type="checkbox" name="deleted" checked="${bookmark.deleted and 'checked' or ''}" />
                 </div>
                 <div class="right">
                     <span class="form_label">Date added:</span>
