Permalink
Browse files

Merge pull request #3 from dstegelman/feature/celery

Feature/celery
  • Loading branch information...
2 parents ed5567c + 26567cb commit eaae14a6bc82b8d3b4116f41d30bf527384d7016 Derek Stegelman committed Feb 4, 2012
Binary file not shown.
@@ -1,6 +1,6 @@
Metadata-Version: 1.0
Name: django-mail-queue
-Version: 1.0.1
+Version: 1.1.0
Summary: Simple Mail Queuing for Django
Home-page: http://github.com/dstegelman/django-mail-queue
Author: Derek Stegelman
@@ -7,5 +7,9 @@ django_mail_queue.egg-info/top_level.txt
mailqueue/__init__.py
mailqueue/admin.py
mailqueue/models.py
+mailqueue/tasks.py
mailqueue/urls.py
-mailqueue/views.py
+mailqueue/views.py
+mailqueue/migrations/0001_initial.py
+mailqueue/migrations/0002_auto__add_field_mailermessage_html_content.py
+mailqueue/migrations/__init__.py
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -1,4 +1,4 @@
# Sphinx build info version 1
# This file hashes the configuration used when building these files. When it is not found, a full rebuild will be done.
-config: b483f19b32e73764bffde6a04b8359ec
+config: 710ece22081f69a21e92d7e03c04bed5
tags: fbb0d17656682115ca4d033fb2f83ba1
@@ -9,15 +9,15 @@ Django Mail Queue requires::
south
django 1.3 or greater
-
+ celery
Installation
------------
Using ``pip``::
- pip install git+git://github.com/dstegelman/django-mail-queue.git
+ pip install django-mail-queue
Go to https://github.com/dstegelman/django-mail-queue if you need to download a package or clone the repo.
@@ -39,9 +39,15 @@ Add URL-patterns::
(r'^mail-queue/', include('mailqueue.urls')),
)
-Cron Job
---------
+
+Cron Job (optional)
+-------------------
Setup a cron job to hit the root of mail-queue. So the example above would hit /mail-queue. This runs the mail queue which grabs emails and sends them. To decrease load, it only tries
to send 30 emails at a time.
+
+Celery
+------
+
+Instead of using the cron job the celery task worker will attempt to send email email when it's saved. The cron job will clean up any emails that get lost.
@@ -14,6 +14,7 @@ Create a new MailerMesage() object::
new_message.to_address = "someone@example.com"
new_message.from_address = "hello@example.com"
new_message.content = "Mail content"
+ new_message.html_content = "<h1>Mail Content</h1>"
new_message.app = "Name of your App that is sending the email."
new_message.save()
@@ -79,6 +79,14 @@ div.sphinxsidebar input {
font-size: 1em;
}
+div.sphinxsidebar input[type="text"] {
+ width: 170px;
+}
+
+div.sphinxsidebar input[type="submit"] {
+ width: 30px;
+}
+
img {
border: 0;
}
@@ -236,7 +244,6 @@ img.align-center, .figure.align-center, object.align-center {
}
.align-center {
- clear: both;
text-align: center;
}
@@ -440,6 +447,11 @@ dl.glossary dt {
font-style: oblique;
}
+abbr, acronym {
+ border-bottom: dotted 1px;
+ cursor: help;
+}
+
/* -- code displays --------------------------------------------------------- */
pre {
@@ -525,4 +537,4 @@ span.eqno {
#top-link {
display: none;
}
-}
+}
@@ -2,7 +2,7 @@
* doctools.js
* ~~~~~~~~~~~
*
- * Sphinx JavaScript utilties for all documentation.
+ * Sphinx JavaScript utilities for all documentation.
*
* :copyright: Copyright 2007-2011 by the Sphinx team, see AUTHORS.
* :license: BSD, see LICENSE for details.
@@ -185,9 +185,9 @@ var Documentation = {
body.highlightText(this.toLowerCase(), 'highlighted');
});
}, 10);
- $('<li class="highlight-link"><a href="javascript:Documentation.' +
- 'hideSearchWords()">' + _('Hide Search Matches') + '</a></li>')
- .appendTo($('.sidebar .this-page-menu'));
+ $('<p class="highlight-link"><a href="javascript:Documentation.' +
+ 'hideSearchWords()">' + _('Hide Search Matches') + '</a></p>')
+ .appendTo($('#searchbox'));
}
},
@@ -213,7 +213,7 @@ var Documentation = {
* helper function to hide the search marks again
*/
hideSearchWords : function() {
- $('.sidebar .this-page-menu li.highlight-link').fadeOut(300);
+ $('#searchbox .highlight-link').fadeOut(300);
$('span.highlighted').removeClass('highlighted');
},
@@ -1,6 +1,6 @@
/*
- * searchtools.js
- * ~~~~~~~~~~~~~~
+ * searchtools.js_t
+ * ~~~~~~~~~~~~~~~~
*
* Sphinx JavaScript utilties for the full-text search.
*
@@ -36,10 +36,11 @@ jQuery.makeSearchSummary = function(text, keywords, hlwords) {
return rv;
}
+
/**
* Porter Stemmer
*/
-var PorterStemmer = function() {
+var Stemmer = function() {
var step2list = {
ational: 'ate',
@@ -300,20 +301,20 @@ var Search = {
},
query : function(query) {
- var stopwords = ['and', 'then', 'into', 'it', 'as', 'are', 'in',
- 'if', 'for', 'no', 'there', 'their', 'was', 'is',
- 'be', 'to', 'that', 'but', 'they', 'not', 'such',
- 'with', 'by', 'a', 'on', 'these', 'of', 'will',
- 'this', 'near', 'the', 'or', 'at'];
-
- // stem the searchterms and add them to the correct list
- var stemmer = new PorterStemmer();
+ var stopwords = ["and","then","into","it","as","are","in","if","for","no","there","their","was","is","be","to","that","but","they","not","such","with","by","a","on","these","of","will","this","near","the","or","at"];
+
+ // Stem the searchterms and add them to the correct list
+ var stemmer = new Stemmer();
var searchterms = [];
var excluded = [];
var hlterms = [];
var tmp = query.split(/\s+/);
- var object = (tmp.length == 1) ? tmp[0].toLowerCase() : null;
+ var objectterms = [];
for (var i = 0; i < tmp.length; i++) {
+ if (tmp[i] != "") {
+ objectterms.push(tmp[i].toLowerCase());
+ }
+
if ($u.indexOf(stopwords, tmp[i]) != -1 || tmp[i].match(/^\d+$/) ||
tmp[i] == "") {
// skip this "word"
@@ -344,9 +345,6 @@ var Search = {
var filenames = this._index.filenames;
var titles = this._index.titles;
var terms = this._index.terms;
- var objects = this._index.objects;
- var objtypes = this._index.objtypes;
- var objnames = this._index.objnames;
var fileMap = {};
var files = null;
// different result priorities
@@ -357,40 +355,19 @@ var Search = {
$('#search-progress').empty();
// lookup as object
- if (object != null) {
- for (var prefix in objects) {
- for (var name in objects[prefix]) {
- var fullname = (prefix ? prefix + '.' : '') + name;
- if (fullname.toLowerCase().indexOf(object) > -1) {
- match = objects[prefix][name];
- descr = objnames[match[1]] + _(', in ') + titles[match[0]];
- // XXX the generated anchors are not generally correct
- // XXX there may be custom prefixes
- result = [filenames[match[0]], fullname, '#'+fullname, descr];
- switch (match[2]) {
- case 1: objectResults.push(result); break;
- case 0: importantResults.push(result); break;
- case 2: unimportantResults.push(result); break;
- }
- }
- }
- }
+ for (var i = 0; i < objectterms.length; i++) {
+ var others = [].concat(objectterms.slice(0,i),
+ objectterms.slice(i+1, objectterms.length))
+ var results = this.performObjectSearch(objectterms[i], others);
+ // Assume first word is most likely to be the object,
+ // other words more likely to be in description.
+ // Therefore put matches for earlier words first.
+ // (Results are eventually used in reverse order).
+ objectResults = results[0].concat(objectResults);
+ importantResults = results[1].concat(importantResults);
+ unimportantResults = results[2].concat(unimportantResults);
}
- // sort results descending
- objectResults.sort(function(a, b) {
- return (a[1] > b[1]) ? -1 : ((a[1] < b[1]) ? 1 : 0);
- });
-
- importantResults.sort(function(a, b) {
- return (a[1] > b[1]) ? -1 : ((a[1] < b[1]) ? 1 : 0);
- });
-
- unimportantResults.sort(function(a, b) {
- return (a[1] > b[1]) ? -1 : ((a[1] < b[1]) ? 1 : 0);
- });
-
-
// perform the search on the required terms
for (var i = 0; i < searchterms.length; i++) {
var word = searchterms[i];
@@ -489,7 +466,7 @@ var Search = {
listItem.slideDown(5, function() {
displayNextItem();
});
- });
+ }, "text");
} else {
// no source available, just display title
Search.output.append(listItem);
@@ -510,9 +487,74 @@ var Search = {
}
}
displayNextItem();
+ },
+
+ performObjectSearch : function(object, otherterms) {
+ var filenames = this._index.filenames;
+ var objects = this._index.objects;
+ var objnames = this._index.objnames;
+ var titles = this._index.titles;
+
+ var importantResults = [];
+ var objectResults = [];
+ var unimportantResults = [];
+
+ for (var prefix in objects) {
+ for (var name in objects[prefix]) {
+ var fullname = (prefix ? prefix + '.' : '') + name;
+ if (fullname.toLowerCase().indexOf(object) > -1) {
+ var match = objects[prefix][name];
+ var objname = objnames[match[1]][2];
+ var title = titles[match[0]];
+ // If more than one term searched for, we require other words to be
+ // found in the name/title/description
+ if (otherterms.length > 0) {
+ var haystack = (prefix + ' ' + name + ' ' +
+ objname + ' ' + title).toLowerCase();
+ var allfound = true;
+ for (var i = 0; i < otherterms.length; i++) {
+ if (haystack.indexOf(otherterms[i]) == -1) {
+ allfound = false;
+ break;
+ }
+ }
+ if (!allfound) {
+ continue;
+ }
+ }
+ var descr = objname + _(', in ') + title;
+ anchor = match[3];
+ if (anchor == '')
+ anchor = fullname;
+ else if (anchor == '-')
+ anchor = objnames[match[1]][1] + '-' + fullname;
+ result = [filenames[match[0]], fullname, '#'+anchor, descr];
+ switch (match[2]) {
+ case 1: objectResults.push(result); break;
+ case 0: importantResults.push(result); break;
+ case 2: unimportantResults.push(result); break;
+ }
+ }
+ }
+ }
+
+ // sort results descending
+ objectResults.sort(function(a, b) {
+ return (a[1] > b[1]) ? -1 : ((a[1] < b[1]) ? 1 : 0);
+ });
+
+ importantResults.sort(function(a, b) {
+ return (a[1] > b[1]) ? -1 : ((a[1] < b[1]) ? 1 : 0);
+ });
+
+ unimportantResults.sort(function(a, b) {
+ return (a[1] > b[1]) ? -1 : ((a[1] < b[1]) ? 1 : 0);
+ });
+
+ return [importantResults, objectResults, unimportantResults]
}
}
$(document).ready(function() {
Search.init();
-});
+});

Some generated files are not rendered by default. Learn more.

Oops, something went wrong.
Oops, something went wrong.

0 comments on commit eaae14a

Please sign in to comment.