autocreatequota - does it really work? [once again]

Voutsinas Nikos nvoutsin at noc.uoa.gr
Fri Nov 15 12:25:11 EST 2002


Please ignore our previous patch ( it only works with the use of some 
libraries implemented for internal use ). I am sorry for the 
inconvenience but, beleive me, if you apply the following patch 
everything will work as Christos promished. So once again:

Patch installation: cd into the directory where cyrus-imapd-2.1.10 
resides, and then execute:
/usr/local/bin/patch -p0 <edunet-autocreate
-------------- next part --------------
diff -Naur cyrus-imapd-2.1.10/imap/imapd.c cyrus-imapd-2.1.10-autocreate/imap/imapd.c
--- cyrus-imapd-2.1.10/imap/imapd.c	Wed Nov  6 22:43:20 2002
+++ cyrus-imapd-2.1.10-autocreate/imap/imapd.c	Fri Nov 15 19:15:41 2002
@@ -139,6 +139,7 @@
 void fatal(const char *s, int code);
 
 void cmdloop(void);
+void autocreate_folders(void);
 void cmd_login(char *tag, char *user);
 void cmd_authenticate(char *tag, char *authtype);
 void cmd_noop(char *tag, char *cmd);
@@ -1672,6 +1673,42 @@
     }
 }
 
+
+/* 
+ * Autocreate Inboxes and subfolders upon login
+ */
+void autocreate_folders()
+{
+    char mailboxname[MAX_MAILBOX_NAME+1];
+    sfolder *subfolder;
+    int i,r=0;
+
+	if (imapd_userisadmin) return;
+
+	/* Exclude Anonymous */
+	if(!strcmp(imapd_userid, "anonymous")) return;
+
+	r = (*imapd_namespace.mboxname_tointernal)(&imapd_namespace,
+		"INBOX", imapd_userid, mailboxname);
+
+	if (!r) r=mboxlist_autocreate_inbox(mailboxname, imapd_userid, imapd_authstate, 1, 0, 0);        
+
+	if (!r) {
+	    subfolder=mboxlist_get_subfolders();
+	    for(i=0;subfolder[i].folder!=NULL;i++){
+		r = (*imapd_namespace.mboxname_tointernal)(&imapd_namespace, subfolder[i].folder, 
+		                                            imapd_userid, mailboxname);
+		if (!r) r=mboxlist_autocreate_inbox(mailboxname, imapd_userid, imapd_authstate,
+		                                    0, subfolder[i].sub, 0);
+	    }
+        
+	   /* Free ... subfolders ???? */
+	   free_subfolder(subfolder);
+
+	}
+return;
+}
+
 /*
  * Perform a LOGIN command
  */
@@ -1804,6 +1841,7 @@
     mboxname_hiersep_tointernal(&imapd_namespace, imapd_userid);
 
     freebuf(&passwdbuf);
+    autocreate_folders();
     return;
 }
 
@@ -1924,6 +1962,7 @@
     /* Translate any separators in userid */
     mboxname_hiersep_tointernal(&imapd_namespace, imapd_userid);
 
+    autocreate_folders();
     return;
 }
 
@@ -3500,13 +3539,14 @@
 
 /*
  * Perform a CREATE command
+ * Autocreatequota functionality
+ * has been removed, due to autocreate_inbox.
  */
 void
 cmd_create(char *tag, char *name, char *partition, int localonly)
 {
     int r = 0;
     char mailboxname[MAX_MAILBOX_NAME+1];
-    int autocreatequota;
 
     if (partition && !imapd_userisadmin) {
 	r = IMAP_PERMISSION_DENIED;
@@ -3529,19 +3569,6 @@
 				   imapd_userisadmin, 
 				   imapd_userid, imapd_authstate,
 				   localonly, localonly);
-
-	if (r == IMAP_PERMISSION_DENIED && !strcasecmp(name, "INBOX") &&
-	    (autocreatequota = config_getint("autocreatequota", 0))) {
-
-	    /* Auto create */
-	    r = mboxlist_createmailbox(mailboxname, 0,
-				       partition, 1, imapd_userid,
-				       imapd_authstate, 0, 0);
-	    
-	    if (!r && autocreatequota > 0) {
-		(void) mboxlist_setquota(mailboxname, autocreatequota, 0);
-	    }
-	}
     }
 
     if (imapd_mailbox) {
diff -Naur cyrus-imapd-2.1.10/imap/lmtpd.c cyrus-imapd-2.1.10-autocreate/imap/lmtpd.c
--- cyrus-imapd-2.1.10/imap/lmtpd.c	Wed Nov  6 22:43:22 2002
+++ cyrus-imapd-2.1.10-autocreate/imap/lmtpd.c	Fri Nov 15 19:15:14 2002
@@ -1380,6 +1380,10 @@
     int r;
     int sl = strlen(BB);
 
+    sfolder *subfolder;
+    char mailboxname[MAX_MAILBOX_NAME+1];
+    int i;
+
     /* check to see if mailbox exists and we can append to it */
     if (!strncmp(user, BB, sl) && user[sl] == '+') {
 	/* special shared folder address */
@@ -1405,6 +1409,21 @@
 	       - don't care about message size (1 msg over quota allowed) */
 	    r = append_check(buf, MAILBOX_FORMAT_NORMAL, authstate,
 			     0, quotacheck > 0 ? 0 : quotacheck);
+
+	    if (r == IMAP_MAILBOX_NONEXISTENT ) {
+	        r=mboxlist_autocreate_inbox(buf, (char *)user, authstate, 1, 0, 1);
+
+	        if (!r) {
+	            subfolder=mboxlist_get_subfolders();
+	            for(i=0;subfolder[i].folder!=NULL;i++){
+	                r = (*lmtpd_namespace.mboxname_tointernal)(&lmtpd_namespace, subfolder[i].folder, 
+					                           user, mailboxname);
+	                if (!r) r=mboxlist_autocreate_inbox(mailboxname, (char *)user,
+				                            authstate, 0, subfolder[i].sub, 1);
+	            }
+	            free_subfolder(subfolder);
+	        }
+	    }
 	}
     }
 
diff -Naur cyrus-imapd-2.1.10/imap/mboxlist.c cyrus-imapd-2.1.10-autocreate/imap/mboxlist.c
--- cyrus-imapd-2.1.10/imap/mboxlist.c	Wed Nov  6 22:43:22 2002
+++ cyrus-imapd-2.1.10-autocreate/imap/mboxlist.c	Fri Nov 15 19:15:14 2002
@@ -2724,3 +2724,161 @@
     mboxlist_closesubs(subs);
     return r;
 }
+
+/*
+ * Autocreate INBOX upon Login
+ */
+
+int
+mboxlist_autocreate_inbox (const char *mailboxname, char *userid,
+			   struct auth_state *auth_state, int isinbox,
+			   int sub_flag, int islmtp)
+{
+  char *partition = NULL;
+  int autocreatequota;
+  int r = 0;
+
+  if (isinbox)
+    {
+
+      if (islmtp)
+	{
+	  if (!config_getswitch ("createonpost", 0))
+	    return IMAP_MAILBOX_NONEXISTENT;
+	}
+      else
+	{
+	  r = mboxlist_lookup (mailboxname, NULL, NULL, NULL);
+	  switch (r)
+	    {
+	    case IMAP_MAILBOX_NONEXISTENT:
+	      break;
+	    case 0:
+	      return IMAP_MAILBOX_EXISTS;
+	      break;
+	    default:
+	      return r;
+	      break;
+	    }
+	}
+
+      autocreatequota = config_getint ("autocreatequota", 0);
+      if (autocreatequota)
+	{
+	  r = mboxlist_createmailbox (mailboxname, MAILBOX_FORMAT_NORMAL,
+				      partition, 1, userid, auth_state, 0, 0);
+	  if (!r)
+	    {
+	      r = mboxlist_changesub (mailboxname, userid,
+				      auth_state, 1, islmtp == 1 ? 1 : 0);
+	      if (!r && autocreatequota > 0)
+		{
+		  r = mboxlist_setquota (mailboxname, autocreatequota, 0);
+		}
+	    }
+	  syslog (LOG_NOTICE, "User %s, INBOX autocreate in partition-%s: %s",
+		  userid, partition,
+		  r == 0 ? "succeeded" : error_message (r));
+
+	}
+
+      return r;
+    }
+  else
+    {
+      r = mboxlist_createmailbox (mailboxname, MAILBOX_FORMAT_NORMAL,
+				  NULL, 1, userid, auth_state, 0, 0);
+      if (!r && sub_flag)
+	{
+	  r = mboxlist_changesub (mailboxname, userid,
+				  auth_state, 1, islmtp == 1 ? 1 : 0);
+	}
+      syslog (LOG_INFO, "User %s, %s autocreate: %s", userid, mailboxname,
+	      r == 0 ? "succeeded" : error_message (r));
+      return r;
+    }
+}
+
+#define SEPERATOR "|"
+#define SUBFLAG "SUB:"
+
+/*
+ * Retrive INBOX subfolders to create upon Login
+ */
+sfolder *
+mboxlist_get_subfolders ()
+{
+  char *autofolders;
+  char *p, *q;
+  char *name;
+  int sub_flag = 0, len = 0, i = 0;
+
+  sfolder *subfolder = 0;
+
+  autofolders = (char *) xstrdup (config_getstring ("autocreatefolders", ""));
+  p = strtok (autofolders, SEPERATOR);
+  while (p)
+    {
+      while (*p && isspace ((int) *p))
+	p++;
+      if (!strncmp (p, SUBFLAG, strlen (SUBFLAG)))
+	{
+	  sub_flag = 1;
+	  p += strlen (SUBFLAG);
+	  while (*p && isspace ((int) *p))
+	    p++;
+	}
+      for (q = p + strlen (p) - 1; q > p && isspace ((int) *q); q--)
+	{
+	  *q = '\0';
+	}
+      if (strlen (p) == 0)
+	{
+	  p = strtok (NULL, SEPERATOR);
+	  continue;
+	}
+
+      len = strlen ("INBOX.") + strlen (p);
+      name = xmalloc ((len + 1) * sizeof (char));
+      memcpy (name, "INBOX.", strlen ("INBOX."));
+      memcpy (name + strlen ("INBOX."), p, strlen (p));
+      name[len] = NULL;
+      i++;
+
+      subfolder = xrealloc (subfolder, i * sizeof (sfolder));
+      subfolder[i - 1].folder = xstrdup (name);
+      subfolder[i - 1].sub = sub_flag;
+
+      free (name);
+      name = NULL;
+      sub_flag = 0;
+      p = strtok (NULL, SEPERATOR);
+    }
+  /* Null termination */
+  subfolder = xrealloc (subfolder, (i + 1) * sizeof (sfolder));
+  subfolder[i].folder = NULL;
+  subfolder[i].sub = 0;
+
+  free (autofolders);
+  autofolders = NULL;
+
+  return subfolder;
+}
+
+
+/*
+ * Free sfolder structs
+ */
+void
+free_subfolder (sfolder * subfolder)
+{
+  int i;
+
+  for (i = 0; subfolder[i].folder != NULL; i++)
+    {
+      free (subfolder[i].folder);
+    }
+
+  free (subfolder);
+  subfolder = NULL;
+}
diff -Naur cyrus-imapd-2.1.10/imap/mboxlist.h cyrus-imapd-2.1.10-autocreate/imap/mboxlist.h
--- cyrus-imapd-2.1.10/imap/mboxlist.h	Wed May 29 19:49:16 2002
+++ cyrus-imapd-2.1.10-autocreate/imap/mboxlist.h	Fri Nov 15 19:15:14 2002
@@ -82,6 +82,12 @@
     char acls[1];
 };
 
+/* INBOX subfolders to create upon Login */
+typedef struct {
+         char *folder;
+         int sub;
+}sfolder;
+
 /* Lookup 'name' in the mailbox list. */
 int mboxlist_lookup(const char *name, char **pathp, char **aclp, void *tid);
 
@@ -188,5 +194,18 @@
 
 /* done with database stuff */
 void mboxlist_done(void);
+
+/* Autocreate INBOXes upon Login */
+int mboxlist_autocreate_inbox(const char *mailboxname, char *userid,
+                      struct auth_state *auth_state, int isinbox, int sub_flag, int islmtp);
+/*
+ * Retrive INBOX subfolders to create upon Login
+ */
+sfolder *mboxlist_get_subfolders(void);
+ 
+/*
+ * Free sfolder structs
+ */
+void free_subfolder(sfolder *subfolder);
 
 #endif


More information about the Info-cyrus mailing list