merged
authorwenzelm
Wed, 06 Nov 2019 23:25:11 +0100
changeset 71069 9314a4cc84ea
parent 71065 98ac9a4323a2 (current diff)
parent 71068 510b89906d86 (diff)
child 71070 79b89278b825
merged
--- a/etc/options	Wed Nov 06 21:23:43 2019 +0100
+++ b/etc/options	Wed Nov 06 23:25:11 2019 +0100
@@ -343,22 +343,6 @@
 option build_log_transaction_size : int = 1  -- "number of log files for each db update"
 
 
-section "Phabricator server"
-
-option phabricator_www_user : string = "www-data"
-option phabricator_www_root : string = "/var/www"
-
-option phabricator_mysql_config : string = "/etc/mysql/debian.cnf"
-option phabricator_apache_root : string = "/etc/apache2"
-
-option phabricator_smtp_host : string = ""
-option phabricator_smtp_port : int = 465
-option phabricator_smtp_user : string = ""
-option phabricator_smtp_passwd : string = ""
-option phabricator_smtp_protocol : string = "ssl"
-option phabricator_smtp_message_id : bool = true
-
-
 section "Isabelle/Scala/ML system channel"
 
 option system_channel_address : string = ""
--- a/src/Pure/Tools/phabricator.scala	Wed Nov 06 21:23:43 2019 +0100
+++ b/src/Pure/Tools/phabricator.scala	Wed Nov 06 23:25:11 2019 +0100
@@ -1,7 +1,9 @@
 /*  Title:      Pure/Tools/phabricator.scala
     Author:     Makarius
 
-Support for Phabricator server. See also:
+Support for Phabricator server, notably for Ubuntu 18.04 LTS.
+
+See also:
   - https://www.phacility.com/phabricator
   - https://secure.phabricator.com/book/phabricator
 */
@@ -30,6 +32,8 @@
 
   /* global system resources */
 
+  val www_user = "www-data"
+
   val daemon_user = "phabricator"
 
   val ssh_standard = 22
@@ -47,12 +51,28 @@
   def isabelle_phabricator_name(name: String = "", ext: String = ""): String =
     "isabelle-" + phabricator_name(name = name, ext = ext)
 
-  def default_root(options: Options, name: String): Path =
-    Path.explode(options.string("phabricator_www_root")) +
-    Path.basic(phabricator_name(name = name))
+  def default_root(name: String): Path =
+    Path.explode("/var/www") + Path.basic(phabricator_name(name = name))
+
+  def default_repo(name: String): Path = default_root(name) + Path.basic("repo")
+
+  val mailers_path: Path = Path.explode("mailers.json")
 
-  def default_repo(options: Options, name: String): Path =
-    default_root(options, name) + Path.basic("repo")
+  val mailers_template: String =
+"""[
+  {
+    "key": "example.org",
+    "type": "smtp",
+    "options": {
+      "host": "mail.example.org",
+      "port": 465,
+      "user": "phabricator@example.org",
+      "password": "********",
+      "protocol": "ssl",
+      "message-id": true
+    }
+  }
+]"""
 
 
 
@@ -108,7 +128,6 @@
   }
 
   def phabricator_setup(
-    options: Options,
     name: String = default_name,
     root: String = "",
     repo: String = "",
@@ -137,13 +156,11 @@
     user_setup(daemon_user, "Phabricator Daemon User", ssh_setup = true)
     user_setup(name, "Phabricator SSH User")
 
-    val www_user = options.string("phabricator_www_user")
-
 
     /* basic installation */
 
-    val root_path = if (root.nonEmpty) Path.explode(root) else default_root(options, name)
-    val repo_path = if (repo.nonEmpty) Path.explode(repo) else default_repo(options, name)
+    val root_path = if (root.nonEmpty) Path.explode(root) else default_root(name)
+    val repo_path = if (repo.nonEmpty) Path.explode(repo) else default_repo(name)
 
     val configs = read_config()
 
@@ -203,8 +220,7 @@
 
 
     def mysql_conf(R: Regex): Option[String] =
-      split_lines(File.read(Path.explode(options.string("phabricator_mysql_config")))).
-        collectFirst({ case R(a) => a })
+      split_lines(File.read(Path.explode("/etc/mysql/debian.cnf"))).collectFirst({ case R(a) => a })
 
     for (user <- mysql_conf("""^user\s*=\s*(\S*)\s*$""".r)) {
       config.execute("config set mysql.user " + Bash.string(user))
@@ -260,7 +276,7 @@
 
     progress.echo("Apache setup...")
 
-    val apache_root = Path.explode(options.string("phabricator_apache_root"))
+    val apache_root = Path.explode("/etc/apache2")
     val apache_sites = apache_root + Path.explode("sites-available")
 
     if (!apache_sites.is_dir) error("Bad Apache sites directory " + apache_sites)
@@ -317,6 +333,15 @@
 """)
 
 
+    /* mail configuration */
+
+    val mail_config = config.home + mailers_path
+
+    progress.echo("Template for mail configuration: " + mail_config)
+
+    File.write(mail_config, mailers_template)
+
+
     progress.echo("\nDONE\nWeb configuration via " + server_url)
   }
 
@@ -328,7 +353,6 @@
     {
       var repo = ""
       var package_update = false
-      var options = Options.init()
       var root = ""
 
       val getopts =
@@ -336,10 +360,9 @@
 Usage: isabelle phabricator_setup [OPTIONS] [NAME]
 
   Options are:
-    -R DIR       repository directory (default: """ + default_repo(options, "NAME") + """)
+    -R DIR       repository directory (default: """ + default_repo("NAME") + """)
     -U           full update of system packages before installation
-    -o OPTION    override Isabelle system OPTION (via NAME=VAL or NAME)
-    -r DIR       installation root directory (default: """ + default_root(options, "NAME") + """)
+    -r DIR       installation root directory (default: """ + default_root("NAME") + """)
 
   Install Phabricator as Ubuntu LAMP application (Linux, Apache, MySQL, PHP).
 
@@ -351,7 +374,6 @@
 """,
           "R:" -> (arg => repo = arg),
           "U" -> (_ => package_update = true),
-          "o:" -> (arg => options = options + arg),
           "r:" -> (arg => root = arg))
 
       val more_args = getopts(args)
@@ -365,44 +387,85 @@
 
       val progress = new Console_Progress
 
-      phabricator_setup(options, name, root = root, repo = repo,
+      phabricator_setup(name, root = root, repo = repo,
         package_update = package_update, progress = progress)
     })
 
 
 
-  /** update **/
+  /** setup mail **/
 
-  def phabricator_update(name: String, progress: Progress = No_Progress)
+  def phabricator_setup_mail(
+    name: String = default_name,
+    config_file: Option[Path] = None,
+    test_user: String = "",
+    progress: Progress = No_Progress)
   {
     Linux.check_system_root()
 
-    ???
+    val config = get_config(name)
+    val default_config_file = config.home + mailers_path
+
+    val mail_config = config_file getOrElse default_config_file
+
+    def setup_mail
+    {
+      progress.echo("Using mail configuration from " + mail_config)
+      config.execute("config set cluster.mailers --stdin < " + File.bash_path(mail_config))
+
+      if (test_user.nonEmpty) {
+        progress.echo("Sending test mail to " + quote(test_user))
+        progress.bash(cwd = config.home.file, echo = true,
+          script = """echo "Test from Phabricator ($(date))" | ./bin/mail send-test --subject "Test" --to """ +
+            Bash.string(test_user)).check
+      }
+    }
+
+    if (config_file.isEmpty) {
+      if (!default_config_file.is_file) File.write(default_config_file, mailers_template)
+      if (File.read(default_config_file) == mailers_template) {
+        progress.echo(
+          "Please invoke the tool again, after providing details in\n  " + default_config_file)
+      }
+      else setup_mail
+    }
+    else setup_mail
   }
 
 
   /* Isabelle tool wrapper */
 
   val isabelle_tool2 =
-    Isabelle_Tool("phabricator_update", "update Phabricator server installation", args =>
+    Isabelle_Tool("phabricator_setup_mail",
+      "setup mail configuration for existing Phabricator server", args =>
     {
+      var test_user = ""
+      var name = default_name
+      var config_file: Option[Path] = None
+
       val getopts =
         Getopts("""
-Usage: isabelle phabricator_update [NAME]
+Usage: isabelle phabricator_setup_mail [OPTIONS]
+
+  Options are:
+    -T USER      send test mail to Phabricator user
+    -f FILE      config file (default: """ + mailers_path + """ within installation home)
+    -n NAME      Phabricator installation name (default: """ + quote(default_name) + """)
 
-  Update Phabricator installation, with lookup of NAME (default + """ + quote(default_name) + """)
-  in """ + global_config + "\n")
+  Provide mail configuration for existing Phabricator installation. See also
+  https://secure.phabricator.com/book/phabricator/article/configuring_outbound_email
+  (notably section "Mailer: SMTP").
+""",
+          "T:" -> (arg => test_user = arg),
+          "f:" -> (arg => config_file = Some(Path.explode(arg))),
+          "n:" -> (arg => name = arg))
 
       val more_args = getopts(args)
-      val name =
-        more_args match {
-          case Nil => default_name
-          case List(name) => name
-          case _ => getopts.usage()
-        }
+      if (more_args.nonEmpty) getopts.usage()
 
       val progress = new Console_Progress
 
-      phabricator_update(name, progress = progress)
+      phabricator_setup_mail(name = name, config_file = config_file,
+        test_user = test_user, progress = progress)
     })
 }