Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Habitat: maximum integration #55

Open
wants to merge 56 commits into
base: develop
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
56 commits
Select commit Hold shift + click to select a range
6e05f66
Initialize habitat plan
themightychris May 27, 2017
a54c680
Enable node scaffolding
themightychris May 27, 2017
1931095
Remove pkg_source for local build
themightychris May 27, 2017
90e5a36
Set pkg_upstream_url to github
themightychris May 27, 2017
305eae0
Set package name and origin
themightychris May 27, 2017
9d22b78
Add build dependencies
themightychris May 27, 2017
32f81cb
Add core services and runtime dependencies
themightychris May 27, 2017
b5e283e
Add habitat results/ directory to .gitignore
themightychris May 27, 2017
1788779
Configure node engine version
themightychris May 27, 2017
992cc01
Bump kernel package version to 1.0.0
themightychris May 27, 2017
1f88be9
Configure npm start script
themightychris May 27, 2017
550d697
Add basic config for kernel
themightychris May 27, 2017
99b2ee4
Copy php plan from habitat core-plans
themightychris May 27, 2017
d3a4473
Compile apcu statically into php
themightychris May 27, 2017
5b32593
Add service-plans results to .gitignore
themightychris May 27, 2017
1285533
Change php origin to emergence
themightychris May 27, 2017
8431416
Copy mariadb plan from habitat core-plans
themightychris May 27, 2017
c211143
Change mariadb origin to emergence
themightychris May 27, 2017
8e549ad
Add sed to mariadb runtime requirements for mysql_install_db
themightychris May 27, 2017
1962e15
Copy nginx plan from habitat core-plans
themightychris May 28, 2017
9814cfd
Move nginx service config to runtime configuration file
themightychris May 28, 2017
ea9a64f
Move useful config-driven sections of nginx.conf to reusable includes
themightychris May 28, 2017
9e96f34
Add config_path to nginx for passing custom configuration file
themightychris May 28, 2017
211e38d
Convert kernel to use habitat environment
themightychris May 28, 2017
41cd875
Restore nginx defaults to do_build
themightychris May 28, 2017
eadf8df
Tweak nginx config
themightychris May 28, 2017
4441ec4
Ensure rX permissions on svc/static tree
themightychris May 28, 2017
5dc20fe
Pass bindPort into kernel configuration
themightychris May 28, 2017
87ef825
Add default site with generic welcome message
themightychris May 28, 2017
6c0e1f5
Only enforce origin for CORS preflight requests
themightychris May 28, 2017
a27b0ca
Enable gettext extension for PHP
themightychris May 28, 2017
af85cc0
Copy php5 plan from habitat core-plans
themightychris May 28, 2017
c37be9b
Change php5 plan origin to emergence
themightychris May 28, 2017
a9873c2
Add needed extensions to php5
themightychris May 28, 2017
5ba9b11
Switch kernel to use php5
themightychris May 28, 2017
bade584
Pass timezone to kernel config.json and use in bin/shell
themightychris May 29, 2017
76fba33
Ensure config directory is iterable
themightychris May 29, 2017
fb2d969
Use bash shell for init script and remove pushd/popd commands
themightychris Jun 17, 2017
a39ff95
Add bash to runtime dependencies
themightychris Jun 17, 2017
a5a8eda
Apply php.ini to php-fpm to load zend opcache
themightychris Jun 17, 2017
398a8da
Add readline to php builds for CLI support
themightychris Jun 17, 2017
c2f0d0d
Add coreutils to runtime deps for shell scripts
themightychris Jun 17, 2017
36096f5
Fix bash interpreter in shell scripts
themightychris Jun 17, 2017
f3ecd0f
Use su instead of sudo for privilege drop
themightychris Jun 17, 2017
04eb7b1
Update readme format and add habitat instructions
themightychris Jun 18, 2017
8a2f14a
Test existing kernel socket and delete if stale
themightychris Jun 19, 2017
9ff4506
Add git to runtime dependencies
themightychris Jun 20, 2017
d242847
Link hab and git binaries for PHP scripts
themightychris Jun 20, 2017
69b444d
Update git-shell script for habitat environment
themightychris Jun 20, 2017
295aebf
Use local underscore executable
themightychris Jun 20, 2017
9a33fb3
Add curl runtime dependency
themightychris Jun 20, 2017
2052038
Use new curl syntax for unix socket URLs
themightychris Jun 20, 2017
70dc78d
Add ssh-keygen to bin
themightychris Jun 21, 2017
8278f5f
Add ssh client to bin
themightychris Jun 21, 2017
c912890
WIP: Upgrade mariadb to 10.2
themightychris Sep 6, 2017
eba358b
Commit TODOs and dev scripts
themightychris Dec 31, 2017
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
/node_modules/
.DS_Store
/typings/
/typings/
/results/
/service-plans/*/results/
89 changes: 55 additions & 34 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,44 +1,65 @@
Emergence
=========
# Emergence

[![Join the chat at https://gitter.im/JarvusInnovations/Emergence](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/JarvusInnovations/Emergence?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)

Emergence is a NodeJS-powered server that provides a web interface for configuring and launching the services that power your website or application. It provides virtualized storage containers for your code and assets that are accessible via WebDAV and API. Each storage container maintains complete version history for all files and can be linked over the web to a parent container that files will be inherited from just-in-time.


Features
---------
* Rich web interface provides for all setup and management
* Plugin-based support for system services to be configured and run
* Plugins included for nginx and mysql
* Versioned storage containers
* Inherit remote containers over http
* Copy-on-write
* Accessible remotely via WebDAV and locally via API
* PHP development framework
* Classes automatically loaded from storage container
* Lightweight MVC classes optimized for serial inheritance across sites
* Extendable templating system powered by Dwoo


Requirements
-------------
* NodeJS
* npm
* underscore
* node-static
* mysql
* nginx
* php-fpm
* php 5.3+
* apc
* mysqli


Installation
--------------
## Features

- Rich web interface provides for all setup and management
- Plugin-based support for system services to be configured and run
- Plugins included for nginx and mysql
- Versioned storage containers
- Inherit remote containers over http
- Copy-on-write
- Accessible remotely via WebDAV and locally via API
- PHP development framework
- Classes automatically loaded from storage container
- Lightweight MVC classes optimized for serial inheritance across sites
- Extendable templating system powered by Dwoo


## Installation

See http://emr.ge/docs


## Building with Habitat

- `cd ~/Repositories/emergence`
- `hab studio enter`
- `build`
- Optionally export a docker container image: `hab pkg export docker emergence/emergence-kernel`


## Debugging with Habitat

From within studio: `hab sup start emergence/emergence-kernel`


## Running with Docker

- Start a container from new image: `docker run -it -p 9080:80 -p 9083:9083 --name myemergence emergence/emergence-kernel`


## Habitat Migration Todo

- [X] Use habitat config system to generate base service configs, add `include .../var/nginx.sites` to nginx, stick dynamic ish there
- [ ] Compare stock services configs with hab-provided configs
- [ ] Pull Request mariadb fix
- [ ] Get nginx running with configured external config
- [X] Move stock nginx config bodies to .include files (e.g. http.include)
- [X] Add default static nginx site to nginx.conf before sites include
- [ ] Review all initialized permissions
- [ ] Remove shelljs
- [ ] Upgrade dwoo and see if php7 works

- Get docker container working
- [X] Run new docker container
- [X] Check that Zend is loaded now
- [X] get shell wrapper working
- [X] Figure out why cookies dont work -- set from console for now
- [X] Commit changes

Visit http://serverhost:9083 in your browser
- [ ] PR readline into core-plans php and php5
26 changes: 19 additions & 7 deletions bin/create-site.sh → bin/create-site
Original file line number Diff line number Diff line change
@@ -1,5 +1,21 @@
#!/bin/bash


# determine location of this script
SOURCE="${BASH_SOURCE[0]}"
while [ -h "$SOURCE" ]; do # resolve $SOURCE until the file is no longer a symlink
DIR="$( cd -P "$( dirname "$SOURCE" )" && pwd )"
SOURCE="$(readlink "$SOURCE")"
[[ $SOURCE != /* ]] && SOURCE="$DIR/$SOURCE" # if $SOURCE was a relative symlink, we need to resolve it relative to the path where the symlink file was located
done
DIR="$( cd -P "$( dirname "$SOURCE" )" && pwd )"


# get path to underscore
UNDERSCORE=$DIR/../node_modules/.bin/underscore


# parse args
DEFAULT_PRECACHE_TREES='dwoo-plugins,event-handlers,html-templates,php-classes,php-config,php-migrations,site-root,site-tasks'
DEFAULT_GENERATE_TABLES='UserSession,User'

Expand Down Expand Up @@ -77,12 +93,8 @@ case $i in
esac
done

if [ "$GENERATE_TABLES" ] || [ "$PRECACHE_TREES" ] || [ "$ENTER_SHELL" ]; then
command -v underscore >/dev/null 2>&1 || { echo >&2 "underscore must be installed to use --precache-trees or --generate-tables"; exit 1; }
fi

if [ -z "$KERNEL_SOCKET" ]; then
KERNEL_SOCKET="/emergence/kernel.sock"
KERNEL_SOCKET="/hab/svc/emergence-kernel/var/run/kernel.sock"
fi

if [ ! -S "$KERNEL_SOCKET" ]; then
Expand Down Expand Up @@ -136,7 +148,7 @@ RESPONSE=$(
--unix-socket "${KERNEL_SOCKET}" \
-H "Content-Type: application/json" \
-d "${REQUEST_BODY}" \
"http:/sites"
"http://localhost/sites"
)

echo "$RESPONSE"
Expand All @@ -145,7 +157,7 @@ if [ -z "$PRECACHE_TREES" ] && [ -z "$GENERATE_TABLES" ] && [ -z "$ENTER_SHELL"
exit 0
fi

SITE_HANDLE=$(echo "${RESPONSE}" | underscore --outfmt=text extract data.handle)
SITE_HANDLE=$(echo "${RESPONSE}" | $UNDERSCORE --outfmt=text extract data.handle)

if [ "$PRECACHE_TREES" ]; then
emergence-shell $SITE_HANDLE 1>&2 << END_OF_PHP
Expand Down
36 changes: 20 additions & 16 deletions bin/git-shell
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,6 @@ SITE_HANDLE=$1
SITE_LAYER=$2

UNDERSCORE=$DIR/../node_modules/.bin/underscore
EMERGENCE_USER=`cat /emergence/config.json | $UNDERSCORE extract user --outfmt text`

BLACK="\033[01;30m"
MAGENTA="\033[1;31m"
Expand All @@ -43,13 +42,12 @@ PS2="\[$ORANGE\]→ \[$RESET\]" \


# check environment
test $EUID -eq 0 || die "emergence-git-shell must be run with sudo"
test -x "$UNDERSCORE" || die "unable to execute $UNDERSCORE"
test -n "$SITE_HANDLE" -a -n "$SITE_LAYER"|| die "usage: emergence-git-shell site_handle layer_id"


# get site directory
SITE_DIR="/emergence/sites/$SITE_HANDLE"
SITE_DIR="/hab/svc/emergence-kernel/data/sites/$SITE_HANDLE"
test -d "$SITE_DIR" || die "site $SITE_HANDLE not found at $SITE_DIR"


Expand Down Expand Up @@ -89,6 +87,20 @@ if [ -n "$GIT_USER_DIRTY" ]; then
fi


# setup environment
export PS1
export PS2
export SITE_HOSTNAME
export SITE_LAYER
export GIT_SSH

export HISTFILE="$GIT_DIR.bash_history"
export GIT_AUTHOR_NAME="$GIT_NAME"
export GIT_AUTHOR_EMAIL="$GIT_EMAIL"
export GIT_COMMITTER_NAME="$GIT_NAME"
export GIT_COMMITTER_EMAIL="$GIT_EMAIL"


# execute subshell
echo "Opening git shell at $GIT_DIR"
cd $GIT_DIR
Expand All @@ -97,16 +109,8 @@ git status

echo "Committing as $GIT_NAME <$GIT_EMAIL>"

exec sudo -u $EMERGENCE_USER \
HOME="$GIT_DIR" \
HISTFILE="$GIT_DIR.bash_history" \
GIT_SSH="$GIT_SSH" \
GIT_AUTHOR_NAME="$GIT_NAME" \
GIT_AUTHOR_EMAIL="$GIT_EMAIL" \
GIT_COMMITTER_NAME="$GIT_NAME" \
GIT_COMMITTER_EMAIL="$GIT_EMAIL" \
PS1="$PS1" \
PS2="$PS2" \
SITE_HOSTNAME="$SITE_HOSTNAME" \
SITE_LAYER="$SITE_LAYER" \
/bin/bash --norc
if [ "$(whoami)" == "hab" ]; then
HOME="$GIT_DIR" exec bash --norc
else
exec su hab -c "HOME='$GIT_DIR' bash --norc"
fi
151 changes: 5 additions & 146 deletions bin/kernel
Original file line number Diff line number Diff line change
Expand Up @@ -6,160 +6,19 @@ var _ = require('underscore'),
url = require('url'),
path = require('path'),
fs = require('fs'),
sitesLib = require('../kernel-lib/sites.js');


var CONFIG;

if (fs.existsSync('/emergence/config.json')) {
// try to load existing kernel config

CONFIG = JSON.parse(fs.readFileSync('/emergence/config.json', 'ascii'));
} else {
// try to smart-init a new kernel config
var issueFile = "",
platform = require('os').platform(),
distro = platform;

// detect ubuntu
// TODO: find better ways to determine default options than platform detection
if (platform == 'linux') {
try {
issueFile = fs.readFileSync('/etc/issue', 'ascii');
if (issueFile.match(/Ubuntu/)) {
distro = 'ubuntu';
}
} catch (err) {
// ignore any failure to real /etc/issue and leave platform set to linux
}
}

console.log('Initializing new emergence environment for distro="'+distro+'"...');

if (!fs.existsSync('/emergence')) {
fs.mkdirSync('/emergence', '775');
}

CONFIG = {
user: distro=='ubuntu' ? 'www-data' : 'nobody',
group: distro=='ubuntu' ? 'www-data' : 'nobody',

server: {
host: "0.0.0.0"
},
services: {
plugins: { }
}
};




// detect nginx
if (fs.existsSync('/usr/sbin/nginx')) {
CONFIG.services.plugins.web = {
type: 'nginx',
autoStart: true,
execPath: '/usr/sbin/nginx',
bindHost: '0.0.0.0'
};
} else if (fs.existsSync('/usr/local/sbin/nginx')) {
CONFIG.services.plugins.web = {
type: 'nginx',
autoStart: true,
execPath: '/usr/local/sbin/nginx',
bindHost: '0.0.0.0'
};
}

// detect mysql
if (fs.existsSync('/usr/sbin/mysqld')) {
CONFIG.services.plugins.sql = {
type: 'mysql',
autoStart: true,
execPath: '/usr/sbin/mysqld',
managerUser: 'root',
managerPassword: sitesLib.generatePassword()
};
} else if (fs.existsSync('/usr/local/bin/mysqld')) {
CONFIG.services.plugins.sql = {
type: 'mysql',
autoStart: true,
execPath: '/usr/local/bin/mysqld',
managerUser: 'root',
managerPassword: sitesLib.generatePassword()
};
} else if (fs.existsSync('/usr/bin/mysqld_safe')) {
CONFIG.services.plugins.sql = {
type: 'mysql',
autoStart: true,
execPath: '/usr/bin/mysqld_safe',
managerUser: 'root',
managerPassword: sitesLib.generatePassword()
};
}

// detect php-fpm
if (fs.existsSync('/usr/sbin/php-fpm5.6')) {
CONFIG.services.plugins.php = {
type: 'php-fpm',
autoStart: true,
execPath: '/usr/sbin/php-fpm5.6'
};
} else if (fs.existsSync('/usr/sbin/php-fpm7.0')) {
CONFIG.services.plugins.php = {
type: 'php-fpm',
autoStart: true,
execPath: '/usr/sbin/php-fpm7.0'
};
} else if (fs.existsSync('/usr/bin/php-fpm')) {
CONFIG.services.plugins.php = {
type: 'php-fpm',
autoStart: true,
execPath: '/usr/bin/php-fpm'
};
} else if (fs.existsSync('/usr/sbin/php5-fpm')) {
CONFIG.services.plugins.php = {
type: 'php-fpm',
autoStart: true,
execPath: '/usr/sbin/php5-fpm'
};
} else if (fs.existsSync('/usr/local/sbin/php-fpm')) {
CONFIG.services.plugins.php = {
type: 'php-fpm',
autoStart: true,
execPath: '/usr/local/sbin/php-fpm'
};
} else if (fs.existsSync('/usr/sbin/php-fpm')) {
CONFIG.services.plugins.php = {
type: 'php-fpm',
autoStart: true,
execPath: '/usr/sbin/php-fpm'
};
}

fs.writeFileSync('/emergence/config.json', JSON.stringify(CONFIG, null, 4));
fs.chmodSync('/emergence/config.json', '600');
console.log('Generated and wrote initial config: /emergence/config.json');
}

// create default admin user
if (!fs.existsSync('/emergence/admins.htpasswd')) {
console.log('Creating default administrative user: admin/admin');
fs.writeFileSync('/emergence/admins.htpasswd', 'admin:{SHA}0DPiKuNIrrVmD8IUCuw1hQxNqZc=');
fs.chmodSync('/emergence/admins.htpasswd', '600');
}
sitesLib = require('../kernel-lib/sites.js'),
kernelConfig = require('/hab/svc/emergence-kernel/config/config.json');


// load core modules
var eSites = sitesLib.createSites(CONFIG);
var eServices = require('../kernel-lib/services.js').createServices(eSites, CONFIG);
var eSites = sitesLib.createSites(kernelConfig);
var eServices = require('../kernel-lib/services.js').createServices(eSites, kernelConfig);

// instantiate management server
var eManagementServer = require('../kernel-lib/server.js').createServer({
sites: eSites,
services: eServices
}, CONFIG);
}, kernelConfig);


// start server
Expand Down
Loading