Skip to content


Subversion checkout URL

You can clone with
Download ZIP


Created a base class that doesn't return an HttpResponse object #21

wants to merge 3 commits into from

2 participants


I've created a new class called RawAjaxFileUploader which just performs the upload and returns the response dictionary to the client code. This allows extra server-side processing (such as saving the path the uploaded file in the database).

AjaxFileUploader is a subclass of this class which behaves exactly as it used to, returning the response serialised and wrapped in an HttpResponse object.


Hey Boosh,

I'm not against this pull request, but it does raise some questions for me. Can you toss some more info my way?

What's the use-case here, instead of overriding upload_complete in the backend?

I'm wary of providing too many ways to do the same thing - and though I see the logic in what you're doing, it's still tightly coupled to the JS - which expects a HttpResponse. I'm missing some useful case that you clearly have.

A couple other minor points:

  • Raw isn't my favorite name. Base would be better (though it duplicates the Base backend, and creates confusion), or something that indicates that it returns a dict. I'm open to suggestions - Raw just states that it's a stripped down version of something, and as a new user, I have no idea what.
  • Please add yourself to the AUTHORS file with your pull, attributed how you'd like!

Thanks for contributing!



This makes it more modular, by allowing the backend to be responsible purely for storage and the view to handle business logic, such as any pre- or post-processing that may be required.

In my case, I'm scaling images. So I've written a custom backend to scale the uploaded image to multiple different sets of dimensions, and I need to update my model to save the file name. I could put this in a backend, but I want to isolate this functionality. I'll use the same handler for this 'vanilla' upload and scaling, and later add a way of allowing users to crop the uploaded image (similar to how you select your face for your profile image on facebook).

The view does still need to return the JSON as an HttpResponse - this now allows me to do pre-/post-processing around the ajax uploader instead of having it as a single black box.

As for the name - I'm OK with Base, and I'm fine without being added to AUTHORS.

Thanks for your work!



I think I'd still put your image-scaling code in the upload_complete hook. That's what it's really there for (cropping images is actually one of the examples.)

However, in this case, I think that really comes down to coding style. You make a fair case, and I'm happy to take the merge. However, for consistency and attempting to have one clear way to do things, I'm not going to add it to the docs. If folks are looking to implement something in the same style, they'll be happy to find your abstracted backend there.

If you don't mind making the change to Base, I'll merge it in right away!



OK done - but I just updated the docs before I saw this ticket :-(


Doing a catch-up clean-out of issues on ajaxuploader. Looks like this one stalled, so I'm closing it. Please re-open if that's not right!

@skoczen skoczen closed this
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Commits on Mar 20, 2012
  1. Refactored AjaxFileUploader to provide a base class that doesn't retu…

    Al B authored
    …rn an HTTP response.
Commits on Mar 23, 2012
  1. Updated readme

    Al B authored
This page is out of date. Refresh to see the latest.
Showing with 38 additions and 2 deletions.
  1. +23 −0
  2. +15 −2 ajaxuploader/
@@ -88,6 +88,29 @@ url(r'start$', views.start, name="start"),
url(r'ajax-upload$', views.import_uploader, name="my_ajax_upload"),
+Or if you want to perform some pre-/post-processing on the ajax requests, you can use code similar to below:
+def ajax_upload(request):
+ # confirm that this user is permitted to upload files
+ # ....
+ # handle the upload using BaseAjaxFileUploader. We'll need to convert it
+ # to json later ourselves before returning it.
+ uploader = BaseAjaxFileUploader()
+ upload_response = uploader(request)
+ if upload_response['success'] == True:
+ # if the upload was successful, do something like save the path in a model
+ # The filename is in upload_response['filename']
+ # return the response as JSON
+ return HttpResponse(json.dumps(upload_response, cls=DjangoJSONEncoder))
Step 4. Set up your template.
This sample is included in the templates directory, but at the minimum, you need:
17 ajaxuploader/
@@ -5,7 +5,11 @@
from ajaxuploader.backends.local import LocalUploadBackend
-class AjaxFileUploader(object):
+class BaseAjaxFileUploader(object):
+ """
+ Performs an upload via AJAX then returns a dictionary which can be
+ processed further on the server side.
+ """
def __init__(self, backend=None, **kwargs):
if backend is None:
backend = LocalUploadBackend
@@ -59,4 +63,13 @@ def _ajax_upload(self, request):
if extra_context is not None:
- return HttpResponse(json.dumps(ret_json, cls=DjangoJSONEncoder))
+ return ret_json
+class AjaxFileUploader(BaseAjaxFileUploader):
+ """
+ Subclass of BaseAjaxFileUploader that serialises the response from the
+ upload and returns it as an HttpResponse.
+ """
+ def _ajax_upload(self, request):
+ ret_json = super(AjaxFileUploader, self)._ajax_upload(request)
+ return HttpResponse(json.dumps(ret_json, cls=DjangoJSONEncoder))
Something went wrong with that request. Please try again.