Exemple #1
0
	def post(self):
		ret = { 'status': 'error', 'message': '', 'task_id': '', }
		user = self.get_mdb_user()
		if not user:
			ret['message'] = "<strong>FATAL</strong> (FileSaveHandler): no user ?!"
		else:
			from main.tasks import save_node
			try:
				node = get_node_by_path(user, self.get_argument('db_path'))
				yield gen.Task(save_node,
					node.id, self.get_argument('content'))
			except Exception, e:
				ret['message'] = "<strong>FATAL</strong>(save.save_node): %s" % e
			else:
Exemple #2
0
def save(request):
	"""
	Update dropbox file and its local copy with new content
	"""
	ret = { 'status': 'error', 'message': '', 'task_id': '', }
	if request.method == 'POST' and request.user:
		try:
			user = MDBUser.objects.get(username=request.user.username)
		except Exception, e:
			ret['message'] = "<strong>FATAL</strong>(save.user): %s" % e
		else:
			try:
				node = get_node_by_path(user, request.POST['db_path'])
				from main.tasks import save_node
				save_node(node.id, request.POST['content'])
			except Exception, e:
				ret['message'] = "<strong>FATAL</strong>(save.save_node): %s" % e
			else:
Exemple #3
0
def process_web_action(user, request, callback=None):
	"""
	Execute requested action for user
	Arguments:
		user: 				user to execute the action for
		request:
			['filename']:		user specified filename, passed from modal dialog
			['db_path']:		path of tree element, which was selected in UI
			['db_dir_path']:	parent dir for tree element, which was selected in UI
			['action']:			the actual action to perform
		NOTE: not all request fields are used in every action
	"""
	try:
		# User entered file or dir name
		filename = request['filename']
		# Selected node
		node = None
		if request['db_path']:
			node = get_node_by_path(user, request['db_path'])
		# Selected node's parent dir
		node_dir = None
		if request['db_dir_path']:
			db_dir_path = request['db_dir_path']
			if db_dir_path != '/':
				db_dir_path = db_dir_path.rstrip('/')
			node_dir = get_node_by_path(user, db_dir_path)
		# Perform requested action
		action = request['action']
		if action == 'remove_file':
			if not node.is_file:
				raise MDBException("ERROR: remove_file: '%s' is not a file ?!" %
								   (node.db_path, ))
			if django_settings.ASYNC_DROPBOX:
				yield gen.Task(remove_node_as_file,
					node.id)
			else:
				remove_node_as_file(node.id)
		elif action == 'remove_subdir':
			if node.is_file:
				raise MDBException("ERROR: remove_subdir(): '%s' is not a dir ?!" %
								   (node.db_path, ))
			if django_settings.ASYNC_DROPBOX:
				yield gen.Task(remove_node_as_dir,
					node.id)
			else:
				remove_node_as_dir(node.id)
		elif action == 'rename_file':
			if not node.is_file:
				raise MDBException("ERROR: rename_file(): '%s' is not a file ?!" %
								   (node.db_path, ))
			if django_settings.ASYNC_DROPBOX:
				yield gen.Task(rename_node,
					node.id, filename)
			else:
				rename_node(node.id, filename)
		elif action == 'rename_subdir':
			# Sanity check
			if node.db_path == "/":
				raise MDBException("ERROR: rename_subdir(): Can't rename root !")
			if node.is_file:
				raise MDBException("ERROR: rename_subdir(): '%s' is not a dir ?!" %
								   (node.db_path, ))
			if django_settings.ASYNC_DROPBOX:
				yield gen.Task(rename_node,
					node.id, filename)
			else:
				rename_node(node.id, filename)
		elif action == 'add_file':
			# TODO: get default content from folder settings (Meta-Data)
			if django_settings.ASYNC_DROPBOX:
				yield gen.Task(create_new_file,
					node_dir.id, filename, " ")
			else:
				create_new_file(node_dir.id, filename, " ")
		elif action == 'add_subdir':
			if django_settings.ASYNC_DROPBOX:
				yield gen.Task(create_new_dir,
					node_dir.id, filename)
			else:
				create_new_dir(node_dir.id, filename)
		elif action == 'reset':
			MDBUser.objects.filter(pk=user.pk).update(
				token_string	= "",
				auth_token 		= "",
				task_id 		= "",
			)
		else:
			raise MDBException('ERROR: invalid action (%s)' % (action, ))
	finally:
		if callback: callback()
Exemple #4
0
def sync_dir_from_dropbox(node_id, use_ust=True, callback=None):
	"""
	Sync dir which was updated on dropbox
	The whole dir is checked for added/removed files and dirs and each entry
	is updated using appropriate method
	Arguments:
		node_id: 			updated dir
		use_ust: 			if True, process remove in User Synchronous mode
	"""
	node, db_sess = _get_node(node_id)

	if use_ust:
		if django_settings.ASYNC_DROPBOX:
			yield gen.Task(async_ust_start, node.user)
		else:
			ust_start(node.user)

	# We need to try/except the whole block to make sure
	# that we call ust_end() before leaving the method
	try:
		if django_settings.ASYNC_DROPBOX:
			resp = yield gen.Task(db_sess.dir_changed,
				node.db_path, node.hash)
		else:
			resp = db_sess.dir_changed(node.db_path, node.hash)
		if not resp:
			l.info("sync_DIR_FROM_dropbox: '%s':'%s' skipping (same hash)" %\
				   (node.user.username, node.db_path, ))
		else:
			# User may want to know that this dir was updated
			append_to_changes_list(node.user, node.db_path)

			# Retrieve list of files and dirs from dropbox for given directory
			if django_settings.ASYNC_DROPBOX:
				file_dicts = yield gen.Task(db_sess.get_files_as_dicts,
					node.db_path)
			else:
				file_dicts = db_sess.get_files_as_dicts(node.db_path)
			if file_dicts:
				yield_keys = []
				# Check each file in directory for updates
				# We go through OUR file list and compare each file's
				# .last_modified date with the one in matching dropbox file
				for child in node.get_children():
					if not child.is_file:
						continue
					file_dict = dicts_find(file_dicts, child.db_path)
					if file_dict and dict_last_modified(file_dict) > child.last_modified:
						# File in dropbox was changed: remember new mod date and sync it
						MDBTree.objects.filter(pk=child.pk).update(
							last_modified = dict_last_modified(file_dict),
						)
						if django_settings.ASYNC_DROPBOX:
							yield_key = object()
							yield_keys.append(yield_key)
							local_callback = (yield gen.Callback(yield_key))
						else:
							local_callback = None
						sync_file_from_dropbox(child.id, use_ust=False, callback=local_callback)
				# Wait for all add_file_from_dropbox() to complete
				if django_settings.ASYNC_DROPBOX and yield_keys:
					yield gen.WaitAll(yield_keys)

			# Get only list of files as a set
			# And see what's new/missing
			db_files = set(dicts_to_paths(file_dicts, files_only=True))
			if db_files:
				# Get list of files in dir from database
				known_files = set(node.get_paths('FILES'))
				yield_keys = []
				# Add new files from dropbox to our database
				for new_file in db_files - known_files:
					if new_file != '':
						db_last_modified =\
						dict_last_modified(dicts_find(file_dicts, new_file))
						if django_settings.ASYNC_DROPBOX:
							yield_key = object()
							yield_keys.append(yield_key)
							local_callback = (yield gen.Callback(yield_key))
						else:
							local_callback = None
						add_file_from_dropbox(node.id, new_file, db_last_modified, use_ust=False,
							callback=local_callback)
				# Wait for all add_file_from_dropbox() to complete
				if django_settings.ASYNC_DROPBOX and yield_keys:
					yield gen.WaitAll(yield_keys)

				# Remove files deleted from dropbox from our database
				for missing_file in known_files - db_files:
					if missing_file != '':
						missing_node = get_node_by_path(node.user, missing_file)
						# Only remove it from our database and server
						if django_settings.ASYNC_DROPBOX:
							yield_key = object()
							remove_node_as_file(missing_node.id, skip_dropbox=True, use_ust=False,
								callback=(yield gen.Callback(yield_key)))
							yield gen.Wait(yield_key)
						else:
							remove_node_as_file(missing_node.id, skip_dropbox=True, use_ust=False)

			# Get only list of dirs as a set
			# And see what's new/missing
			db_dirs = set(dicts_to_paths(file_dicts, dirs_only=True))
			yield_keys = []
			if db_dirs:
				# Get list of dirs in dir from database
				known_dirs = set(node.get_paths('DIRS'))
				# Add new dirs from dropbox to our database
				for new_dir in db_dirs - known_dirs:
					if new_dir != '':
						if django_settings.ASYNC_DROPBOX:
							yield_key = object()
							yield_keys.append(yield_key)
							local_callback = (yield gen.Callback(yield_key))
						else:
							local_callback = None
						add_dir_from_dropbox(node.id, new_dir, use_ust=False, callback=local_callback)
					#ust_store_id(async_res.task_id, node.user)
				# Wait for all add_dir_from_dropbox() to complete
				if django_settings.ASYNC_DROPBOX and yield_keys:
					yield gen.WaitAll(yield_keys)

				# Remove dirs, which are missing from dropbox from our database
				for missing_dir in known_dirs - db_dirs:
					if missing_dir != '' and missing_dir != '/' :
						missing_node = get_node_by_path(node.user, missing_dir)
						# Only remove it from our database and server
						if django_settings.ASYNC_DROPBOX:
							yield_key = object()
							remove_node_as_dir(missing_node.id, skip_dropbox=True, use_ust=False,
								callback=(yield gen.Callback(yield_key)))
							yield gen.Wait(yield_key)
						else:
							remove_node_as_dir(missing_node.id, skip_dropbox=True, use_ust=False)

			# Save new hash for future checks
			MDBTree.objects.filter(pk=node.pk).update(
				hash 		= resp['hash'],
				last_synced = datetime.utcnow(),
			)
	except Exception, e:
		l.error("sync_DIR_FROM_dropbox: '%s':'%s' (%s)" %\
				(node.user.username, node.db_path, e, ))
		raise MDBException("ERROR: "+e.message)