[Migration] fix issues with users from Django Auth
[mygpo.git] / mygpo / api / backend.py
blob1b1e8feecf30aa588b92131ab17055e94a7ebdf2
2 # This file is part of my.gpodder.org.
4 # my.gpodder.org is free software: you can redistribute it and/or modify it
5 # under the terms of the GNU Affero General Public License as published by
6 # the Free Software Foundation, either version 3 of the License, or (at your
7 # option) any later version.
9 # my.gpodder.org is distributed in the hope that it will be useful, but
10 # WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
11 # or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public
12 # License for more details.
14 # You should have received a copy of the GNU Affero General Public License
15 # along with my.gpodder.org. If not, see <http://www.gnu.org/licenses/>.
18 from collections import defaultdict
19 from functools import partial
20 import uuid
22 from mygpo.podcasts.models import Podcast
23 from mygpo.users.models import EpisodeUserState, Device, DeviceDoesNotExist, \
24 PodcastUserState
25 from mygpo.decorators import repeat_on_conflict
26 from mygpo.core.json import json
27 from mygpo.users.settings import STORE_UA
28 from mygpo.users.models import Client
29 from mygpo.db.couchdb import bulk_save_retry, get_userdata_database
30 from mygpo.db.couchdb.podcast_state import podcast_state_for_user_podcast
33 def get_device(user, uid, user_agent, undelete=True):
34 """
35 Loads or creates the device indicated by user, uid.
37 If the device has been deleted and undelete=True, it is undeleted.
38 """
40 store_ua = user.profile.get_wksetting(STORE_UA)
42 save = False
44 client, created = Client.objects.get_or_create(user=user, uid=uid,
45 defaults = {
46 'id': uuid.uuid1()
49 if client.deleted and undelete:
50 client.deleted = False
51 save = True
53 if store_ua and user_agent and client.user_agent != user_agent:
54 client.user_agent = user_agent
56 if save:
57 client.save()
59 return client
62 class BulkSubscribe(object):
63 """ Performs bulk subscribe/unsubscribe operations """
65 def __init__(self, user, device, podcasts = {}, actions=None):
66 self.user = user
67 self.device = device
68 self.podcasts = podcasts
69 self.actions = actions or []
71 self.operations = {
72 'subscribe': partial(self._subscribe, device=device),
73 'unsubscribe': partial(self._unsubscribe, device=device),
77 def execute(self):
78 """ Executes all added actions in bulk """
79 obj_funs = map(self._get_obj_fun, self.actions)
80 udb = get_userdata_database()
81 bulk_save_retry(obj_funs, udb)
83 # prepare for another run
84 self.actions = []
87 def add_action(self, url, op):
88 """ Adds a new (un)subscribe action
90 url is the podcast url to subscribe to / unsubscribe from
91 op is either "subscribe" or "unsubscribe" """
92 self.actions.append( (url, op) )
95 def _get_obj_fun(self, action):
96 url, op = action
98 podcast = self.podcasts.get(url,
99 Podcast.objects.get_or_create_for_url(url))
101 state = podcast_state_for_user_podcast(self.user, podcast)
103 fun = self.operations[op]
104 return (state, fun)
108 def _subscribe(self, state, device):
109 state.subscribe(device)
110 return state
112 def _unsubscribe(self, state, device):
113 state.unsubscribe(device)
114 return state