def revokePermission(self, subscription, permission, permanent=DEFAULT_CONTEXT_PERMISSIONS_PERMANENCY): """ Revoke a permission on a context's user subscription. Revokes will persist over context default permission changes based on permanent parameter. Non permanent permission revoke will remove grants! """ criteria = {} new_permissions = [] # Add current permissions except revoked one new_permissions = [p for p in subscription['permissions'] if permission != p] if permanent: # Add permission to vetos if not present subscription.setdefault('_vetos', []) if permission not in subscription['_vetos']: subscription['_vetos'].append(permission) # Remove permission from grants if present subscription.setdefault('_grants', []) subscription['_grants'] = [granted for granted in subscription['_grants'] if granted != permission] # Get a dummy context from subscription to determine the fields to update ContextClass = getMaxModelByObjectType(subscription['objectType']) context_unique_field = ContextClass.unique.lstrip('_') temp_context = ContextClass.from_object( self.request, { context_unique_field: subscription[context_unique_field], 'objectType': subscription['objectType'] } ) context_storage_field = temp_context.user_subscription_storage subscription_unique_field = '{}.{}'.format(context_storage_field, context_unique_field) criteria.update({subscription_unique_field: subscription[context_unique_field]}) # update object that matches hash criteria.update({'_id': self['_id']}) # of collection entry with _id # overwrite permissions what = { '$set': { '{}.$.permissions'.format(context_storage_field): new_permissions, '{}.$._grants'.format(context_storage_field): subscription.get('_grants', []), '{}.$._vetos'.format(context_storage_field): subscription.get('_vetos', []) } } subscription['permissions'] = new_permissions fields_to_squash = ['published', 'owner', 'creator', 'tags', 'vetos', 'grants'] subscription = flatten(subscription, squash=fields_to_squash) self.mdb_collection.update(criteria, what) return subscription
def getSubscription(self, context): """ """ subscription_object_type = context.get('objectType', None) if subscription_object_type is None: return None ContextClass = getMaxModelByObjectType(subscription_object_type) temp_context = ContextClass.from_object(self.request, context) for subscription in self.get(temp_context.user_subscription_storage, []): if subscription.get(temp_context.unique.lstrip('_')) == str(temp_context[temp_context.unique]): return subscription
def process_file(self, request, activity_file): """ Process file and save it into the database """ base_path = request.registry.settings.get("file_repository") uploadURL = "" file_type = self["object"].get("objectType", "file").lower() # Look if the activity belongs to an specific context if self.get("contexts", False): # Look if we need to upload to an external URL context = self.get("contexts")[0] ContextClass = getMaxModelByObjectType(self.get("contexts")[0]["objectType"]) identifier = ( context[ContextClass.unique] if ContextClass.unique in context else context[ContextClass.unique.lstrip("_")] ) context = ContextClass.from_database(self.request, identifier) uploadURL = context.get("uploadURL", "") if uploadURL: headers = { "X-Oauth-Scope": request.headers.get("X-Oauth-Scope"), "X-Oauth-Username": request.headers.get("X-Oauth-Username"), "X-Oauth-Token": request.headers.get("X-Oauth-Token"), } # Todo: Make sure that the mimetype is correctly or even informed # Use magic or imghdr libraries for that files = {"image": (activity_file.filename, activity_file.file, activity_file.type)} res = requests.post(uploadURL, headers=headers, files=files) if res.status_code == 201: response = json.loads(res.text) self["object"]["fullURL"] = response.get("uploadURL", "") if file_type == "image": self["object"]["thumbURL"] = response.get("thumbURL", "") else: # We have a conversation or an activity with no related context # or a context with no community which we should save localy dirs = list(re.search("(\w{2})(\w{2})(\w{2})(\w{2})(\w{2})(\w{2})(\w{12})", str(self["_id"])).groups()) filename = dirs.pop() path = base_path + "/" + "/".join(dirs) if not os.path.exists(path): os.makedirs(path) r_file = open(path + "/" + filename, "w") r_file.write(activity_file.file.read()) r_file.close() full_endpoint_name = "image/full" if file_type == "image" else "file/download" self["object"]["fullURL"] = "/{}/{}/{}".format(self.resource_root, str(self["_id"]), full_endpoint_name) if file_type == "image": # Generate thumbnail activity_file.file.seek(0) image = Image.open(activity_file.file) thumb = rotate_image_by_EXIF(image) thumb.thumbnail((400, 400), Image.ANTIALIAS) thumb.save(path + "/" + filename + ".thumb", "JPEG") self["object"]["thumbURL"] = "/{}/{}/image/thumb".format(self.resource_root, str(self["_id"])) self["object"]["mimetype"] = activity_file.headers.getheader("content-type", "") # If there's a user-provided filename, preserve it if "filename" not in self["object"]: # Try to get filename from content disposition filename = re.search( r'filename="(.*?)"', activity_file.headers.getheader("content-disposition", "") ).groups() # Ignore empty filenames and "file" filenames (the latter coming from maxclient) if filename and filename != "file": self["object"]["filename"] = filename[0]