diff --git a/.gitignore b/.gitignore
index dade81e..20e461c 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,2 +1,3 @@
Gemfile.lock
.bundled_gems/
+.vagrant
diff --git a/manifests/init.pp b/manifests/init.pp
index 2857582..b8a40ae 100644
--- a/manifests/init.pp
+++ b/manifests/init.pp
@@ -1,174 +1,90 @@
+# Copyright 2016 Hewlett Packard Enterprise Development Company, L.P.
+#
+# Licensed under the Apache License, Version 2.0 (the "License"); you may
+# not use this file except in compliance with the License. You may obtain
+# a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+# License for the specific language governing permissions and limitations
+# under the License.
+#
# == Class: phabricator
#
+# Set up a full, standalone instance of phabricator.
+#
class phabricator (
- $mysql_user_password,
- $instance = 'dev',
+ # Database Configurations.
$mysql_database = 'phabricator',
$mysql_host = 'localhost',
$mysql_port = 3306,
$mysql_user = 'phabricator',
- $phab_dir = '/phabricator',
- $ssl_cert_file = "/etc/ssl/certs/${::fqdn}.pem",
+ $mysql_user_password,
+ $mysql_root_password,
+
+ # Phabricator working directory
+ $phabricator_dir = '/opt/phabricator',
+
+ # OpenID configuration
+ $auth_location = '/auth/login/RemoteUser:self/',
+ $authopenidsingleidp = 'https://openstackid.org/',
+
+ # SSL Certificates.
+ $ssl_cert_file = undef,
$ssl_cert_file_contents = undef, # If left empty puppet will not create file.
$ssl_chain_file = undef,
$ssl_chain_file_contents = undef, # If left empty puppet will not create file.
- $ssl_key_file = "/etc/ssl/private/${::fqdn}.key",
- $ssl_key_file_contents = undef, # If left empty puppet will not create file.
- $vhost_name = $::fqdn,
+ $ssl_key_file = undef,
+ $ssl_key_file_contents = undef, # If left empty puppet will not create file.
+
+ # Httpd config.
+ $httpd_vhost = $::fqdn,
+ $httpd_admin_email = 'noc@openstack.org',
) {
- $instances_dir = "${phab_dir}/instances"
- $instance_dir = "${instances_dir}/${instance}"
+ # Set up the shared configuration.
+ class { '::phabricator::vars':
+ mysql_database => $mysql_database,
+ mysql_host => $mysql_host,
+ mysql_port => $mysql_port,
+ mysql_user => $mysql_user,
+ mysql_user_password => $mysql_user_password,
+ mysql_root_password => $mysql_root_password,
+ phabricator_dir => $phabricator_dir,
+ ssl_cert_file => $ssl_cert_file,
+ ssl_cert_file_contents => $ssl_cert_file_contents,
+ ssl_chain_file => $ssl_chain_file,
+ ssl_chain_file_contents => $ssl_chain_file_contents,
+ ssl_key_file => $ssl_key_file,
+ ssl_key_file_contents => $ssl_key_file_contents,
+ httpd_vhost => $httpd_vhost,
+ httpd_admin_email => $httpd_admin_email,
- $packages = [
- 'php5',
- 'php5-mysql',
- 'php5-gd',
- 'php5-dev',
- 'php5-curl',
- 'php-apc',
- 'php5-cli',
- 'python-pygmentize'
- ]
- package { $packages:
- ensure => installed,
- }
-
- if !defined(Package['git']) {
- package { 'git':
- ensure => present
- }
- }
-
- file { $phab_dir:
- ensure => directory,
- }
- file { $instances_dir:
- ensure => directory,
- }
- file { $instance_dir:
- ensure => directory,
- }
-
- if $ssl_cert_file_contents != undef {
- file { $ssl_cert_file:
- owner => 'root',
- group => 'root',
- mode => '0640',
- content => $ssl_cert_file_contents,
- before => Httpd::Vhost[$vhost_name],
- }
- }
-
- if $ssl_key_file_contents != undef {
- file { $ssl_key_file:
- owner => 'root',
- group => 'ssl-cert',
- mode => '0640',
- content => $ssl_key_file_contents,
- before => Httpd::Vhost[$vhost_name],
- }
- }
-
- if $ssl_chain_file_contents != undef {
- file { $ssl_chain_file:
- owner => 'root',
- group => 'root',
- mode => '0640',
- content => $ssl_chain_file_contents,
- before => Httpd::Vhost[$vhost_name],
- }
- }
-
- vcsrepo { "${instance_dir}/phabricator":
- ensure => latest,
- provider => git,
- source => 'https://github.com/phacility/phabricator.git',
- require => [
- File[$instance_dir],
- Package['git'],
+ before => [
+ Class['Phabricator::Certificates'],
+ Class['Phabricator::Httpd'],
+ Class['Phabricator::Mysql'],
+ Class['Phabricator::Install'],
]
}
- vcsrepo { "${instance_dir}/arcanist":
- ensure => latest,
- provider => git,
- source => 'https://github.com/phacility/arcanist.git',
- require => [
- File[$instance_dir],
- Package['git'],
+ include ::phabricator::certificates
+ include ::phabricator::mysql
+
+ class { '::phabricator::httpd':
+ require => [
+ Class['phabricator::install'],
+ Class['phabricator::mysql'],
+ Class['phabricator::certificates']
]
}
- vcsrepo { "${instance_dir}/libphutil":
- ensure => latest,
- provider => git,
- source => 'https://github.com/phacility/libphutil.git',
- require => [
- File[$instance_dir],
- Package['git'],
+ class { '::phabricator::install':
+ require => [
+ Class['phabricator::mysql'],
]
}
-
- file { 'initial.db':
- ensure => present,
- path => "${phab_dir}/initial.db",
- source => 'puppet:///modules/phabricator/initial.db',
- }
-
- file {'local.json':
- ensure => present,
- path => "${instance_dir}/phabricator/conf/local/local.json",
- content => template('phabricator/local.json.erb'),
- }
-
- file { '/etc/php5/mods-available/phabricator.ini':
- ensure => present,
- owner => 'root',
- group => 'root',
- content => "; configuration for phabricator\n; priority=20\npost_max_size = 32M",
-
- }
-
- file { '/etc/php5/apache2/conf.d/20-phabricator.ini':
- ensure => 'link',
- target => '/etc/php5/mods-available/phabricator.ini',
- notify => Service['httpd'],
- }
-
- exec { 'load-initial-db':
- command => "/usr/bin/mysql < ${phab_dir}/initial.db && ${instance_dir}/phabricator/bin/storage upgrade --force",
- unless => "${instance_dir}/phabricator/bin/storage status",
- subscribe => File['initial.db'],
- refreshonly => true,
- require => [
- Vcsrepo["${instance_dir}/phabricator"],
- File['initial.db'],
- ]
- }
-
- exec { 'update-database':
- command => "${instance_dir}/phabricator/bin/storage upgrade --force",
- refreshonly => true,
- subscribe => Vcsrepo["${instance_dir}/phabricator"],
- require => Vcsrepo["${instance_dir}/phabricator"],
- }
-
- include ::httpd
- include ::httpd::ssl
- include ::httpd::php
-
- httpd_mod { 'rewrite':
- ensure => present,
- }
-
- ::httpd::vhost { $vhost_name:
- port => 443,
- docroot => "${instance_dir}/phabricator/webroot/",
- priority => '50',
- template => 'phabricator/vhost.erb',
- ssl => true,
- require => File[$instance_dir],
- }
-
}
diff --git a/manifests/install.pp b/manifests/install.pp
new file mode 100644
index 0000000..a8e68be
--- /dev/null
+++ b/manifests/install.pp
@@ -0,0 +1,195 @@
+# Copyright 2016 Hewlett Packard Enterprise Development Company, L.P.
+#
+# Licensed under the Apache License, Version 2.0 (the "License"); you may
+# not use this file except in compliance with the License. You may obtain
+# a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+# License for the specific language governing permissions and limitations
+# under the License.
+#
+# == Class: phabricator::install
+#
+# Installation of phabricator itself.
+#
+class phabricator::install (
+ $phabricator_dir = $phabricator::vars::phabricator_dir,
+ $mysql_database = $phabricator::vars::mysql_database,
+ $mysql_host = $phabricator::vars::mysql_host,
+ $mysql_port = $phabricator::vars::mysql_port,
+ $mysql_user = $phabricator::vars::mysql_user,
+ $mysql_user_password = $phabricator::vars::mysql_user_password,
+ $httpd_vhost = $phabricator::vars::httpd_vhost,
+) {
+
+ # Dependencies
+ package { [
+ 'php5',
+ 'php5-mysql',
+ 'php5-gd',
+ 'php5-dev',
+ 'php5-curl',
+ 'php-apc',
+ 'php5-cli',
+ 'php5-json',
+ 'sendmail',
+ 'python-pygments']:
+ ensure => present,
+ }
+ if !defined(Package['git']) {
+ package { 'git':
+ ensure => present
+ }
+ }
+ if !defined(Package['libapache2-mod-auth-openid']) {
+ package { 'libapache2-mod-auth-openid':
+ ensure => present
+ }
+ }
+
+ # Set "post_max_size" in your PHP configuration to at least 32MB to support
+ # large file uploads.
+ ini_setting { 'Increase post_max_size in php.ini':
+ ensure => present,
+ path => '/etc/php5/apache2/php.ini',
+ section => 'PHP',
+ setting => 'post_max_size',
+ value => '32M',
+ notify => Service['httpd'],
+ }
+
+ # In production, OPcache should be configured to never revalidate code. This
+ # will slightly improve performance. To do this, disable
+ # "opcache.validate_timestamps" in your PHP configuration.
+ ini_setting { 'Set opcache.validate_timestamps in php.ini':
+ ensure => present,
+ path => '/etc/php5/apache2/php.ini',
+ section => 'opcache',
+ setting => 'opcache.validate_timestamps',
+ value => '0',
+ notify => Service['httpd'],
+ }
+
+ # PHP setting "always_populate_raw_post_data" should be set to "-1" to avoid
+ # deprecation warnings.
+ ini_setting { 'Disable PHP always_populate_raw_post_data on php.ini':
+ ensure => present,
+ path => '/etc/php5/apache2/php.ini',
+ section => 'PHP',
+ setting => 'always_populate_raw_post_data',
+ value => '-1',
+ notify => Service['httpd'],
+ }
+
+ file { [$phabricator_dir, "${phabricator_dir}/repo"]:
+ ensure => directory,
+ }
+
+ vcsrepo { "${phabricator_dir}/phabricator":
+ ensure => latest,
+ provider => git,
+ source => 'https://github.com/phacility/phabricator.git',
+ revision => 'stable',
+ require => [
+ File[$phabricator_dir],
+ Package['git'],
+ ]
+ }
+
+ vcsrepo { "${phabricator_dir}/arcanist":
+ ensure => latest,
+ provider => git,
+ source => 'https://github.com/phacility/arcanist.git',
+ revision => 'stable',
+ require => [
+ File[$phabricator_dir],
+ Package['git'],
+ ]
+ }
+
+ vcsrepo { "${phabricator_dir}/libphutil":
+ ensure => latest,
+ provider => git,
+ source => 'https://github.com/phacility/libphutil.git',
+ revision => 'stable',
+ require => [
+ File[$phabricator_dir],
+ Package['git'],
+ ]
+ }
+
+ vcsrepo { "${phabricator_dir}/libphremoteuser":
+ ensure => latest,
+ provider => git,
+ source => 'https://github.com/psigen/libphremoteuser.git',
+ revision => 'master',
+ require => [
+ File[$phabricator_dir],
+ Package['git', 'libapache2-mod-auth-openid'],
+ ]
+ }
+
+ exec { 'Letting Phabricator know about libphremoteuser...':
+ command => "${phabricator_dir}/phabricator/bin/config set load-libraries '[\"libphremoteuser/src\"]'",
+ subscribe => Vcsrepo["${phabricator_dir}/libphremoteuser"],
+ require => [
+ Vcsrepo["${phabricator_dir}/arcanist"],
+ Vcsrepo["${phabricator_dir}/libphremoteuser"],
+ ]
+ }
+
+ exec {'set-auth_providerconfig':
+ command => "/usr/bin/mysql -u ${mysql_user} -p${mysql_user_password} < ${phabricator_dir}/set-auth_providerconfig.sql",
+ subscribe => File['set-auth_providerconfig.sql'],
+ require => [
+ Vcsrepo["${phabricator_dir}/phabricator"],
+ File['set-auth_providerconfig.sql'],
+ File[$phabricator_dir],
+ Service['Phabricator-daemons']
+ ]
+ }
+
+ file {'set-auth_providerconfig.sql':
+ ensure => present,
+ path => "${phabricator_dir}/set-auth_providerconfig.sql",
+ content => template('phabricator/set-auth_providerconfig.sql.erb'),
+ }
+
+ file { 'local.json':
+ ensure => present,
+ path => "${phabricator_dir}/phabricator/conf/local/local.json",
+ content => template('phabricator/local.json.erb'),
+ require => Vcsrepo["${phabricator_dir}/phabricator"],
+ notify => Service['httpd'],
+ }
+
+ exec { 'load-initial-db':
+ command => "${phabricator_dir}/phabricator/bin/storage upgrade --force",
+ unless => "${phabricator_dir}/phabricator/bin/storage status",
+ require => [
+ Vcsrepo["${phabricator_dir}/phabricator"],
+ Vcsrepo["${phabricator_dir}/libphutil"],
+ Vcsrepo["${phabricator_dir}/arcanist"],
+ ]
+ }
+
+ service { 'Phabricator-daemons':
+ ensure => running,
+ provider => base,
+ start => "${phabricator_dir}/phabricator/bin/phd start",
+ stop => "${phabricator_dir}/phabricator/bin/phd stop",
+ restart => "${phabricator_dir}/phabricator/bin/phd restart",
+ status => "${phabricator_dir}/phabricator/bin/phd status",
+ subscribe => Vcsrepo["${phabricator_dir}/libphutil"],
+ require => [
+ File[$phabricator_dir],
+ Vcsrepo["${phabricator_dir}/phabricator"],
+ Vcsrepo["${phabricator_dir}/libphutil"],
+ Vcsrepo["${phabricator_dir}/arcanist"],
+ ]
+ }
+}
diff --git a/manifests/mysql.pp b/manifests/mysql.pp
index f76128a..f5d3ab4 100644
--- a/manifests/mysql.pp
+++ b/manifests/mysql.pp
@@ -1,4 +1,4 @@
-# Copyright 2014 Hewlett-Packard Development Company, L.P.
+# Copyright 2016 Hewlett Packard Enterprise Development Company, L.P.
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
@@ -14,31 +14,41 @@
#
# == Class: phabricator::mysql
#
+# Set up a mysql host for phabricator.
+#
class phabricator::mysql(
- $mysql_root_password,
- $mysql_bind_address = '127.0.0.1',
- $mysql_port = '3306'
- ) {
+ $mysql_host = $phabricator::vars::mysql_host,
+ $mysql_port = $phabricator::vars::mysql_port,
+ $mysql_user = $phabricator::vars::mysql_user,
+ $mysql_user_password = $phabricator::vars::mysql_user_password,
+ $mysql_root_password = $phabricator::vars::mysql_root_password,
+) {
- class { '::mysql::server':
- config_hash => {
- 'root_password' => $mysql_root_password,
- 'default_engine' => 'InnoDB',
- 'bind_address' => $mysql_bind_address,
- 'port' => $mysql_port,
- }
- }
-
- mysql::server::config { 'phab_config':
- settings => {
- 'mysqld' => {
- 'max_allowed_packet' => '32M',
- 'sql_mode' => 'STRICT_ALL_TABLES',
- 'ft_stopword_file' => '/phabricator/instances/dev/phabricator/resources/sql/stopwords.txt',
- 'ft_min_word_len' => '3',
- 'ft_boolean_syntax' => '\' |-><()~*:""&^\'',
- 'innodb_buffer_pool_size' => '1600M',
- }
+ class { '::mysql::server':
+ root_password => $mysql_root_password,
+ remove_default_accounts => true,
+ override_options => {
+ mysqld => {
+ max_allowed_packet => '32M',
+ sql_mode => 'STRICT_ALL_TABLES',
+ ft_stopword_file => '/opt/phabricator/phabricator/resources/sql/stopwords.txt',
+ ft_min_word_len => 3,
+ ft_boolean_syntax => '\' |-><()~*:""&^\'',
+ innodb_buffer_pool_size => '1600M',
}
- }
+ },
}
+
+ mysql_user { "${mysql_user}@${mysql_host}":
+ provider => 'mysql',
+ password_hash => mysql_password($mysql_user_password),
+ }
+
+ # Phabricator creates a mess of tables. This ensures that we don't have
+ # to create ACL's for all of them.
+ mysql_grant { "${mysql_user}@${mysql_host}/phabricator%.*":
+ privileges => ['ALL'],
+ table => 'phabricator%.*',
+ user => "${mysql_user}@${mysql_host}",
+ }
+}
diff --git a/manifests/vars.pp b/manifests/vars.pp
new file mode 100644
index 0000000..d1fdf84
--- /dev/null
+++ b/manifests/vars.pp
@@ -0,0 +1,47 @@
+# Copyright 2016 Hewlett Packard Enterprise Development Company, L.P.
+#
+# Licensed under the Apache License, Version 2.0 (the "License"); you may
+# not use this file except in compliance with the License. You may obtain
+# a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+# License for the specific language governing permissions and limitations
+# under the License.
+#
+# == Class: phabricator::vars
+#
+# Variables, and their defaults, shared between all the submodules. This
+# module is used as the source of all the shared default values.
+#
+class phabricator::vars (
+ # Database Configurations.
+ $mysql_database = 'phabricator',
+ $mysql_host = 'localhost',
+ $mysql_port = 3306,
+ $mysql_user = 'phabricator',
+ $mysql_user_password,
+ $mysql_root_password,
+
+ # Phabricator working directory
+ $phabricator_dir = '/opt/phabricator',
+
+ # SSL Certificates.
+ $ssl_cert_file = undef,
+ $ssl_cert_file_contents = undef, # If left empty puppet will not create file.
+ $ssl_chain_file = undef,
+ $ssl_chain_file_contents = undef, # If left empty puppet will not create file.
+ $ssl_key_file = undef,
+ $ssl_key_file_contents = undef, # If left empty puppet will not create file.
+
+ # Virtual host config.
+ $httpd_vhost = $::fqdn,
+ $httpd_admin_email = 'noc@openstack.org',
+) {
+
+ # Non-configurable-options (derived)
+ $httpd_docroot = "${phabricator_dir}/phabricator/webroot"
+}
diff --git a/templates/set-auth_providerconfig.sql.erb b/templates/set-auth_providerconfig.sql.erb
new file mode 100644
index 0000000..0dce575
--- /dev/null
+++ b/templates/set-auth_providerconfig.sql.erb
@@ -0,0 +1,19 @@
+DELETE FROM phabricator_auth.auth_providerconfig;
+
+INSERT INTO phabricator_auth.auth_providerconfig
+ SELECT
+ 1 as id,
+ "PHID-AUTH-7nztvra7ehvmx2xnmjgc" as phid,
+ "PhabricatorAuthProviderRemoteUser" as providerClass,
+ "RemoteUser" as providerType,
+ "self" as providerDomain,
+ 1 as isEnabled,
+ 1 as shouldAllowLogin,
+ 1 as shouldAllowRegistration,
+ 1 as shouldAllowLink,
+ 1 as shouldAllowUnlink,
+ 1 as shouldTrustEmails,
+ "[]" as properties,
+ 1469712430 as dateCreated,
+ 1469712430 as dateModified,
+ 0 as shouldAutoLogin;
diff --git a/templates/vhost.erb b/templates/vhost.erb
index de27939..cc3e424 100644
--- a/templates/vhost.erb
+++ b/templates/vhost.erb
@@ -1,6 +1,6 @@
- ServerAdmin noc@openstack.org
- ServerName <%= scope.lookupvar("phabricator::vhost_name") %>
+ ServerAdmin <%= @httpd_admin_email %>
+ ServerName <%= @httpd_vhost %>
DocumentRoot /var/www
@@ -16,7 +16,7 @@
RewriteEngine on
RewriteCond %{SERVER_PORT} !^443$
- RewriteRule ^/(.*)$ https://<%= scope.lookupvar("phabricator::vhost_name") %>/$1 [L,R]
+ RewriteRule ^/(.*)$ https://<%= @httpd_vhost %>/$1 [L,R]
ErrorLog /var/log/apache2/phabricator-error.log
@@ -30,24 +30,24 @@
ServerAdmin noc@openstack.org
- ServerName <%= scope.lookupvar("phabricator::vhost_name") %>
+ ServerName <%= @httpd_vhost %>
SSLEngine on
SSLProtocol All -SSLv2 -SSLv3
- SSLCertificateFile <%= scope.lookupvar("phabricator::ssl_cert_file") %>
- SSLCertificateKeyFile <%= scope.lookupvar("phabricator::ssl_key_file") %>
+ SSLCertificateFile <%= @ssl_cert_file %>
+ SSLCertificateKeyFile <%= @ssl_key_file %>
<%# scope.lookupvar returns nil for an undefined variable in puppet 4 -%>
<%# scope.lookupvar returns :undef for an undefined variable in puppet 3 -%>
- <% unless ['', nil, :undef].include?(scope.lookupvar("phabricator::ssl_chain_file")) %>
- SSLCertificateChainFile <%= scope.lookupvar("phabricator::ssl_chain_file") %>
+ <% unless ['', nil, :undef].include?(scope.lookupvar("ssl_chain_file")) %>
+ SSLCertificateChainFile <%= @ssl_chain_file %>
<% end %>
- DocumentRoot <%= @docroot %>
+ DocumentRoot <%= @httpd_docroot %>
Options FollowSymLinks
AllowOverride None
- >
+ >
Options Indexes FollowSymLinks MultiViews
AllowOverride None
Order allow,deny
@@ -55,6 +55,12 @@
Require all granted
+ >
+ AuthType OpenID
+ require valid-user
+ AuthOpenIDSingleIdP <%= @authopenidsingleidp %>
+
+
RewriteEngine on
RewriteRule ^/rsrc/(.*) - [L,QSA]
RewriteRule ^/favicon.ico - [L,QSA]