view src/nabble/view/web/template/UserNamespace.java @ 47:72765b66e2c3

remove mailing list code
author Franklin Schmidt <fschmidt@gmail.com>
date Fri, 18 Jun 2021 17:44:24 -0600
parents cc5b7d515580
children
line wrap: on
line source

package nabble.view.web.template;

import fschmidt.util.java.Filter;
import fschmidt.util.java.HtmlUtils;
import nabble.model.DailyNumber;
import nabble.model.FilteredNodeIterator;
import nabble.model.ModelException;
import nabble.model.ModelHome;
import nabble.model.Node;
import nabble.model.NodeIterator;
import nabble.model.NodeSearcher;
import nabble.model.Person;
import nabble.model.Site;
import nabble.model.Subscription;
import nabble.model.User;
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.ListSequence;
import nabble.view.lib.Jtp;
import nabble.view.lib.Permissions;
import nabble.view.lib.Shared;

import javax.servlet.ServletException;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Map;


@Namespace (
	name = "user",
	global = false
)
public final class UserNamespace {
	private final Person personR;
	private User userR;

	public UserNamespace(Person person) {
/*
		if( person == null )
			throw new NullPointerException("person is null");
*/
		this.personR = person;
		this.userR = person instanceof User ? (User)person : null;
	}

	public void refreshUser() {
		if( isUser() )
			userR = userR.getGoodCopy();
	}

	public boolean isUser() {
		return userR != null;
	}

	public User user() {
		return userR;
	}

	public Person person() {
		return isUser() ? user() : personR;
	}

	private Site site() {
		return person().getSite();
	}

	public static final CommandSpec this_user = CommandSpec.DO;

	@Command public void this_user(IPrintWriter out,ScopedInterpreter<UserNamespace> interp) {
		out.print( interp.getArg(this,"do") );
	}

	@Command public void id(IPrintWriter out,Interpreter interp) {
		out.print( interp.encode( person().getIdString() ) );
	}

	@Command public void search_id(IPrintWriter out,Interpreter interp) {
		out.print( person().getSearchId() );
	}

	public static final CommandSpec name = new CommandSpec.Builder()
		.optionalParameters("truncate")
		.build()
	;

	@Command public void name(IPrintWriter out,Interpreter interp)
		throws IOException
	{
		String truncate = interp.getArgString("truncate");
		String name = person().getName();
		if( name==null ) {
			out.print((String)null);
			return;
		}
		if (truncate != null) {
			try {
				name = Jtp.truncate(name,Integer.valueOf(truncate),"...");
			} catch (NumberFormatException e) {
				throw new RuntimeException("Invalid \"truncate\" attribute: " + truncate);
			}
		}
		out.print( interp.encode(name) );
	}

	public static final CommandSpec avatar_url = new CommandSpec.Builder()
		.optionalParameters("size")
		.build()
	;

	@Command public void avatar_url(IPrintWriter out,Interpreter interp)
		throws IOException
	{
		String size = interp.getArgString("size");
		out.print( interp.encode(Shared.getAvatarImageURL(person(), "small".equals(size))) );
	}

	public static final CommandSpec default_avatar_url = new CommandSpec.Builder()
		.optionalParameters("size")
		.build()
	;

	@Command public void default_avatar_url(IPrintWriter out,Interpreter interp)
		throws IOException
	{
		String size = interp.getArgString("size");
		out.print( interp.encode(Shared.getDefaultAvatarImageURL("small".equals(size))) );
	}

	@Command public void is_registered(IPrintWriter out,Interpreter interp) {
		out.print( isUser() && user().isRegistered() );
	}

	@Command public void has_too_many_posts(IPrintWriter out,Interpreter interp) {
		out.print( isUser() && user().hasTooManyPosts() );
	}

	public static final CommandSpec registration_date = CommandSpec.DO;

	@Command public void registration_date(IPrintWriter out,ScopedInterpreter<DateNamespace> interp) {
		out.print( interp.getArg( new DateNamespace(user().getRegistered()), "do" ) );
	}

	@Command public void is_deactivated(IPrintWriter out,Interpreter interp) {
		out.print( isUser() && user().isDeactivated() );
	}

	@Command public void is_anonymous(IPrintWriter out,Interpreter interp) {
		out.print( !isUser() );
	}

	@Command public void is_authenticated(IPrintWriter out,Interpreter interp) {
		out.print( isUser() );
	}

	@Command public void user_email(IPrintWriter out,Interpreter interp) {
		out.print( user().getEmail() );
	}

	@Command public void resetcode(IPrintWriter out,Interpreter interp) {
		out.print( user().getResetcode() );
	}

	@Command public void send_email_url(IPrintWriter out,Interpreter interp) {
		out.print( interp.encode( "/user/SendEmail.jtp?type=user&user=" + user().getId() ) );
	}


	public static final CommandSpec is_in_group = new CommandSpec.Builder()
		.dotParameter("group")
		.build()
	;

	@Command public void is_in_group(IPrintWriter out,Interpreter interp) {
		String group = interp.getArgString("group");
		out.print( isUser() && Permissions.isInGroup(user(),group) );
	}

	public static final CommandSpec has_permission = new CommandSpec.Builder()
		.parameters("node","permission_node","permission")
		.build()
	;

	@Command public void has_permission(IPrintWriter out,Interpreter interp) {
		NodeNamespace nodeNs = interp.getArgAsNamespace(NodeNamespace.class,"node");
		NodeNamespace permissionNodeNs = interp.getArgAsNamespace(NodeNamespace.class,"permission_node");
		String perm = interp.getArgString("permission");
		out.print( Permissions.hasPermission(permissionNodeNs.node(),nodeNs.node(),user(),perm) );
	}

	public static final CommandSpec has_site_permission = new CommandSpec.Builder()
		.parameters("permission")
		.build()
	;

	@Command public void has_site_permission(IPrintWriter out,Interpreter interp) {
		String perm = interp.getArgString("permission");
		out.print( Permissions.hasSitePermission(NabbleNamespace.current().site(),user(),perm) );
	}

	public static final CommandSpec owns = new CommandSpec.Builder()
		.dotParameter("node")
		.build()
	;

	@Command public void owns(IPrintWriter out,Interpreter interp) {
		NodeNamespace nodeNs = interp.getArgAsNamespace(NodeNamespace.class,"node");
		out.print( nodeNs.node().getOwner().equals(person()) );
	}

	public static final CommandSpec as_user_page = CommandSpec.DO;

	@Command public void as_user_page(IPrintWriter out,ScopedInterpreter<UserPageNamespace> interp) {
		out.print( interp.getArg(new UserPageNamespace(this),"do") );
	}


	public static final CommandSpec groups = CommandSpec.DO;

	@Command public void groups(IPrintWriter out,ScopedInterpreter<NabbleNamespace.GroupList> interp) {
		List<String> groups = Permissions.getPersonGroups(user());
		Object block = interp.getArg(new NabbleNamespace.GroupList(groups),"do");
		out.print(block);
	}

	public static final CommandSpec nodes_list = CommandSpec.DO()
		.parameters("length")
		.optionalParameters("start","sort","filter")
		.requiredInStack(ServletNamespace.class)
		.build()
	;

	@Command public void nodes_list(IPrintWriter out,ScopedInterpreter<NodeList> interp)
		throws ServletException
	{
		ServletNamespace servletNamespace = interp.getFromStack(ServletNamespace.class);
		int start = NodeNamespace.getLoopStart(interp);
		int length = NodeNamespace.getLoopLength(interp);
		String filter = interp.getArgString("filter");
		NodeIterator<? extends Node> nodeIter = person().getNodesByDateDesc(filter);
		try {
			Filter<Node> viewFilter = Permissions.canBeViewedByPersonFilter(servletNamespace.getVisitorUser());
			nodeIter = new FilteredNodeIterator(nodeIter,viewFilter);
			NodeList.userNodes( out, interp, nodeIter, start, length );
		} finally {
			nodeIter.close();
		}
	}

	@Command public void post_filter(IPrintWriter out,Interpreter interp) {
		out.print( "(is_app is null or not is_app)" );
	}

	@Command public void app_filter(IPrintWriter out,Interpreter interp) {
		out.print( "is_app" );
	}

	@Command public void topic_filter(IPrintWriter out,Interpreter interp) {
		out.print( "(is_app is null or not is_app) and exists(select 1 from node p where node.parent_id=p.node_id and is_app)" );
	}

	@Command public void reply_filter(IPrintWriter out,Interpreter interp) {
		out.print( "(is_app is null or not is_app) and exists(select 1 from node p where node.parent_id=p.node_id and (is_app is null or not is_app))" );
	}

	public static final CommandSpec equals = new CommandSpec.Builder()
		.dotParameter("user")
		.build()
	;

	@Command public void equals(IPrintWriter out,Interpreter interp) {
		UserNamespace userNs = interp.getArgAsNamespace(UserNamespace.class,"user");
		out.print( userNs.person().equals(person()) );
	}


	@Namespace (
		name = "user_list",
		global = true
	)
	public static class UserList extends ListSequence<User> {

		public UserList(List<User> nodeUsers) {
			super(nodeUsers);
		}

		public static final CommandSpec current_user = CommandSpec.DO;

		@Command public void current_user(IPrintWriter out,ScopedInterpreter<UserNamespace> interp) {
			out.print( interp.getArg(new UserNamespace(get()),"do") );
		}

		@Command public void next_user(IPrintWriter out,Interpreter interp) {
			next_element(out,interp);
		}

		public static final CommandSpec sort_by_node_count_desc = CommandSpec.NO_OUTPUT;

		@Command public void sort_by_node_count_desc(IPrintWriter out,Interpreter interp) {
			Collections.sort(elements,User.nodeCountComparatorDesc);
		}

		public static final CommandSpec sort_by_name = CommandSpec.NO_OUTPUT;

		@Command public void sort_by_name(IPrintWriter out,Interpreter interp) {
			Collections.sort(elements,User.BY_NAME_COMPARATOR);
		}

		public static final CommandSpec sub_list = CommandSpec.DO()
			.parameters("length")
			.optionalParameters("start")
			.build()
		;

		@Command public void sub_list(IPrintWriter out,ScopedInterpreter<UserList> interp) {
			int start = interp.getArgAsInt("start",0);
			int length = interp.getArgAsInt("length");
			UserList ns ;
			if( start==0 && length >= elements.size() ) {
				ns = this;
			} else {
				ns = new UserList(elements.subList(start,Math.min(elements.size(),start+length)));
			}
			out.print( interp.getArg(ns,"do") );
		}
	}

	public static final CommandSpec signature_impl = CommandSpec.DO;

	@Command public void signature_impl(IPrintWriter out,ScopedInterpreter<MessageNamespace> interp) {
		out.print( interp.getArg( new MessageNamespace(person().getSignature()), "do" ) );
	}

	@Command public void has_signature(IPrintWriter out,Interpreter interp) {
		out.print( person().getSignature() != null );
	}

	public static final CommandSpec node_count = new CommandSpec.Builder()
		.optionalParameters("filter")
		.build()
	;

	@Command public void node_count(IPrintWriter out,Interpreter interp) {
		out.print( person().getNodeCount(interp.getArgString("filter")) );
	}

	@Command public void is_banned(IPrintWriter out, Interpreter interp) {
		out.print( isUser() && Permissions.isBanned(user()) );
	}

	public static final CommandSpec ban = CommandSpec.NO_OUTPUT;

	@Command public void ban(IPrintWriter out, Interpreter interp) {
		Permissions.ban(user());
		site().update(); // uncache
	}

	public static final CommandSpec unban = CommandSpec.NO_OUTPUT;

	@Command public void unban(IPrintWriter out, Interpreter interp) {
		Permissions.unban(user());
		site().update(); // uncache
	}

	public static final CommandSpec delete_user_nodes = CommandSpec.NO_OUTPUT;

	@Command public void delete_user_nodes(IPrintWriter out, Interpreter interp) {
		person().deleteNodes();
	}


	@Command public void is_sysadmin(IPrintWriter out, Interpreter interp) {
		out.print( isUser() && Permissions.isSysAdmin(user()) );
	}

	public static final CommandSpec reset_password_path = new CommandSpec.Builder()
		.parameters("email","q")
		.build()
	;

	@Command public void reset_password_path(IPrintWriter out,Interpreter interp) {
		String email = interp.getArgString("email");
		String q = interp.getArgString("q");
		out.print( interp.encode( "/user/ResetPassword.jtp" ) );
		if (email!=null && q!=null)
			out.print( interp.encode("?email=" + HtmlUtils.urlEncode(email) + "&q=" + HtmlUtils.urlEncode(q)) );
	}

	@Command public void change_email_path(IPrintWriter out,Interpreter interp) {
		out.print( interp.encode( "/user/ChangeEmail.jtp?user=" + user().getId() ) );
	}

	@Command public void change_avatar_path(IPrintWriter out,Interpreter interp) {
		out.print( interp.encode( "/user/ChangeAvatar.jtp" ) );
	}

	@Command public void advanced_settings_path(IPrintWriter out,Interpreter interp) {
		out.print( interp.encode( "/user/Advanced.jtp" ) );
	}

	@Command public void remove_account_path(IPrintWriter out,Interpreter interp) {
		out.print( interp.encode( "/user/RemoveAccount.jtp" ) );
	}

	private Map<Long,Long> lastVisitedNodeIds = null;

	private Long lastVisitedNodeId(Interpreter interp,long nodeId) {
		if( !isUser() )
			return null;
		if( lastVisitedNodeIds == null ) {
			RequestNamespace.ParameterValueList params = interp.getFromStack(RequestNamespace.ParameterValueList.class);
			List<Long> ids = new ArrayList<Long>();
			for( String value : params.values() ) {
				ids.add(Long.parseLong(value));
			}
			lastVisitedNodeIds = user().lastVisitedNodeIds(ids);
		}
		return lastVisitedNodeIds.get(nodeId);
	}

	public static final CommandSpec has_visited_node = CommandSpec.DO()
		.parameters("node_id")
		.requiredInStack(RequestNamespace.ParameterValueList.class)
		.build()
	;

	@Command public void has_visited_node(IPrintWriter out, Interpreter interp) {
		Long id = lastVisitedNodeId(interp, interp.getArgAsLong("node_id"));
		Node node = id == null? null : site().getNode(id);
		if (id != null && node == null)
			lastVisitedNodeIds.remove(id);
		out.print( node != null);
	}

	public static final CommandSpec last_visited_node = CommandSpec.DO()
		.parameters("node_id")
		.requiredInStack(RequestNamespace.ParameterValueList.class)
		.build()
	;

	@Command public void last_visited_node(IPrintWriter out, ScopedInterpreter<NodeNamespace> interp) {
		Node lastVisitedNode = null;
		long nodeId = interp.getArgAsLong("node_id");
		Long id = lastVisitedNodeId(interp,nodeId);
		if (id != null)
			lastVisitedNode = site().getNode(id);
		out.print( interp.getArg( new NodeNamespace(lastVisitedNode), "do" ) );
	}

	public static final CommandSpec mark_visited = CommandSpec.NO_OUTPUT()
		.parameters("last_node_id")
		.dotParameter("node")
		.build()
	;

	@Command public void mark_visited(IPrintWriter out, Interpreter interp) {
		if (isUser()) {
			NodeNamespace nodeNs = interp.getArgAsNamespace(NodeNamespace.class,"node");
			long lastNodeId = interp.getArgAsLong("last_node_id");
			user().markVisited(nodeNs.node(), lastNodeId);
		}
	}

	public static final CommandSpec register = new CommandSpec.Builder()
		.requiredInStack(ServletNamespace.class)
		.build()
	;

	@Command public void register(IPrintWriter out, Interpreter interp)
		throws ModelException, IOException
	{
		user().register();
		refreshUser();
		ServletNamespace servletNamespace = interp.getFromStack(ServletNamespace.class);
		Jtp.doLogin(servletNamespace.request, servletNamespace.response, user(), false);
		DailyNumber.registrations.inc();
	}

	public static final CommandSpec NAME = new CommandSpec.Builder()
		.dotParameter("name")
		.build()
	;

	public static final CommandSpec has_property = NAME;

	@Command public void has_property(IPrintWriter out,Interpreter interp) {
		String name = interp.getArgString("name");
		out.print(user().getProperty(name) != null);
	}

	public static final CommandSpec get_property = NAME;

	@Command public void get_property(IPrintWriter out,Interpreter interp) {
		String name = interp.getArgString("name");
		out.print(user().getProperty(name));
	}

	public static final CommandSpec delete_property = CommandSpec.NO_OUTPUT()
		.parameters("name")
		.build()
	;

	@Command public void delete_property(IPrintWriter out,Interpreter interp) {
		User user = user();
		String name = interp.getArgString("name");
		user.setProperty(name, null);
		user.getSite().update();
	}

	public static final CommandSpec set_property = CommandSpec.NO_OUTPUT()
		.parameters("name", "value")
		.build()
	;

	@Command public void set_property(IPrintWriter out,Interpreter interp) {
		User user = user();
		String name = interp.getArgString("name");
		String value = interp.getArgString("value");
		user.setProperty(name, value);
		user.getSite().update();
	}

	public static final CommandSpec has_subscription_to_descentants_of = CommandSpec.NO_OUTPUT()
		.dotParameter("node")
		.build()
	;

	@Command public void has_subscription_to_descentants_of(IPrintWriter out,Interpreter interp) {
		if (userR == null) {
			out.print(false);
			return;
		}
		NodeNamespace nodeNs = interp.getArgAsNamespace(NodeNamespace.class,"node");
		for (Node n : nodeNs.node().getAncestors() ) {
			if (userR.isSubscribed(n)) {
				Subscription subscription = userR.getSubscription(n);
				if (subscription.getTo() == Subscription.To.DESCENDANTS) {
					out.print(true);
					return;
				}
			}
		}
		out.print(false);
	}

}