]>
Commit | Line | Data |
---|---|---|
1 | #!/usr/bin/python | |
2 | ||
3 | from __future__ import division | |
4 | ||
5 | import datetime | |
6 | import textile | |
7 | ||
8 | from misc import Object | |
9 | ||
10 | class Wishlist(Object): | |
11 | def get(self, slug): | |
12 | wish = self.db.get("SELECT * FROM wishlist WHERE slug = %s", slug) | |
13 | ||
14 | if wish: | |
15 | return Wish(self, wish.id) | |
16 | ||
17 | def get_all_by_query(self, query, *args): | |
18 | wishes = [] | |
19 | ||
20 | for row in self.db.query(query, *args): | |
21 | wish = Wish(self, row.id, row) | |
22 | wishes.append(wish) | |
23 | ||
24 | return wishes | |
25 | ||
26 | def get_all_running(self): | |
27 | return self.get_all_by_query("SELECT * FROM wishlist \ | |
28 | WHERE (CASE \ | |
29 | WHEN date_end IS NULL THEN \ | |
30 | NOW() >= date_start AND goal >= donated \ | |
31 | ELSE \ | |
32 | NOW() BETWEEN date_start AND date_end \ | |
33 | END) AND status = 'running' \ | |
34 | ORDER BY prio ASC, date_end ASC") | |
35 | ||
36 | def get_all_finished(self, limit=5, offset=None): | |
37 | query = "SELECT * FROM wishlist \ | |
38 | WHERE (CASE \ | |
39 | WHEN date_end IS NULL THEN \ | |
40 | donated >= goal \ | |
41 | ELSE \ | |
42 | NOW() > date_end \ | |
43 | END) AND status IS NOT NULL \ | |
44 | ORDER BY date_end DESC" | |
45 | args = [] | |
46 | ||
47 | if limit: | |
48 | query += " LIMIT %s" | |
49 | args.append(limit) | |
50 | ||
51 | if offset: | |
52 | query += " OFFSET %s" | |
53 | args.append(offset) | |
54 | ||
55 | return self.get_all_by_query(query, *args) | |
56 | ||
57 | def get_hot_wishes(self, limit=3): | |
58 | query = "SELECT * FROM wishlist \ | |
59 | WHERE \ | |
60 | status = %s \ | |
61 | AND \ | |
62 | date_start <= NOW() \ | |
63 | AND \ | |
64 | (CASE WHEN date_end IS NOT NULL THEN \ | |
65 | NOW() BETWEEN date_start AND date_end \ | |
66 | ELSE \ | |
67 | TRUE \ | |
68 | END) \ | |
69 | AND \ | |
70 | (AGE(NOW(), date_start) <= INTERVAL '10 days' \ | |
71 | OR \ | |
72 | AGE(date_end, NOW()) <= INTERVAL '14 days' \ | |
73 | OR \ | |
74 | (donated / goal) >= 0.85 \ | |
75 | OR \ | |
76 | goal >= 3000 \ | |
77 | OR \ | |
78 | prio <= 5 \ | |
79 | ) \ | |
80 | ORDER BY prio ASC, date_end ASC LIMIT %s" | |
81 | ||
82 | return self.get_all_by_query(query, "running", limit) | |
83 | ||
84 | ||
85 | class Wish(object): | |
86 | def __init__(self, wishlist, id, data=None): | |
87 | self.wishlist = wishlist | |
88 | self.id = id | |
89 | ||
90 | self.__data = data | |
91 | ||
92 | def __repr__(self): | |
93 | return "<%s %s>" % (self.__class__.__name__, self.title) | |
94 | ||
95 | def __cmp__(self, other): | |
96 | return cmp(self.date_end, other.date_end) | |
97 | ||
98 | @property | |
99 | def db(self): | |
100 | return self.wishlist.db | |
101 | ||
102 | @property | |
103 | def data(self): | |
104 | if self.__data is None: | |
105 | self.__data = self.db.get("SELECT * FROM wishlist WHERE id = %s", self.id) | |
106 | assert self.__data | |
107 | ||
108 | return self.__data | |
109 | ||
110 | @property | |
111 | def title(self): | |
112 | return self.data.title | |
113 | ||
114 | @property | |
115 | def title_short(self): | |
116 | if len(self.title) > 30: | |
117 | return "%s..." % self.title[:30] | |
118 | ||
119 | return self.title | |
120 | ||
121 | @property | |
122 | def slug(self): | |
123 | return self.data.slug | |
124 | ||
125 | @property | |
126 | def tag(self): | |
127 | return self.data.tag | |
128 | ||
129 | @property | |
130 | def description(self): | |
131 | return textile.textile(self.data.description) | |
132 | ||
133 | @property | |
134 | def goal(self): | |
135 | return self.data.goal | |
136 | ||
137 | @property | |
138 | def donated(self): | |
139 | return self.data.donated | |
140 | ||
141 | @property | |
142 | def percentage(self): | |
143 | return (self.donated / self.goal) * 100 | |
144 | ||
145 | @property | |
146 | def percentage_bar(self): | |
147 | if self.percentage > 100: | |
148 | return 100 | |
149 | ||
150 | return self.percentage | |
151 | ||
152 | @property | |
153 | def progressbar_colour(self): | |
154 | if self.is_new(): | |
155 | return "bar-success" | |
156 | ||
157 | if self.percentage >= 90: | |
158 | return "bar-danger" | |
159 | ||
160 | return "bar-warning" | |
161 | ||
162 | @property | |
163 | def status(self): | |
164 | if self.data.status == "running" and not self.running: | |
165 | return "closed" | |
166 | ||
167 | return self.data.status | |
168 | ||
169 | @property | |
170 | def running(self): | |
171 | if self.date_end: | |
172 | if self.remaining_days and self.remaining_days < 0: | |
173 | return False | |
174 | ||
175 | else: | |
176 | if self.donated >= self.goal: | |
177 | return False | |
178 | ||
179 | return True | |
180 | ||
181 | @property | |
182 | def date_start(self): | |
183 | return self.data.date_start | |
184 | ||
185 | @property | |
186 | def date_end(self): | |
187 | return self.data.date_end | |
188 | ||
189 | @property | |
190 | def running_days(self): | |
191 | running = datetime.datetime.today() - self.date_start | |
192 | return running.days | |
193 | ||
194 | @property | |
195 | def remaining_days(self): | |
196 | if self.date_end: | |
197 | remaining = self.date_end - datetime.datetime.today() | |
198 | return remaining.days | |
199 | ||
200 | def is_new(self): | |
201 | return self.running_days < 10 | |
202 | ||
203 | def get_tweet(self, locale): | |
204 | _ = locale.translate | |
205 | ||
206 | t = [ | |
207 | _("Checkout this crowdfunding wish from #ipfire:"), | |
208 | "http://wishlist.ipfire.org/wish/%s" % self.slug, | |
209 | ] | |
210 | ||
211 | return " ".join(t) |