-
Notifications
You must be signed in to change notification settings - Fork 0
/
qiniufs.py
145 lines (124 loc) · 4.13 KB
/
qiniufs.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
# -*- coding: utf-8 -*-
from __future__ import absolute_import
import os
import datetime
import urlparse
import qiniu
import binascii
POLICY_FILED = [
'callbackUrl',
'callbackBody',
'returnUrl',
'returnBody',
'persistentOps',
'persistentNotifyUrl',
'persistentPipeline',
'deleteAfterDays',
]
class QiniuFS(object):
"""
Qiniu file storage
Attributes:
bucket: bucket name
access_key: access_key
secret_key: secret_key
prefix_url: domain
policy: policy for upload
"""
def __init__(self, bucket, access_key, secret_key, prefix_url, **kwargs):
self.bucket = bucket
self.access_key = access_key
self.secret_key = secret_key
self.prefix_url = prefix_url
self.policy = self.get_policy(**kwargs)
def __repr__(self):
return '<QiniuFS %s>' % self.bucket
def _make_auth(self):
return qiniu.Auth(self.access_key.encode('ascii'),
self.secret_key.encode('ascii'))
def token(self, key=None, expires=3600):
"""
token
"""
key = key or binascii.hexlify(os.urandom(16))
auth = self._make_auth()
token = auth.upload_token(self.bucket, key=key, expires=expires, policy=self.policy)
return token, key
def upload_data(self, data, mime_type=None, key=None):
"""
upload data stream
Args:
data: data stream
key: data stream name
mime_type: data stream mimeType
Returns:
True or False and {"hash": "<Hash string>", "key": "<Key string>"}
"""
token, key = self.token(key=key)
mime_type = mime_type or 'application/octet-stream'
ret, info = qiniu.put_data(token, key, data, mime_type=mime_type)
if ret is None:
raise UploadError(ret, info)
return True, ret
def upload_file(self, file, mime_type=None, key=None):
"""
upload file object
Args:
file: file object
key: file name
mime_type: file mimeType
Returns:
True or False and {"hash": "<Hash string>", "key": "<Key string>"}
"""
token, key = self.token(key=key)
mime_type = mime_type or 'application/octet-stream'
data_size = len(file.read())
ret, info = qiniu.put_stream(token, key, file, data_size, mime_type=mime_type,
progress_handler=lambda progress, total: progress)
if ret is None:
raise UploadError(ret, info)
return True, ret
def delete_file(self, key):
"""
delete the file form qiniu
"""
auth = self._make_auth()
bucket = qiniu.BucketManager(auth)
ret, info = bucket.delete(self.bucket, key)
return True, ret
def asyn_file_process(self, key, fops, pipeline=None):
"""
asynchronous file persistence
"""
auth = self._make_auth()
pfop = qiniu.PersistentFop(auth, self.bucket, pipeline=pipeline)
ops = []
ops.append(fops)
ret, info = pfop.execute(key, ops, force=True)
return True, ret
def get_url(self, key, scheme='http', style=None, is_private=False):
"""
url for the uploaded file
"""
if self.prefix_url:
url = urlparse.urljoin(self.prefix_url, '/' + key.rstrip('/'))
else:
url = ('http://%s.qiniudn.com/' % self.bucket) + key
if style:
url = url + '-' + style
if is_private:
expires = datetime.timedelta(hours=1)
expires = int(expires.total_seconds())
auth = self._make_auth()
url = auth.private_download_url(url, expires=expires)
return url
def get_policy(self, **kwargs):
"""
http://developer.qiniu.com/article/developer/security/put-policy.html.
"""
for key in kwargs:
if key not in POLICY_FILED:
raise UploadError("input the policy parameters error")
return kwargs
class UploadError(Exception):
pass