david / django-storages

Support for many storages (S3, MogileFS, etc) in Django.

Clone this repository (size: 177.1 KB): HTTPS / SSH
$ hg clone http://code.welldev.org/django-storages
commit 66: 41cc5987a7fb
parent 61: 7683dd9e9f35
branch: default
S3: Add encryption option, depends on ezPyCrypto lib from http://www.freenet.org.nz/ezPyCrypto/, thanks @erikcw
David Larlet / david
6 months ago

Changed (Δ1.2 KB):

raw changeset »

AUTHORS (1 lines added, 0 lines removed)

backends/s3.py (39 lines added, 1 lines removed)

Up to file-list AUTHORS:

@@ -14,6 +14,7 @@ By order of apparition, thanks:
14
14
    * Rich Leland (Mosso Cloud Files)
15
15
    * Jason Christa (patches)
16
16
    * Adam Nelson (patches)
17
    * Erik CW (S3 encryption)
17
18
18
19
Extra thanks to Marty for adding this in Django, 
19
20
you can buy his very interesting book (Pro Django).

Up to file-list backends/s3.py:

@@ -33,9 +33,18 @@ class S3Storage(Storage):
33
33
34
34
    def __init__(self, bucket=settings.AWS_STORAGE_BUCKET_NAME,
35
35
            access_key=None, secret_key=None, acl=DEFAULT_ACL,
36
            calling_format=settings.AWS_CALLING_FORMAT):
36
            calling_format=settings.AWS_CALLING_FORMAT, encrypt=False):
37
37
        self.bucket = bucket
38
38
        self.acl = acl
39
        self.encrypt = encrypt
40
        
41
        if encrypt:
42
            try:
43
                import ezPyCrypto
44
            except ImportError:
45
                raise ImproperlyConfigured, "Could not load ezPyCrypto.\
46
                \nSee http://www.freenet.org.nz/ezPyCrypto/ to install it."
47
            self.crypto_key = ezPyCrypto.key
39
48
40
49
        if not access_key and not secret_key:
41
50
            access_key, secret_key = self._get_access_keys()
@@ -70,6 +79,22 @@ class S3Storage(Storage):
70
79
        return os.path.normpath(name).replace('\\', '/')
71
80
72
81
    def _put_file(self, name, content):
82
        if self.encrypt:
83
        
84
            # Create a key object
85
            key = self.crypto_key()
86
        
87
            # Read in a public key
88
            fd = open(settings.CRYPTO_KEYS_PUBLIC, "rb")
89
            public_key = fd.read()
90
            fd.close()
91
        
92
            # import this public key
93
            key.importKey(public_key)
94
        
95
            # Now encrypt some text against this public key
96
            content = key.encString(content)
97
        
73
98
        content_type = mimetypes.guess_type(name)[0] or "application/x-octet-stream"
74
99
        self.headers.update({
75
100
            'x-amz-acl': self.acl, 
@@ -95,6 +120,19 @@ class S3Storage(Storage):
95
120
        if response.http_response.status not in (200, 206):
96
121
            raise IOError("S3StorageError: %s" % response.message)
97
122
        headers = response.http_response.msg
123
        
124
        if self.encrypt:
125
            # Read in a private key
126
            fd = open(settings.CRYPTO_KEYS_PRIVATE, "rb")
127
            private_key = fd.read()
128
            fd.close()
129
        
130
            # Create a key object, and auto-import private key
131
            key = self.crypto_key(private_key)
132
        
133
            # Decrypt this file
134
            response.object.data = key.decString(response.object.data)
135
        
98
136
        return response.object.data, headers.get('etag', None), headers.get('content-range', None)
99
137
        
100
138
    def _save(self, name, content):