Ivan Melnikov avatar Ivan Melnikov committed d611663 Draft

Restrict page access

Comments (0)

Files changed (3)

 ###   Models   ###
 ##################
 
+# Enum to describe access policy
+class Access():
+	ALL = 'ALL'
+	PRIVATE = 'PRIVATE'
+	PARENT = 'PARENT'
+
+# Main class to store wiki-page
 class Page(db.Model):
 	path = db.StringProperty(required=True)
 	updated = db.DateTimeProperty(auto_now=True)
 	html = db.TextProperty() #required=True
 	user_id = db.IntegerProperty()
 	# title = db.StringProperty()
-	# access = db.StringProperty()
+	
+	access = db.StringProperty(default=Access.ALL)
 
 	# url path
 	# for root return empty string to avoid //.edit urls
 	return urllib.quote(url.encode('utf-8'))
 
 def not_empty(l):
-	return len(l) > 0	
+	return len(l) > 0
+
+def check_access(page):
+	# TODO: add cache
+	if page.access == Access.PRIVATE:
+		user = get_user()
+		# TODO: store private user list in separate entity
+		if user.key().id() == page.user_id:
+			return True
+		else:
+			return False
+
+	if page.access == Access.ALL:
+		return True
+
+	# Return false for unsupported access policies
+	return False
+
 
 
 jinja_environment = jinja2.Environment(
 jinja_environment.filters['user_name'] = user_name
 jinja_environment.filters['urlencode'] = encode
 jinja_environment.tests['not_empty'] = not_empty
+jinja_environment.tests['access'] = check_access
 
 
 log = logging.getLogger('page')
 
 
+class PreviewPage(webapp2.RequestHandler):
+	def post(self):
+		text = self.request.get('text')
+		html = convert(text)
+		self.response.out.write(html)
+
+
+class GetPage(webapp2.RequestHandler):
+	''' Get formated wiki page '''
+	@auth
+	def get(self, path):
+		if not path: path = '/'
+		page = get_page(path)
+
+		values = {'page': page, 'breadcrumbs': breadcrumbs(path)}
+		if page:
+			values['files'] = get_files(page)
+			# TODO: lazy load
+			values['upload'] = blobstore.create_upload_url(encode(page.upath()+'/.files'))
+			
+		template = jinja_environment.get_template('get.html')
+		self.response.out.write(template.render(values))
+
+
 class EditPage(webapp2.RequestHandler):
 	''' Edit wiki page '''
 	@auth
 		self.redirect(encode(page.path))
 
 
-class PreviewPage(webapp2.RequestHandler):
-	def post(self):
-		text = self.request.get('text')
-		html = convert(text)
-		self.response.out.write(html)
-
-
-class GetPage(webapp2.RequestHandler):
-	''' Get formated wiki page '''
-	@auth
-	def get(self, path):
-		if not path: path = '/'
-		page = get_page(path)
-
-		values = {'page': page, 'breadcrumbs': breadcrumbs(path)}
-		if page:
-			values['files'] = get_files(page)
-			# TODO: lazy load
-			values['upload'] = blobstore.create_upload_url(encode(page.upath()+'/.files'))
-			
-		template = jinja_environment.get_template('get.html')
-		self.response.out.write(template.render(values))
-
-
 class DeletePage(webapp2.RequestHandler):
 	''' Delete page '''
 	@auth
 		self.redirect(path)
 
 
+class AccessPage(webapp2.RequestHandler):
+	def get(self, path):
+		if not path: path = '/'
+		page = get_page(path)
+
+		values = {'page': page, 'breadcrumbs': breadcrumbs(path)}
+		if page:
+			# TODO: lazy load
+			values['files'] = get_files(page)
+			values['upload'] = blobstore.create_upload_url(encode(page.upath()+'/.files'))
+
+		template = jinja_environment.get_template('access.html')
+		self.response.out.write(template.render(values))
+
+	def post(self, path):
+		if not path: path = '/'
+		page = get_page(path)
+
+		param = self.request.get('access')
+		if param == 'all':
+			access = Access.ALL
+		if param == 'private':
+			access = Access.PRIVATE
+		
+		page.access = access
+		page.user_id = get_user().key().id()
+		page.put()
+
+		# Update page cache
+		set_page(path, page)
+
+		self.redirect(path)
+
+
 class EditPageFiles(blobstore_handlers.BlobstoreUploadHandler, blobstore_handlers.BlobstoreDownloadHandler):
 	def post(self, path):
 		if not path: path = '/'
 
 							   (URL_MOVE_PAGE, MovePageCluster),
 
+							   ('/\.preview', PreviewPage),
 							   ('(.*)/\.edit', EditPage),
 							   ('(.*)/\.delete', DeletePage),
 							   ('(.*)/\.log', HistoryPage),
 							   ('(.*)/\.move', MovePage),
 							   ('(.*)/\.tree', TreePage),
 							   ('(.*)/\.subscribe', SubscribePage),
-							   ('/\.preview', PreviewPage),
+							   ('(.*)/\.access', AccessPage),
 
 							   ('(.*)/\.files', EditPageFiles),
 							   ('(.*)/\.files/(.*)', EditPageFiles),

template/page/access.html

+{% extends "get.html" %}
+
+{% block get_content %}
+
+<h1>Доступ к странице</h1>
+
+<form method="POST">
+
+Страницу могут просматривать	
+<select name="access">
+	<option value="all" {% if page.access == 'ALL' %}selected{% endif %} >
+		Все
+	</option>
+	<option value="private" {% if page.access == 'PRIVATE' %}selected{% endif %}>
+		Приватный
+	</option>
+</select>
+<br/>
+<input type="submit" value="Сохранить"/>
+</form>
+
+{% endblock %}

template/page/get.html

 
 {% block content %}
 
-{% if page %}
+{% if page and page is access %}
 {# cant show any menu for dead page #}
 
 {# page settings #}
 			<a href="{{ page.upath() }}/.move">Переместить</a>
 		</li>
 		<li class="page-files-link">
+			<a href="{{ page.upath() }}/.access">Доступ</a>
+		</li>
+		<li class="page-files-link">
 			<a href="{{ page.upath() }}/.delete">Удалить</a>
 		</li>
 	</ul>
 {% endfor %}
 </div>
 
-{% block get_content %}
-{% if not page %}
+{# check access #}
+{% if page is access %}
 
-	<h2>Данная страница не существует</h2>
+	{% block get_content %}
+	{% if not page %}
 
-	<a onclick="l = window.location; if (l.pathname.length > 1) l.href += '/.edit'; else l.href = '/.edit';" 
-	   class="page-edit-btn">
-		Создать
-	</a>
+		<h2>Данная страница не существует</h2>
+
+		<a onclick="l = window.location; if (l.pathname.length > 1) l.href += '/.edit'; else l.href = '/.edit';" 
+		   class="page-edit-btn">
+			Создать
+		</a>
+
+	{% else %}
+
+		{# wiki page #}
+		<div class="page-text" ondblclick="location.href='{{ page.upath() }}/.edit'">
+			{{ page.html }} 
+		</div>
+
+		<a href="{{ page.upath() }}/.edit" class="page-edit-btn">Правка</a>
+
+	{% endif %}
+	{% endblock %}
 
 {% else %}
-
-	{# wiki page #}
-	<div class="page-text" ondblclick="location.href='{{ page.upath() }}/.edit'">
-		{{ page.html }} 
-	</div>
-
-	<a href="{{ page.upath() }}/.edit" class="page-edit-btn">Правка</a>
+	
+	<h2>Доступ к данной странице закрыт</h2>
 
 {% endif %}
-{% endblock %}
 
 {% endblock %}
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.