diff src/nabble/view/web/template/NodePageNamespace.java @ 0:7ecd1a4ef557

add content
author Franklin Schmidt <fschmidt@gmail.com>
date Thu, 21 Mar 2019 19:15:52 -0600
parents
children
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/nabble/view/web/template/NodePageNamespace.java	Thu Mar 21 19:15:52 2019 -0600
@@ -0,0 +1,226 @@
+package nabble.view.web.template;
+
+import fschmidt.db.DbDatabase;
+import nabble.model.FileUpload;
+import nabble.model.Message;
+import nabble.model.ModelException;
+import nabble.model.Node;
+import nabble.model.Person;
+import nabble.naml.compiler.Command;
+import nabble.naml.compiler.CommandSpec;
+import nabble.naml.compiler.IPrintWriter;
+import nabble.naml.compiler.Interpreter;
+import nabble.naml.compiler.Namespace;
+import nabble.naml.compiler.ScopedInterpreter;
+import nabble.naml.namespaces.TemplateException;
+import nabble.view.lib.Jtp;
+import nabble.view.lib.Permissions;
+import nabble.view.web.forum.NodeEditorNamespace;
+import nabble.view.web.forum.SearchNamespace;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import javax.servlet.ServletException;
+import javax.servlet.http.HttpServletRequest;
+import java.util.Date;
+import java.util.Random;
+
+
+@Namespace (
+	name = "node_page",
+	global = true
+)
+public final class NodePageNamespace {
+
+	private static final Logger logger = LoggerFactory.getLogger(NodePageNamespace.class);
+
+	private NodeNamespace nodeNs;
+
+	public NodePageNamespace(Node node) {
+		this(new NodeNamespace(node));
+	}
+
+	public NodePageNamespace(NodeNamespace nodeNs) {
+		this.nodeNs = nodeNs;
+	}
+
+	public final Node node() {
+		return nodeNs.node();
+	}
+
+	public final NodeNamespace nodeNamespace() {
+		return nodeNs;
+	}
+
+	private DbDatabase db() {
+		return node().getSite().getDb();
+	}
+
+
+	public static final CommandSpec page_node = CommandSpec.DO;
+
+	@Command public void page_node(IPrintWriter out,ScopedInterpreter<NodeNamespace> interp) {
+		out.print( interp.getArg(nodeNs,"do") );
+	}
+
+	public static final CommandSpec search_namespace = CommandSpec.DO()
+		.requiredInStack(ServletNamespace.class)
+		.build()
+	;
+
+	@Command public void search_namespace(IPrintWriter out,ScopedInterpreter<SearchNamespace> interp)
+		throws ServletException
+	{
+		ServletNamespace servletNamespace = interp.getFromStack(ServletNamespace.class);
+		out.print( interp.getArg(new SearchNamespace(node(),servletNamespace),"do") );
+	}
+
+
+	public static final CommandSpec edit_page_node = CommandSpec.DO()
+		.optionalParameters("commit")
+		.requiredInStack(ServletNamespace.class)
+		.build()
+	;
+
+	@Command public void edit_page_node(IPrintWriter out,ScopedInterpreter<NodeEditorNamespace> interp) {
+		ServletNamespace servletNs = interp.getFromStack(ServletNamespace.class);
+		boolean commit = interp.getArgAsBoolean("commit",true);
+		DbDatabase db = db();
+		db.beginTransaction();
+		try {
+			nodeNs.refreshNode();
+			interp.getArgString(new NodeEditorNamespace(node(),servletNs),"do");
+			if( commit ) {
+				db.commitTransaction();
+				nodeNs.refreshNode();
+			}
+		} finally {
+			db.endTransaction();
+		}
+	}
+
+
+	public static final CommandSpec create_child_of_page_node = CommandSpec.DO()
+		.parameters("subject","message","is_html","kind")
+		.optionalParameters("commit","type")
+		.restrictedParameter("kind","app","post")
+		.requiredInStack(ServletNamespace.class)
+		.build()
+	;
+
+	@Command public void create_child_of_page_node(IPrintWriter out,ScopedInterpreter<NodeEditorNamespace> interp)
+		throws ModelException, ServletException
+	{
+		ServletNamespace servletNs = interp.getFromStack(ServletNamespace.class);
+		HttpServletRequest request = servletNs.request;
+		boolean commit = interp.getArgAsBoolean("commit",true);
+		String subject = interp.getArgString("subject");
+		String message = interp.getArgString("message");
+		Message.Format msgFmt = interp.getArgAsBoolean("is_html",false) ? Message.Format.HTML : Message.Format.TEXT;
+		String type = interp.getArgString("type");
+		Node.Kind kind = "app".equals(interp.getArgString("kind"))? Node.Kind.APP : Node.Kind.POST;
+		Person visitor = servletNs.getVisitor();
+		DbDatabase db = db();
+		db.beginTransaction();
+		try {
+			nodeNs.refreshNode();
+			Node node = node();
+			Node newNode = visitor.newChildNode(kind,subject,message,msgFmt,node);
+			FileUpload.checkFileTags(newNode.getMessage(), visitor);
+			if (type != null)
+				newNode.setType(type);
+			interp.getArgString(new NodeEditorNamespace(newNode,servletNs),"do");
+			if( commit ) {
+				db.commitTransaction();
+				nodeNs.refreshNode();
+			}
+		} finally {
+			db.endTransaction();
+		}
+	}
+
+	private static final long TWO_HOURS = 2 * 60 * 60 * 1000;
+
+	@Command public void should_show_creation_notice(IPrintWriter out,Interpreter interp) {
+		long created = node().getWhenCreated().getTime();
+		out.print( System.currentTimeMillis() - created < TWO_HOURS );
+	}
+
+
+	//
+	// Spambot security checker
+	//
+	private static final byte SUBMIT_POSSIBILITIES = 10;
+	private static final long START = new Date().getTime();
+	private static final long FIVE_MINUTES = 5 * 60 * 1000;
+	private static final Random SECURITY_RND = new Random();
+
+	public static final CommandSpec antispam_submit_button = CommandSpec.DO()
+		.parameters("class", "value")
+		.requiredInStack(ServletNamespace.class)
+		.build()
+	;
+
+	@Command public void antispam_submit_button(IPrintWriter out,Interpreter interp) {
+		ServletNamespace servletNs = interp.getFromStack(ServletNamespace.class);
+		HttpServletRequest request = servletNs.request;
+
+		String className = interp.getArgString("class");
+		String value = interp.getArgString("value");
+
+		Byte goodIndex = (byte) SECURITY_RND.nextInt(SUBMIT_POSSIBILITIES);
+		request.getSession().setAttribute("sec"+node().getId(), goodIndex);
+		for (byte i = 0; i < SUBMIT_POSSIBILITIES; i++) {
+			out.print("<input id=\"s" + i + "\" type=\"submit\" class=\""+ className + "\" value=\"" + value + "\" name=\"s" + i + "\" style=\"display:none\"/>");
+		}
+		String elementId = "s" + goodIndex;
+		StringBuilder bufValue = new StringBuilder();
+		for (int i = 0; i < elementId.length(); i++) {
+			if (bufValue.length() > 0)
+				bufValue.append(',');
+			bufValue.append((int) elementId.charAt(i));
+		}
+		out.print("<script type='text/javascript'>");
+		out.print("var sv=String.fromCharCode("+ bufValue.toString() +");");
+		out.print("document.getElementById(sv).style.display='inline-block';");
+		out.print("</script>");
+	}
+
+	public static final CommandSpec check_antispam_submit = CommandSpec.DO()
+		.optionalParameters("bypass")
+		.requiredInStack(ServletNamespace.class)
+		.build()
+	;
+
+	@Command public void check_antispam_submit(IPrintWriter out,Interpreter interp)
+			throws TemplateException
+	{
+		ServletNamespace servletNs = interp.getFromStack(ServletNamespace.class);
+		HttpServletRequest request = servletNs.request;
+
+		String bypass = interp.getArgString("bypass");
+		if (bypass != null && request.getParameter(bypass) != null)
+			return;
+
+		String attributeName = "sec"+node().getId();
+		Byte goodIndex = (Byte) request.getSession().getAttribute(attributeName);
+		boolean isSafe = goodIndex != null;
+		if (isSafe) {
+			for (int i= 0; i < SUBMIT_POSSIBILITIES; i++) {
+				String param = request.getParameter("s"+i);
+				if (i == goodIndex)
+					isSafe = isSafe &&  param != null;
+				else
+					isSafe = isSafe && param == null;
+			}
+		}
+		request.getSession().removeAttribute(attributeName);
+		if (!isSafe) {
+			long now = new Date().getTime();
+			if (now - START > FIVE_MINUTES) {
+				logger.error("suspicious_request - IP: " + Jtp.getClientIpAddr(request));
+				throw TemplateException.newInstance("suspicious_request");
+			}
+		}
+	}
+}