merge with changeset 352:7bc8d8bfe443
authorProduction Moz <dev@sopinspace.com>
Tue, 31 May 2011 18:26:38 +0200
changeset 354 4c7feb67d4a0
parent 353 c5de47e27dbd (diff)
parent 343 7bc8d8bfe443 (current diff)
child 355 c926868cf7e6
merge with changeset 352:7bc8d8bfe443
--- a/src/cm/activity.py	Fri Jan 28 11:09:34 2011 +0100
+++ b/src/cm/activity.py	Tue May 31 18:26:38 2011 +0200
@@ -49,6 +49,9 @@
 
 VISIT_DURATION = timedelta(seconds=30 * 60) # 30 minutes
 
+from cm.utils.cache import memoize, dj_memoize
+
+@dj_memoize
 def get_activity(text='all', user='all', reference_date=None, nb_slots=31, slot_timedelta=timedelta(days=1), action="all", kind=''):
     """
     text : text: specific text
--- a/src/cm/converters/latex_header.txt	Fri Jan 28 11:09:34 2011 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,9 +0,0 @@
-\documentclass{article}
-\usepackage{amsmath}
-\usepackage[utf8x]{inputenc}
-\usepackage{listings}
-\usepackage{eurofont}
-\lstnewenvironment{code}{\lstset{language=Haskell,basicstyle=\small\ttfamily}}{}
-\setlength{\parindent}{0pt}
-\setlength{\parskip}{6pt plus 2pt minus 1pt}
-\usepackage[T1]{fontenc}
\ No newline at end of file
--- a/src/cm/converters/pandoc_converters.py	Fri Jan 28 11:09:34 2011 +0100
+++ b/src/cm/converters/pandoc_converters.py	Tue May 31 18:26:38 2011 +0200
@@ -11,10 +11,12 @@
 import StringIO
 import tidy
 from cm.utils.string_utils import to_unicode
+from xml.dom.minidom import parseString
+import re
 
 PANDOC_BIN = "pandoc"
-PANDOC_OPTIONS = " --sanitize-html "
-PANDOC_OPTIONS_RAW = " -R "
+PANDOC_OPTIONS = " --sanitize-html --email-obfuscation=none  "
+PANDOC_OPTIONS_RAW = " -R --email-obfuscation=none "
 
 MARKDOWN2PDF_BIN = "markdown2pdf"
 
@@ -85,6 +87,8 @@
                         add_xml_decl=0, 
                         indent=0, 
                         tidy_mark=0,
+                        logical_emphasis=1,
+                        wrap=0,
                         input_encoding='utf8',
                         output_encoding='utf8',
                         )
@@ -95,20 +99,10 @@
     return str(tidyied_content).decode('utf8')
 
 
-def get_filetemp(mode="r"):
-    (fd, fname) = mkstemp()
+def get_filetemp(mode="r", suffix=''):
+    (fd, fname) = mkstemp(suffix)
     return (os.fdopen(fd, mode), fname)
 
-# build absolute address for latex header file
-_tmp_ = __file__.split(os.path.sep)[:-1]
-_tmp_.append('latex_header.txt')
-_tmp_.insert(0, os.path.sep)
-
-LATEX_HEADER_PATH = os.path.join(*_tmp_)
-
-if not os.path.isfile(LATEX_HEADER_PATH):
-    raise Exception('LATEX_HEADER_PATH is not a file!')
-
 @dj_memoize
 def pandoc_markdown2pdf(content=None, file_name=None):
     """
@@ -119,17 +113,16 @@
     content = content_or_file_name(content, file_name)
         
     # write file to disk
-    temp_file, input_temp_name = get_filetemp('w')
-    fp_error, error_temp_name = get_filetemp('w')
+    temp_file, input_temp_name = get_filetemp('w', 'input')
+    fp_error, error_temp_name = get_filetemp('w', 'err')
     
     temp_file.write(content.encode(_PANDOC_ENCODING))
     temp_file.close()
     
-    # custom latex header
-    cust_head_tex = " --custom-header=%s " %LATEX_HEADER_PATH
+    cust_tex = " --xetex "
     
     # use markdown2pdf
-    retcode = call(MARKDOWN2PDF_BIN + cust_head_tex + ' ' + input_temp_name, shell=True, stderr=fp_error)
+    retcode = call(MARKDOWN2PDF_BIN + cust_tex + ' ' + input_temp_name, shell=True, stderr=fp_error)
     fp_error.close()
     
     fp_error = file(error_temp_name)
@@ -179,11 +172,11 @@
         raise Exception('Content is not in unicode format!')
 
     # temp file
-    input_file, input_temp_name = get_filetemp('w')
-    output_temp_fp, output_temp_name = get_filetemp()
+    input_file, input_temp_name = get_filetemp('w', 'input')
+    output_temp_fp, output_temp_name = get_filetemp('r', 'output')
     output_temp_fp.close()
     
-    error_temp_fp, error_temp_name = get_filetemp('w')
+    error_temp_fp, error_temp_name = get_filetemp('w', 'err')
     error_temp_fp.close()
     
     input_file.write(content.encode(_PANDOC_ENCODING))
@@ -194,6 +187,26 @@
     if raw:
         p_options = PANDOC_OPTIONS_RAW
                 
+    # do not use pandoc to convert from html to html
+    if from_format==to_format=='html':
+      # get body content
+      stdoutdata = (content.encode('utf8'))
+      # if for some reason, tidy has not guess the doctype, make xml.dom.minidom happy with HTML entities (&nbsp;)
+      stdoutdata = re.sub(r"&nbsp;", '\xc2\xa0', stdoutdata)
+      dom = parseString(stdoutdata)
+      body = dom.getElementsByTagName("body")[0].toxml()
+      stdoutdata = body[body.find('>')+1:body.rfind('</')]
+      # strip leading spaces
+      stdoutdata = re.sub(r"^\s+", '', stdoutdata)
+      # add new line before closing bracket
+      stdoutdata = re.sub(r"(\/?)>", r"\n\1>", stdoutdata)
+      # do not split closing tag with following opening tag
+      stdoutdata = re.sub(r">\n<", r"><", stdoutdata)
+      # nest headers tags 
+      #stdoutdata = re.sub(r'<h(\d) id="([^"]+)"\n>', r'<div id="\2"><h\1>', stdoutdata)
+      #stdoutdata = re.sub(r'<\/h(\d)\n>', r'</h\1></div>', stdoutdata)
+      return stdoutdata
+
     cmd_args = ' %s -o %s ' %(p_options,output_temp_name) 
     if full:
         cmd_args += ' -s '
--- a/src/cm/media/js/lib/yui/yui3.0.0/build/cssreset/reset-min.css	Fri Jan 28 11:09:34 2011 +0100
+++ b/src/cm/media/js/lib/yui/yui3.0.0/build/cssreset/reset-min.css	Tue May 31 18:26:38 2011 +0200
@@ -2,7 +2,7 @@
 Copyright (c) 2009, Yahoo! Inc. All rights reserved.
 Code licensed under the BSD License:
 http://developer.yahoo.net/yui/license.txt
-version: 3.0.0
-build: 1549
+version: 3.0.0b1
+build: 1163
 */
-html{color:#000;background:#FFF;}body,div,dl,dt,dd,ul,ol,li,h1,h2,h3,h4,h5,h6,pre,code,form,fieldset,legend,input,textarea,p,blockquote,th,td{margin:0;padding:0;}table{border-collapse:collapse;border-spacing:0;}fieldset,img{border:0;}address,caption,cite,code,dfn,em,strong,th,var{font-style:normal;font-weight:normal;}li{list-style:none;}caption,th{text-align:left;}h1,h2,h3,h4,h5,h6{font-size:100%;font-weight:normal;}q:before,q:after{content:'';}abbr,acronym{border:0;font-variant:normal;}sup{vertical-align:text-top;}sub{vertical-align:text-bottom;}input,textarea,select{font-family:inherit;font-size:inherit;font-weight:inherit;}input,textarea,select{*font-size:100%;}legend{color:#000;}
\ No newline at end of file
+fieldset,img{border:0;}
--- a/src/cm/media/js/lib/yui/yui_3.0.0b1/build/cssreset/reset-min.css	Fri Jan 28 11:09:34 2011 +0100
+++ b/src/cm/media/js/lib/yui/yui_3.0.0b1/build/cssreset/reset-min.css	Tue May 31 18:26:38 2011 +0200
@@ -5,4 +5,4 @@
 version: 3.0.0b1
 build: 1163
 */
-html{color:#000;background:#FFF;}body,div,dl,dt,dd,ul,ol,li,h1,h2,h3,h4,h5,h6,pre,code,form,fieldset,legend,input,textarea,p,blockquote,th,td{margin:0;padding:0;}table{border-collapse:collapse;border-spacing:0;}fieldset,img{border:0;}address,caption,cite,code,dfn,em,strong,th,var{font-style:normal;font-weight:normal;}li{list-style:none;}caption,th{text-align:left;}h1,h2,h3,h4,h5,h6{font-size:100%;font-weight:normal;}q:before,q:after{content:'';}abbr,acronym{border:0;font-variant:normal;}sup{vertical-align:text-top;}sub{vertical-align:text-bottom;}input,textarea,select{font-family:inherit;font-size:inherit;font-weight:inherit;}input,textarea,select{*font-size:100%;}legend{color:#000;}
\ No newline at end of file
+html{color:#000;background:#FFF;}body,div,dl,dt,dd,ul,ol,li,h1,h2,h3,h4,h5,h6,pre,code,form,fieldset,legend,input,textarea,p,blockquote,th,td{margin:0;padding:0;}table{border-collapse:collapse;border-spacing:0;}fieldset,img{border:0;}address,caption,cite,code,dfn,em,var,strong,th{font-style:normal;font-weight:normal;}li{list-style:none;}caption,th{text-align:left;}h1,h2,h3,h4,h5,h6{font-size:100%;font-weight:normal;}q:before,q:after{content:'';}abbr,acronym{border:0;font-variant:normal;}sup{vertical-align:text-top;}sub{vertical-align:text-bottom;}input,textarea,select{font-family:inherit;font-size:inherit;font-weight:inherit;}input,textarea,select{*font-size:100%;}legend{color:#000;}
--- a/src/cm/models.py	Fri Jan 28 11:09:34 2011 +0100
+++ b/src/cm/models.py	Tue May 31 18:26:38 2011 +0200
@@ -841,3 +841,5 @@
 
 # we fill username with email so we need a bigger value 
 User._meta.get_field('username').max_length = 75
+
+import monkey_patches
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/cm/monkey_patches.py	Tue May 31 18:26:38 2011 +0200
@@ -0,0 +1,65 @@
+from south.management.commands.migrate import  Command
+from south.db import DEFAULT_DB_ALIAS
+from south import migration
+import sys
+
+### RBA+GIB: prevent uno custom __import__ from messing with south import machinery (to discover south enabled dj apps)
+def new_handle(self, app=None, target=None, skip=False, merge=False, backwards=False, fake=False, db_dry_run=False, show_list=False, database=DEFAULT_DB_ALIAS, delete_ghosts=False, ignore_ghosts=False, **options):
+
+    # NOTE: THIS IS DUPLICATED FROM django.core.management.commands.syncdb
+    # This code imports any module named 'management' in INSTALLED_APPS.
+    # The 'management' module is the preferred way of listening to post_syncdb
+    # signals, and since we're sending those out with create_table migrations,
+    # we need apps to behave correctly.
+    from django.conf import settings
+    for app_name in settings.INSTALLED_APPS:
+        try:
+            __import__(app_name + '.management', {}, {}, [''])
+        except ImportError, exc:
+            msg = exc.args[0]
+            if (not msg.startswith('No module named') and not msg.endswith(' is unknown') ) or 'management' not in msg:
+                raise
+
+    # END DJANGO DUPE CODE
+        
+    # if all_apps flag is set, shift app over to target
+    if options.get('all_apps', False):
+        target = app
+        app = None
+
+    # Migrate each app
+    if app:
+        try:
+            apps = [Migrations(app)]
+        except NoMigrations:
+            print "The app '%s' does not appear to use migrations." % app
+            print "./manage.py migrate " + self.args
+            return
+    else:
+        apps = list(migration.all_migrations())
+        
+    # Do we need to show the list of migrations?
+    if show_list and apps:
+        list_migrations(apps, database)
+        
+    if not show_list:
+            
+        for app in apps:
+            result = migration.migrate_app(
+                app,
+                target_name = target,
+                fake = fake,
+                db_dry_run = db_dry_run,
+                verbosity = int(options.get('verbosity', 0)),
+                interactive = options.get('interactive', True),
+                load_initial_data = not options.get('no_initial_data', False),
+                merge = merge,
+                skip = skip,
+                database = database,
+                delete_ghosts = delete_ghosts,
+                ignore_ghosts = ignore_ghosts,
+            )
+            if result is False:
+                sys.exit(1) # Migration failed, so the command fails.
+
+Command.handle = new_handle
--- a/src/cm/templates/site/tracking.html	Fri Jan 28 11:09:34 2011 +0100
+++ b/src/cm/templates/site/tracking.html	Tue May 31 18:26:38 2011 +0200
@@ -1,1 +1,16 @@
-{% autoescape off %}{{ TRACKING_HTML }}{% endautoescape %}
\ No newline at end of file
+{% autoescape off %}{{ TRACKING_HTML }}{% endautoescape %}
+
+<!-- Piwik -->
+<script type="text/javascript">
+var pkBaseURL = (("https:" == document.location.protocol) ? "https://stats.co-ment.com/" : "http://piwik.sopinspace.net/");
+document.write(unescape("%3Cscript src='" + pkBaseURL + "piwik.js' type='text/javascript'%3E%3C/script%3E"));
+</script><script type="text/javascript">
+try {
+var piwikTracker = Piwik.getTracker(pkBaseURL + "piwik.php", 17);
+piwikTracker.trackPageView();
+piwikTracker.enableLinkTracking();
+} catch( err ) {}
+</script><noscript><p><img src="https://stats.co-ment.com/piwik.php?idsite=17" style="border:0" alt=""/></p></noscript>
+<!-- End Piwik Tag -->
+
+
--- a/src/cm/utils/cache.py	Fri Jan 28 11:09:34 2011 +0100
+++ b/src/cm/utils/cache.py	Tue May 31 18:26:38 2011 +0200
@@ -1,10 +1,11 @@
 from django.core.cache import cache
 from hashlib import sha1
+from django.conf import settings
 
 # adapted [to django] from http://code.activestate.com/recipes/325205/
 def dj_memoize(f):
     def g(*args, **kwargs):
-        key = sha1( str((f.__name__, f, tuple(args), frozenset(kwargs.items())) )).hexdigest()
+        key = sha1( str((settings.SITE_URL, f.__name__, f, tuple(args), frozenset(kwargs.items())) )).hexdigest()
         val = cache.get(key)
         if not val:
             val = f(*args, **kwargs)
--- a/src/cm/views/texts.py	Fri Jan 28 11:09:34 2011 +0100
+++ b/src/cm/views/texts.py	Tue May 31 18:26:38 2011 +0200
@@ -562,7 +562,7 @@
     """
     Return the inner of the html table for text1 vs text2 diff
     """
-    gen = unified_diff(text1.split('\n'), text2.split('\n'), n=3)
+    gen = unified_diff(text1.replace('\r\n','\n').split('\n'), text2.replace('\r\n','\n').split('\n'), n=3)
     index = 0
     res = ['<table class="diff"><col class="diff-marker"/><col class="diff-content"/><col class="diff-separator"/<col class="diff-marker"/><col class="diff-content"/><tbody>']
     res.append('<tr><td></td><td class="diff-title">%s</td><td></td><td></td><td class="diff-title">%s</td></tr>' %(title1, title2))